Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
23 commits
Select commit Hold shift + click to select a range
f4d3cbc
Use AccountId passed through pallet-evm config
dmitrylavrenov Apr 27, 2023
813c7c9
Fix mocking with external account id usage
dmitrylavrenov Apr 27, 2023
b4295c2
Little fix with sufficients to make all tests working
dmitrylavrenov May 1, 2023
7d1501c
Introduce pallet-evm-system
dmitrylavrenov May 4, 2023
364f78c
Use full info account representation
dmitrylavrenov May 4, 2023
531917b
Use AccountProvider for frame-evm
dmitrylavrenov May 4, 2023
4f74dc0
Add NativeSystemAccountProvider default implementation
dmitrylavrenov May 4, 2023
cc5db17
Restrict Index type
dmitrylavrenov May 4, 2023
e8e6d50
Fix frame evm mock
dmitrylavrenov May 4, 2023
ef440b0
Apply changes to runner stack logic
dmitrylavrenov May 4, 2023
54ad15d
Revert changes applied to test with sufficients
dmitrylavrenov May 4, 2023
ff02337
Apply account provider logic at dispatch evm precompile
dmitrylavrenov May 4, 2023
9503d2a
Fix mock ethereum
dmitrylavrenov May 4, 2023
d155faa
Fix frontier template
dmitrylavrenov May 4, 2023
b160005
Rename description
dmitrylavrenov May 4, 2023
3f6105d
Fix deps
dmitrylavrenov May 5, 2023
5b3325f
Use create and remove accounts logic at account provider
dmitrylavrenov May 5, 2023
0dc1774
Remove redundant providers and sufficients
dmitrylavrenov May 5, 2023
3155c30
Remove toolchain
dmitrylavrenov May 5, 2023
0997a68
Use generic for account data
dmitrylavrenov May 8, 2023
2763294
Edit description
dmitrylavrenov May 8, 2023
b687ed4
Introduce evm-balances
dmitrylavrenov May 8, 2023
112dca3
Use AccountStore type to manage account data
dmitrylavrenov May 8, 2023
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
26 changes: 26 additions & 0 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

4 changes: 4 additions & 0 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,9 @@ members = [
"frame/dynamic-fee",
"frame/ethereum",
"frame/evm",
"frame/evm-balances",
"frame/evm-chain-id",
"frame/evm-system",
"frame/hotfix-sufficients",
"frame/evm/precompile/sha3fips",
"frame/evm/precompile/simple",
Expand Down Expand Up @@ -136,7 +138,9 @@ pallet-base-fee = { version = "1.0.0", path = "frame/base-fee", default-features
pallet-dynamic-fee = { version = "4.0.0-dev", path = "frame/dynamic-fee", default-features = false }
pallet-ethereum = { version = "4.0.0-dev", path = "frame/ethereum", default-features = false }
pallet-evm = { version = "6.0.0-dev", path = "frame/evm", default-features = false }
pallet-evm-balances = { version = "6.0.0-dev", path = "frame/evm-balances", default-features = false }
pallet-evm-chain-id = { version = "1.0.0-dev", path = "frame/evm-chain-id", default-features = false }
pallet-evm-system = { version = "1.0.0-dev", path = "frame/evm-system", default-features = false }
pallet-evm-precompile-modexp = { version = "2.0.0-dev", path = "frame/evm/precompile/modexp", default-features = false }
pallet-evm-precompile-sha3fips = { version = "2.0.0-dev", path = "frame/evm/precompile/sha3fips", default-features = false }
pallet-evm-precompile-simple = { version = "2.0.0-dev", path = "frame/evm/precompile/simple", default-features = false }
Expand Down
1 change: 1 addition & 0 deletions frame/ethereum/src/mock.rs
Original file line number Diff line number Diff line change
Expand Up @@ -152,6 +152,7 @@ impl AddressMapping<AccountId32> for HashedAddressMapping {
}

impl pallet_evm::Config for Test {
type AccountProvider = pallet_evm::NativeSystemAccountProvider<Self>;
type FeeCalculator = FixedGasPrice;
type GasWeightMapping = pallet_evm::FixedGasWeightMapping<Self>;
type WeightPerGas = WeightPerGas;
Expand Down
34 changes: 34 additions & 0 deletions frame/evm-balances/Cargo.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
[package]
name = "pallet-evm-balances"
version = "1.0.0-dev"
license = "Apache-2.0"
description = "FRAME EVM BALANCES pallet."
authors = { workspace = true }
edition = { workspace = true }
repository = { workspace = true }

[package.metadata.docs.rs]
targets = ["x86_64-unknown-linux-gnu"]

[dependencies]
log = { version = "0.4.17", default-features = false }
scale-codec = { package = "parity-scale-codec", workspace = true }
scale-info = { workspace = true }
# Substrate
frame-support = { workspace = true }
frame-system = { workspace = true }
sp-runtime = { workspace = true }
sp-std = { workspace = true }

[features]
default = ["std"]
std = [
"log/std",
"scale-codec/std",
"scale-info/std",
# Substrate
"frame-support/std",
"frame-system/std",
"sp-runtime/std",
"sp-std/std",
]
50 changes: 50 additions & 0 deletions frame/evm-balances/src/account_data.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
//! Account balances logic.

use super::*;

/// All balance information for an account.
#[derive(Encode, Decode, Clone, PartialEq, Eq, Default, RuntimeDebug, MaxEncodedLen, TypeInfo)]
pub struct AccountData<Balance> {
/// Non-reserved part of the balance. There may still be restrictions on this, but it is the
/// total pool what may in principle be transferred, reserved and used for tipping.
///
/// This is the only balance that matters in terms of most operations on tokens. It
/// alone is used to determine the balance when in the contract execution environment.
pub free: Balance,
/// Balance which is reserved and may not be used at all.
///
/// This can still get slashed, but gets slashed last of all.
///
/// This balance is a 'reserve' balance that other subsystems use in order to set aside tokens
/// that are still 'owned' by the account holder, but which are suspendable.
/// This includes named reserve and unnamed reserve.
pub reserved: Balance,
/// The amount that `free` may not drop below when withdrawing for *anything except transaction
/// fee payment*.
pub misc_frozen: Balance,
/// The amount that `free` may not drop below when withdrawing specifically for transaction
/// fee payment.
pub fee_frozen: Balance,
}

impl<Balance: Saturating + Copy + Ord> AccountData<Balance> {
/// How much this account's balance can be reduced for the given `reasons`.
pub(crate) fn usable(&self, reasons: Reasons) -> Balance {
self.free.saturating_sub(self.frozen(reasons))
}

/// The amount that this account's free balance may not be reduced beyond for the given
/// `reasons`.
pub(crate) fn frozen(&self, reasons: Reasons) -> Balance {
match reasons {
Reasons::All => self.misc_frozen.max(self.fee_frozen),
Reasons::Misc => self.misc_frozen,
Reasons::Fee => self.fee_frozen,
}
}

/// The total balance in this account including any that is reserved and ignoring any frozen.
pub(crate) fn total(&self) -> Balance {
self.free.saturating_add(self.reserved)
}
}
172 changes: 172 additions & 0 deletions frame/evm-balances/src/imbalances.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,172 @@
//! Imbalances implementation.

use frame_support::traits::{SameOrOther, TryDrop};
use sp_std::{cmp::Ordering, mem};

use super::*;

/// Opaque, move-only struct with private fields that serves as a token denoting that
/// funds have been created without any equal and opposite accounting.
#[must_use]
#[derive(RuntimeDebug, PartialEq, Eq)]
pub struct PositiveImbalance<T: Config<I>, I: 'static = ()>(T::Balance);

impl<T: Config<I>, I: 'static> PositiveImbalance<T, I> {
/// Create a new positive imbalance from a balance.
pub fn new(amount: T::Balance) -> Self {
PositiveImbalance(amount)
}
}

/// Opaque, move-only struct with private fields that serves as a token denoting that
/// funds have been destroyed without any equal and opposite accounting.
#[must_use]
#[derive(RuntimeDebug, PartialEq, Eq)]
pub struct NegativeImbalance<T: Config<I>, I: 'static = ()>(T::Balance);

impl<T: Config<I>, I: 'static> NegativeImbalance<T, I> {
/// Create a new negative imbalance from a balance.
pub fn new(amount: T::Balance) -> Self {
NegativeImbalance(amount)
}
}

impl<T: Config<I>, I: 'static> TryDrop for PositiveImbalance<T, I> {
fn try_drop(self) -> result::Result<(), Self> {
self.drop_zero()
}
}

impl<T: Config<I>, I: 'static> Default for PositiveImbalance<T, I> {
fn default() -> Self {
Self::zero()
}
}

impl<T: Config<I>, I: 'static> Imbalance<T::Balance> for PositiveImbalance<T, I> {
type Opposite = NegativeImbalance<T, I>;

fn zero() -> Self {
Self(Zero::zero())
}

fn drop_zero(self) -> result::Result<(), Self> {
if self.0.is_zero() {
Ok(())
} else {
Err(self)
}
}

fn split(self, amount: T::Balance) -> (Self, Self) {
let first = self.0.min(amount);
let second = self.0 - first;

mem::forget(self);
(Self(first), Self(second))
}

fn merge(mut self, other: Self) -> Self {
self.0 = self.0.saturating_add(other.0);
mem::forget(other);

self
}

fn subsume(&mut self, other: Self) {
self.0 = self.0.saturating_add(other.0);
mem::forget(other);
}

fn offset(self, other: Self::Opposite) -> SameOrOther<Self, Self::Opposite> {
let (a, b) = (self.0, other.0);
mem::forget((self, other));

match a.cmp(&b) {
Ordering::Greater => SameOrOther::Same(Self(a - b)),
Ordering::Less => SameOrOther::Other(NegativeImbalance::new(b - a)),
Ordering::Equal => SameOrOther::None,
}
}

fn peek(&self) -> T::Balance {
self.0
}
}

impl<T: Config<I>, I: 'static> TryDrop for NegativeImbalance<T, I> {
fn try_drop(self) -> result::Result<(), Self> {
self.drop_zero()
}
}

impl<T: Config<I>, I: 'static> Default for NegativeImbalance<T, I> {
fn default() -> Self {
Self::zero()
}
}

impl<T: Config<I>, I: 'static> Imbalance<T::Balance> for NegativeImbalance<T, I> {
type Opposite = PositiveImbalance<T, I>;

fn zero() -> Self {
Self(Zero::zero())
}

fn drop_zero(self) -> result::Result<(), Self> {
if self.0.is_zero() {
Ok(())
} else {
Err(self)
}
}

fn split(self, amount: T::Balance) -> (Self, Self) {
let first = self.0.min(amount);
let second = self.0 - first;

mem::forget(self);
(Self(first), Self(second))
}

fn merge(mut self, other: Self) -> Self {
self.0 = self.0.saturating_add(other.0);
mem::forget(other);

self
}

fn subsume(&mut self, other: Self) {
self.0 = self.0.saturating_add(other.0);
mem::forget(other);
}

fn offset(self, other: Self::Opposite) -> SameOrOther<Self, Self::Opposite> {
let (a, b) = (self.0, other.0);
mem::forget((self, other));

match a.cmp(&b) {
Ordering::Greater => SameOrOther::Same(Self(a - b)),
Ordering::Less => SameOrOther::Other(PositiveImbalance::new(b - a)),
Ordering::Equal => SameOrOther::None,
}
}

fn peek(&self) -> T::Balance {
self.0
}
}

impl<T: Config<I>, I: 'static> Drop for PositiveImbalance<T, I> {
/// Basic drop handler will just square up the total issuance.
fn drop(&mut self) {
<super::TotalIssuance<T, I>>::mutate(|v| *v = v.saturating_add(self.0));
}
}

impl<T: Config<I>, I: 'static> Drop for NegativeImbalance<T, I> {
/// Basic drop handler will just square up the total issuance.
fn drop(&mut self) {
<super::TotalIssuance<T, I>>::mutate(|v| *v = v.saturating_sub(self.0));
}
}
Loading