Skip to content

Commit

Permalink
inject state root along side block hash while initializing next header
Browse files Browse the repository at this point in the history
  • Loading branch information
vedhavyas committed Sep 22, 2023
1 parent e567296 commit e504a94
Show file tree
Hide file tree
Showing 9 changed files with 46 additions and 12 deletions.
1 change: 1 addition & 0 deletions polkadot/node/service/src/fake_runtime_api.rs
Original file line number Diff line number Diff line change
Expand Up @@ -105,6 +105,7 @@ sp_api::impl_runtime_apis! {
_: TransactionSource,
_: <Block as BlockT>::Extrinsic,
_: <Block as BlockT>::Hash,
_: <Block as BlockT>::Hash,
) -> TransactionValidity {
unimplemented!()
}
Expand Down
3 changes: 2 additions & 1 deletion polkadot/runtime/kusama/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1893,8 +1893,9 @@ sp_api::impl_runtime_apis! {
source: TransactionSource,
tx: <Block as BlockT>::Extrinsic,
block_hash: <Block as BlockT>::Hash,
state_root: <Block as BlockT>::Hash,
) -> TransactionValidity {
Executive::validate_transaction(source, tx, block_hash)
Executive::validate_transaction(source, tx, block_hash, state_root)
}
}

Expand Down
3 changes: 2 additions & 1 deletion polkadot/runtime/rococo/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1704,8 +1704,9 @@ sp_api::impl_runtime_apis! {
source: TransactionSource,
tx: <Block as BlockT>::Extrinsic,
block_hash: <Block as BlockT>::Hash,
state_root: <Block as BlockT>::Hash,
) -> TransactionValidity {
Executive::validate_transaction(source, tx, block_hash)
Executive::validate_transaction(source, tx, block_hash, state_root)
}
}

Expand Down
3 changes: 2 additions & 1 deletion polkadot/runtime/westend/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1553,8 +1553,9 @@ sp_api::impl_runtime_apis! {
source: TransactionSource,
tx: <Block as BlockT>::Extrinsic,
block_hash: <Block as BlockT>::Hash,
state_root: <Block as BlockT>::Hash,
) -> TransactionValidity {
Executive::validate_transaction(source, tx, block_hash)
Executive::validate_transaction(source, tx, block_hash, state_root)
}
}

Expand Down
12 changes: 10 additions & 2 deletions substrate/client/transaction-pool/src/api.rs
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@ use sp_runtime::{
traits::{self, Block as BlockT, BlockIdTo},
transaction_validity::{TransactionSource, TransactionValidity},
};
use sp_runtime::traits::Header;
use sp_transaction_pool::runtime_api::TaggedTransactionQueue;

use crate::{
Expand Down Expand Up @@ -229,6 +230,10 @@ where
.map_err(|e| Error::RuntimeApi(e.to_string()))?
.ok_or_else(|| Error::RuntimeApi(format!("Could not get hash for block `{:?}`.", at)))?;

let header = client.header(block_hash)
.map_err(|e| Error::RuntimeApi(e.to_string()))?
.ok_or_else(|| Error::RuntimeApi(format!("Could not get header for block `{:?}`.", at)))?;

let runtime_api = client.runtime_api();
let api_version = sp_tracing::within_span! { sp_tracing::Level::TRACE, "check_version";
runtime_api
Expand All @@ -244,8 +249,11 @@ where
sp_tracing::within_span!(
sp_tracing::Level::TRACE, "runtime::validate_transaction";
{
if api_version >= 3 {
runtime_api.validate_transaction(block_hash, source, uxt, block_hash)
if api_version == 3 {
runtime_api.validate_transaction_before_version_4(block_hash, source, uxt, block_hash)
.map_err(|e| Error::RuntimeApi(e.to_string()))
} else if api_version >= 4 {
runtime_api.validate_transaction(block_hash, source, uxt, block_hash, *header.state_root())
.map_err(|e| Error::RuntimeApi(e.to_string()))
} else {
let block_number = client.to_number(at)
Expand Down
9 changes: 6 additions & 3 deletions substrate/frame/executive/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -418,7 +418,7 @@ where
sp_io::init_tracing();
sp_tracing::enter_span!(sp_tracing::Level::TRACE, "init_block");
let digests = Self::extract_pre_digest(header);
Self::initialize_block_impl(header.number(), header.parent_hash(), &digests);
Self::initialize_block_impl(header.number(), header.parent_hash(), header.state_root(),&digests);
}

fn extract_pre_digest(header: &frame_system::pallet_prelude::HeaderFor<System>) -> Digest {
Expand All @@ -434,6 +434,7 @@ where
fn initialize_block_impl(
block_number: &BlockNumberFor<System>,
parent_hash: &System::Hash,
state_root: &System::Hash,
digest: &Digest,
) {
// Reset events before apply runtime upgrade hook.
Expand All @@ -445,7 +446,7 @@ where
if Self::runtime_upgraded() {
weight = weight.saturating_add(Self::execute_on_runtime_upgrade());
}
<frame_system::Pallet<System>>::initialize(block_number, parent_hash, digest);
<frame_system::Pallet<System>>::initialize(block_number, parent_hash, state_root, digest);
weight = weight.saturating_add(<AllPalletsWithSystem as OnInitialize<
BlockNumberFor<System>,
>>::on_initialize(*block_number));
Expand Down Expand Up @@ -637,13 +638,15 @@ where
source: TransactionSource,
uxt: Block::Extrinsic,
block_hash: Block::Hash,
state_root: Block::Hash,
) -> TransactionValidity {
sp_io::init_tracing();
use sp_tracing::{enter_span, within_span};

<frame_system::Pallet<System>>::initialize(
&(frame_system::Pallet::<System>::block_number() + One::one()),
&block_hash,
&state_root,
&Default::default(),
);

Expand Down Expand Up @@ -679,7 +682,7 @@ where
// OffchainWorker RuntimeApi should skip initialization.
let digests = header.digest().clone();

<frame_system::Pallet<System>>::initialize(header.number(), header.parent_hash(), &digests);
<frame_system::Pallet<System>>::initialize(header.number(), header.parent_hash(), header.state_root(), &digests);

// Frame system only inserts the parent hash into the block hashes as normally we don't know
// the hash for the header before. However, here we are aware of the hash and we can add it
Expand Down
10 changes: 9 additions & 1 deletion substrate/frame/system/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -612,6 +612,12 @@ pub mod pallet {
pub type BlockHash<T: Config> =
StorageMap<_, Twox64Concat, BlockNumberFor<T>, T::Hash, ValueQuery>;

/// Map of block numbers to state roots.
#[pallet::storage]
#[pallet::getter(fn state_root)]
pub type StateRoot<T: Config> =
StorageMap<_, Twox64Concat, BlockNumberFor<T>, T::Hash, ValueQuery>;

/// Extrinsics data for the current block (maps an extrinsic's index to its data).
#[pallet::storage]
#[pallet::getter(fn extrinsic_data)]
Expand Down Expand Up @@ -1390,7 +1396,7 @@ impl<T: Config> Pallet<T> {
}

/// Start the execution of a particular block.
pub fn initialize(number: &BlockNumberFor<T>, parent_hash: &T::Hash, digest: &generic::Digest) {
pub fn initialize(number: &BlockNumberFor<T>, parent_hash: &T::Hash, state_root: &T::Hash, digest: &generic::Digest) {
// populate environment
ExecutionPhase::<T>::put(Phase::Initialization);
storage::unhashed::put(well_known_keys::EXTRINSIC_INDEX, &0u32);
Expand All @@ -1400,6 +1406,7 @@ impl<T: Config> Pallet<T> {
<Digest<T>>::put(digest);
<ParentHash<T>>::put(parent_hash);
<BlockHash<T>>::insert(*number - One::one(), parent_hash);
<StateRoot<T>>::insert(*number - One::one(), state_root);

// Remove previous block data from storage
BlockWeight::<T>::kill();
Expand Down Expand Up @@ -1474,6 +1481,7 @@ impl<T: Config> Pallet<T> {
// keep genesis hash
if !to_remove.is_zero() {
<BlockHash<T>>::remove(to_remove);
<StateRoot<T>>::remove(to_remove);
}

let version = T::Version::get().state_version();
Expand Down
10 changes: 9 additions & 1 deletion substrate/primitives/transaction-pool/src/runtime_api.rs
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ use sp_runtime::{

sp_api::decl_runtime_apis! {
/// The `TaggedTransactionQueue` api trait for interfering with the transaction queue.
#[api_version(3)]
#[api_version(4)]
pub trait TaggedTransactionQueue {
/// Validate the transaction.
#[changed_in(2)]
Expand All @@ -46,10 +46,18 @@ sp_api::decl_runtime_apis! {
///
/// Note that this call may be performed by the pool multiple times and transactions
/// might be verified in any possible order.
#[changed_in(4)]
fn validate_transaction(
source: TransactionSource,
tx: <Block as BlockT>::Extrinsic,
block_hash: Block::Hash,
) -> TransactionValidity;

fn validate_transaction(
source: TransactionSource,
tx: <Block as BlockT>::Extrinsic,
block_hash: Block::Hash,
state_root: Block::Hash,
) -> TransactionValidity;
}
}
7 changes: 5 additions & 2 deletions substrate/test-utils/runtime/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -54,7 +54,7 @@ use sp_trie::{
PrefixedMemoryDB, StorageProof,
};
use trie_db::{Trie, TrieMut};

use sp_core::storage::StateVersion;
use sp_api::{decl_runtime_apis, impl_runtime_apis};
pub use sp_core::hash::H256;
use sp_inherents::{CheckInherentsResult, InherentData};
Expand Down Expand Up @@ -319,6 +319,7 @@ const MAXIMUM_BLOCK_WEIGHT: Weight =
parameter_types! {
pub const BlockHashCount: BlockNumber = 2400;
pub const Version: RuntimeVersion = VERSION;
pub const ExtrinsicsRootStateVersion: StateVersion = StateVersion::V0;

pub RuntimeBlockLength: BlockLength =
BlockLength::max_with_normal_ratio(5 * 1024 * 1024, NORMAL_DISPATCH_RATIO);
Expand Down Expand Up @@ -367,6 +368,7 @@ impl frame_system::pallet::Config for Runtime {
type SS58Prefix = ();
type OnSetCode = ();
type MaxConsumers = ConstU32<16>;
type ExtrinsicsRootStateVersion = ExtrinsicsRootStateVersion;
}

pub mod currency {
Expand Down Expand Up @@ -505,8 +507,9 @@ impl_runtime_apis! {
source: TransactionSource,
utx: <Block as BlockT>::Extrinsic,
block_hash: <Block as BlockT>::Hash,
state_root: <Block as BlockT>::Hash,
) -> TransactionValidity {
let validity = Executive::validate_transaction(source, utx.clone(), block_hash);
let validity = Executive::validate_transaction(source, utx.clone(), block_hash, state_root);
log::trace!(target: LOG_TARGET, "validate_transaction {:?} {:?}", utx, validity);
validity
}
Expand Down

0 comments on commit e504a94

Please sign in to comment.