Skip to content

Commit

Permalink
feat: send eth tips to collator
Browse files Browse the repository at this point in the history
  • Loading branch information
TarekkMA committed Dec 27, 2024
1 parent d09a674 commit ae79201
Show file tree
Hide file tree
Showing 4 changed files with 166 additions and 99 deletions.
14 changes: 9 additions & 5 deletions runtime/common/src/impl_on_charge_evm_transaction.rs
Original file line number Diff line number Diff line change
Expand Up @@ -22,13 +22,17 @@ macro_rules! impl_on_charge_evm_transaction {
type BalanceFor<T> =
<<T as pallet_evm::Config>::Currency as Inspect<FungibleAccountId<T>>>::Balance;

pub struct OnChargeEVMTransaction<OU>(sp_std::marker::PhantomData<OU>);
pub struct OnChargeEVMTransaction<BaseFeesOU, PriorityFeesOU>(
sp_std::marker::PhantomData<(BaseFeesOU, PriorityFeesOU)>
);

impl<T, OU> OnChargeEVMTransactionT<T> for OnChargeEVMTransaction<OU>
impl<T, BaseFeesOU, PriorityFeesOU> OnChargeEVMTransactionT<T>
for OnChargeEVMTransaction<BaseFeesOU, PriorityFeesOU>
where
T: pallet_evm::Config,
T::Currency: Balanced<pallet_evm::AccountIdOf<T>>,
OU: OnUnbalanced<Credit<pallet_evm::AccountIdOf<T>, T::Currency>>,
BaseFeesOU: OnUnbalanced<Credit<pallet_evm::AccountIdOf<T>, T::Currency>>,
PriorityFeesOU: OnUnbalanced<Credit<pallet_evm::AccountIdOf<T>, T::Currency>>,
U256: UniqueSaturatedInto<<T::Currency as Inspect<pallet_evm::AccountIdOf<T>>>::Balance>,
T::AddressMapping: pallet_evm::AddressMapping<T::AccountId>,
{
Expand All @@ -48,14 +52,14 @@ macro_rules! impl_on_charge_evm_transaction {
base_fee: U256,
already_withdrawn: Self::LiquidityInfo,
) -> Self::LiquidityInfo {
<EVMFungibleAdapter<<T as pallet_evm::Config>::Currency, OU> as OnChargeEVMTransactionT<
<EVMFungibleAdapter<<T as pallet_evm::Config>::Currency, BaseFeesOU> as OnChargeEVMTransactionT<
T,
>>::correct_and_deposit_fee(who, corrected_fee, base_fee, already_withdrawn)
}

fn pay_priority_fee(tip: Self::LiquidityInfo) {
if let Some(tip) = tip {
OU::on_unbalanced(tip);
PriorityFeesOU::on_unbalanced(tip);
}
}
}
Expand Down
85 changes: 53 additions & 32 deletions runtime/moonbase/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -60,7 +60,7 @@ use frame_support::{
construct_runtime,
dispatch::{DispatchClass, GetDispatchInfo, PostDispatchInfo},
ensure,
pallet_prelude::DispatchResult,
pallet_prelude::{DispatchResult, PhantomData},
parameter_types,
traits::{
fungible::{Balanced, Credit, HoldConsideration, Inspect},
Expand Down Expand Up @@ -125,6 +125,7 @@ use xcm_runtime_apis::{
use smallvec::smallvec;
use sp_runtime::serde::{Deserialize, Serialize};

use sp_runtime::traits::TypedGet;
#[cfg(any(feature = "std", test))]
pub use sp_runtime::BuildStorage;

Expand Down Expand Up @@ -338,40 +339,32 @@ impl pallet_balances::Config for Runtime {
type WeightInfo = moonbase_weights::pallet_balances::WeightInfo<Runtime>;
}

pub struct DealWithFees<R>(sp_std::marker::PhantomData<R>);
impl<R> OnUnbalanced<Credit<R::AccountId, pallet_balances::Pallet<R>>> for DealWithFees<R>
/// Deal with substrate based fees and tip. This should be used with pallet_transaction_payment.
pub struct DealWithSubstrateFeesAndTip<R>(sp_std::marker::PhantomData<R>);
impl<R> OnUnbalanced<Credit<R::AccountId, pallet_balances::Pallet<R>>>
for DealWithSubstrateFeesAndTip<R>
where
R: pallet_balances::Config + pallet_treasury::Config,
{
// this seems to be called for substrate-based transactions
fn on_unbalanceds(
mut fees_then_tips: impl Iterator<Item = Credit<R::AccountId, pallet_balances::Pallet<R>>>,
) {
if let Some(fees) = fees_then_tips.next() {
let treasury_proportion =
runtime_params::dynamic_params::runtime_config::FeesTreasuryProportion::get();
let treasury_part = treasury_proportion.deconstruct();
let burn_part = Perbill::one().deconstruct() - treasury_part;
let (_, to_treasury) = fees.ration(burn_part, treasury_part);
// Balances pallet automatically burns dropped Credits by decreasing
// total_supply accordingly
ResolveTo::<TreasuryAccountId<R>, pallet_balances::Pallet<R>>::on_unbalanced(
to_treasury,
);

// handle tip if there is one
if let Some(tip) = fees_then_tips.next() {
// for now we use the same burn/treasury strategy used for regular fees
let (_, to_treasury) = tip.ration(burn_part, treasury_part);
ResolveTo::<TreasuryAccountId<R>, pallet_balances::Pallet<R>>::on_unbalanced(
to_treasury,
);
}
}
fn on_nonzero_unbalanced(amount: Credit<R::AccountId, pallet_balances::Pallet<R>>) {
// Balances pallet automatically burns dropped Credits by decreasing
// total_supply accordingly
let treasury_proportion =
runtime_params::dynamic_params::runtime_config::FeesTreasuryProportion::get();
let treasury_part = treasury_proportion.deconstruct();
let burn_part = Perbill::one().deconstruct() - treasury_part;
let (_, to_treasury) = amount.ration(burn_part, treasury_part);
ResolveTo::<TreasuryAccountId<R>, pallet_balances::Pallet<R>>::on_unbalanced(to_treasury);
}
}

// this is called from pallet_evm for Ethereum-based transactions
// (technically, it calls on_unbalanced, which calls this when non-zero)
/// Deal with ethereum based fees. To handle tips/priority fees, use DealWithEthereumPriorityFees.
pub struct DealWithEthereumBaseFees<R>(sp_std::marker::PhantomData<R>);
impl<R> OnUnbalanced<Credit<R::AccountId, pallet_balances::Pallet<R>>>
for DealWithEthereumBaseFees<R>
where
R: pallet_balances::Config + pallet_treasury::Config,
{
fn on_nonzero_unbalanced(amount: Credit<R::AccountId, pallet_balances::Pallet<R>>) {
// Balances pallet automatically burns dropped Credits by decreasing
// total_supply accordingly
Expand All @@ -384,6 +377,31 @@ where
}
}

pub struct BlockAuthorAccountId<R>(PhantomData<R>);
impl<R> TypedGet for BlockAuthorAccountId<R>
where
R: frame_system::Config + pallet_author_inherent::Config,
pallet_author_inherent::Pallet<R>: Get<R::AccountId>,
{
type Type = R::AccountId;
fn get() -> Self::Type {
<pallet_author_inherent::Pallet<R> as Get<R::AccountId>>::get()
}
}

/// Deal with ethereum based priority fees/tips. See DealWithEthereumBaseFees for base fees.
pub struct DealWithEthereumPriorityFees<R>(sp_std::marker::PhantomData<R>);
impl<R> OnUnbalanced<Credit<R::AccountId, pallet_balances::Pallet<R>>>
for DealWithEthereumPriorityFees<R>
where
R: pallet_balances::Config + pallet_author_inherent::Config,
pallet_author_inherent::Pallet<R>: Get<R::AccountId>,
{
fn on_nonzero_unbalanced(amount: Credit<R::AccountId, pallet_balances::Pallet<R>>) {
ResolveTo::<BlockAuthorAccountId<R>, pallet_balances::Pallet<R>>::on_unbalanced(amount);
}
}

pub struct LengthToFee;
impl WeightToFeePolynomial for LengthToFee {
type Balance = Balance;
Expand All @@ -408,7 +426,7 @@ impl WeightToFeePolynomial for LengthToFee {

impl pallet_transaction_payment::Config for Runtime {
type RuntimeEvent = RuntimeEvent;
type OnChargeTransaction = FungibleAdapter<Balances, DealWithFees<Runtime>>;
type OnChargeTransaction = FungibleAdapter<Balances, DealWithSubstrateFeesAndTip<Runtime>>;
type OperationalFeeMultiplier = ConstU8<5>;
type WeightToFee = ConstantMultiplier<Balance, ConstU128<{ currency::WEIGHT_FEE }>>;
type LengthToFee = LengthToFee;
Expand Down Expand Up @@ -542,7 +560,10 @@ impl pallet_evm::Config for Runtime {
type PrecompilesType = MoonbasePrecompiles<Self>;
type PrecompilesValue = PrecompilesValue;
type ChainId = EthereumChainId;
type OnChargeTransaction = OnChargeEVMTransaction<DealWithFees<Runtime>>;
type OnChargeTransaction = OnChargeEVMTransaction<
DealWithEthereumBaseFees<Runtime>,
DealWithEthereumPriorityFees<Runtime>,
>;
type BlockGasLimit = BlockGasLimit;
type FindAuthor = FindAuthorAdapter<AccountId20, H160, AuthorInherent>;
type OnCreate = ();
Expand Down
83 changes: 52 additions & 31 deletions runtime/moonbeam/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@ use fp_rpc::TransactionStatus;
use cumulus_primitives_core::{relay_chain, AggregateMessageOrigin};
#[cfg(feature = "std")]
pub use fp_evm::GenesisAccount;
use frame_support::pallet_prelude::{TypedGet, PhantomData};
pub use frame_support::traits::Get;
use frame_support::{
construct_runtime,
Expand Down Expand Up @@ -332,40 +333,32 @@ impl pallet_balances::Config for Runtime {
type WeightInfo = moonbeam_weights::pallet_balances::WeightInfo<Runtime>;
}

pub struct DealWithFees<R>(sp_std::marker::PhantomData<R>);
impl<R> OnUnbalanced<Credit<R::AccountId, pallet_balances::Pallet<R>>> for DealWithFees<R>
/// Deal with substrate based fees and tip. This should be used with pallet_transaction_payment.
pub struct DealWithSubstrateFeesAndTip<R>(sp_std::marker::PhantomData<R>);
impl<R> OnUnbalanced<Credit<R::AccountId, pallet_balances::Pallet<R>>>
for DealWithSubstrateFeesAndTip<R>
where
R: pallet_balances::Config + pallet_treasury::Config,
{
// this seems to be called for substrate-based transactions
fn on_unbalanceds(
mut fees_then_tips: impl Iterator<Item = Credit<R::AccountId, pallet_balances::Pallet<R>>>,
) {
if let Some(fees) = fees_then_tips.next() {
let treasury_proportion =
runtime_params::dynamic_params::runtime_config::FeesTreasuryProportion::get();
let treasury_part = treasury_proportion.deconstruct();
let burn_part = Perbill::one().deconstruct() - treasury_part;
let (_, to_treasury) = fees.ration(burn_part, treasury_part);
// Balances pallet automatically burns dropped Credits by decreasing
// total_supply accordingly
ResolveTo::<TreasuryAccountId<R>, pallet_balances::Pallet<R>>::on_unbalanced(
to_treasury,
);

// handle tip if there is one
if let Some(tip) = fees_then_tips.next() {
// for now we use the same burn/treasury strategy used for regular fees
let (_, to_treasury) = tip.ration(burn_part, treasury_part);
ResolveTo::<TreasuryAccountId<R>, pallet_balances::Pallet<R>>::on_unbalanced(
to_treasury,
);
}
}
fn on_nonzero_unbalanced(amount: Credit<R::AccountId, pallet_balances::Pallet<R>>) {
// Balances pallet automatically burns dropped Credits by decreasing
// total_supply accordingly
let treasury_proportion =
runtime_params::dynamic_params::runtime_config::FeesTreasuryProportion::get();
let treasury_part = treasury_proportion.deconstruct();
let burn_part = Perbill::one().deconstruct() - treasury_part;
let (_, to_treasury) = amount.ration(burn_part, treasury_part);
ResolveTo::<TreasuryAccountId<R>, pallet_balances::Pallet<R>>::on_unbalanced(to_treasury);
}
}

// this is called from pallet_evm for Ethereum-based transactions
// (technically, it calls on_unbalanced, which calls this when non-zero)
/// Deal with ethereum based fees. To handle tips/priority fees, use DealWithEthereumPriorityFees.
pub struct DealWithEthereumBaseFees<R>(sp_std::marker::PhantomData<R>);
impl<R> OnUnbalanced<Credit<R::AccountId, pallet_balances::Pallet<R>>>
for DealWithEthereumBaseFees<R>
where
R: pallet_balances::Config + pallet_treasury::Config,
{
fn on_nonzero_unbalanced(amount: Credit<R::AccountId, pallet_balances::Pallet<R>>) {
// Balances pallet automatically burns dropped Credits by decreasing
// total_supply accordingly
Expand All @@ -378,6 +371,31 @@ where
}
}

pub struct BlockAuthorAccountId<R>(PhantomData<R>);
impl<R> TypedGet for BlockAuthorAccountId<R>
where
R: frame_system::Config + pallet_author_inherent::Config,
pallet_author_inherent::Pallet<R>: Get<R::AccountId>,
{
type Type = R::AccountId;
fn get() -> Self::Type {
<pallet_author_inherent::Pallet<R> as Get<R::AccountId>>::get()
}
}

/// Deal with ethereum based priority fees/tips. See DealWithEthereumBaseFees for base fees.
pub struct DealWithEthereumPriorityFees<R>(sp_std::marker::PhantomData<R>);
impl<R> OnUnbalanced<Credit<R::AccountId, pallet_balances::Pallet<R>>>
for DealWithEthereumPriorityFees<R>
where
R: pallet_balances::Config + pallet_author_inherent::Config,
pallet_author_inherent::Pallet<R>: Get<R::AccountId>,
{
fn on_nonzero_unbalanced(amount: Credit<R::AccountId, pallet_balances::Pallet<R>>) {
ResolveTo::<BlockAuthorAccountId<R>, pallet_balances::Pallet<R>>::on_unbalanced(amount);
}
}

pub struct LengthToFee;
impl WeightToFeePolynomial for LengthToFee {
type Balance = Balance;
Expand All @@ -402,7 +420,7 @@ impl WeightToFeePolynomial for LengthToFee {

impl pallet_transaction_payment::Config for Runtime {
type RuntimeEvent = RuntimeEvent;
type OnChargeTransaction = FungibleAdapter<Balances, DealWithFees<Runtime>>;
type OnChargeTransaction = FungibleAdapter<Balances, DealWithSubstrateFeesAndTip<Runtime>>;
type OperationalFeeMultiplier = ConstU8<5>;
type WeightToFee = ConstantMultiplier<Balance, ConstU128<{ currency::WEIGHT_FEE }>>;
type LengthToFee = LengthToFee;
Expand Down Expand Up @@ -533,7 +551,10 @@ impl pallet_evm::Config for Runtime {
type PrecompilesType = MoonbeamPrecompiles<Self>;
type PrecompilesValue = PrecompilesValue;
type ChainId = EthereumChainId;
type OnChargeTransaction = OnChargeEVMTransaction<DealWithFees<Runtime>>;
type OnChargeTransaction = OnChargeEVMTransaction<
DealWithEthereumBaseFees<Runtime>,
DealWithEthereumPriorityFees<Runtime>,
>;
type BlockGasLimit = BlockGasLimit;
type FindAuthor = FindAuthorAdapter<AuthorInherent>;
type OnCreate = ();
Expand Down
Loading

0 comments on commit ae79201

Please sign in to comment.