@@ -101,6 +101,22 @@ pub struct BlockRefMut<'a> {
|
||||
pub traces: &'a Option<Vec<Trace>>,
|
||||
}
|
||||
|
||||
/// A set of immutable references to `ExecutedBlock` fields that are publicly accessible.
|
||||
pub struct BlockRef<'a> {
|
||||
/// Block header.
|
||||
pub header: &'a Header,
|
||||
/// Block transactions.
|
||||
pub transactions: &'a Vec<SignedTransaction>,
|
||||
/// Block uncles.
|
||||
pub uncles: &'a Vec<Header>,
|
||||
/// Transaction receipts.
|
||||
pub receipts: &'a Vec<Receipt>,
|
||||
/// State.
|
||||
pub state: &'a State,
|
||||
/// Traces.
|
||||
pub traces: &'a Option<Vec<Trace>>,
|
||||
}
|
||||
|
||||
impl ExecutedBlock {
|
||||
/// Create a new block from the given `state`.
|
||||
fn new(state: State, tracing: bool) -> ExecutedBlock {
|
||||
@@ -114,7 +130,7 @@ impl ExecutedBlock {
|
||||
}
|
||||
|
||||
/// Get a structure containing individual references to all public fields.
|
||||
pub fn fields(&mut self) -> BlockRefMut {
|
||||
pub fn fields_mut(&mut self) -> BlockRefMut {
|
||||
BlockRefMut {
|
||||
header: &self.base.header,
|
||||
transactions: &self.base.transactions,
|
||||
@@ -124,6 +140,18 @@ impl ExecutedBlock {
|
||||
traces: &self.traces,
|
||||
}
|
||||
}
|
||||
|
||||
/// Get a structure containing individual references to all public fields.
|
||||
pub fn fields(&self) -> BlockRef {
|
||||
BlockRef {
|
||||
header: &self.base.header,
|
||||
transactions: &self.base.transactions,
|
||||
uncles: &self.base.uncles,
|
||||
state: &self.state,
|
||||
receipts: &self.receipts,
|
||||
traces: &self.traces,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// Trait for a object that is_a `ExecutedBlock`.
|
||||
@@ -261,8 +289,8 @@ impl<'x> OpenBlock<'x> {
|
||||
///
|
||||
/// If valid, it will be executed, and archived together with the receipt.
|
||||
pub fn push_transaction(&mut self, t: SignedTransaction, h: Option<H256>) -> Result<&Receipt, Error> {
|
||||
if self.block.transactions_set.contains(t.hash()) {
|
||||
return Err(From::from(ExecutionError::AlreadyImported));
|
||||
if self.block.transactions_set.contains(&t.hash()) {
|
||||
return Err(From::from(TransactionError::AlreadyImported));
|
||||
}
|
||||
|
||||
let env_info = self.env_info();
|
||||
|
||||
@@ -426,9 +426,8 @@ impl<V> BlockChainClient for Client<V> where V: Verifier {
|
||||
block.try_seal(self.engine.deref().deref(), seal)
|
||||
}
|
||||
|
||||
// TODO: either work out a better API than this or refactor prepare_sealing and try_seal in terms of this.
|
||||
fn with_engine<F, T>(&self, f: F) -> T where F: FnOnce(&Engine) -> T {
|
||||
f(self.engine.deref().deref())
|
||||
fn engine(&self) -> &Engine {
|
||||
self.engine.deref().deref()
|
||||
}
|
||||
|
||||
// TODO [todr] Should be moved to miner crate eventually.
|
||||
|
||||
@@ -40,6 +40,7 @@ use log_entry::LocalizedLogEntry;
|
||||
use filter::Filter;
|
||||
use error::{ImportResult, Error};
|
||||
use receipt::LocalizedReceipt;
|
||||
use engine::{Engine};
|
||||
|
||||
/// Blockchain database client. Owns and manages a blockchain and a block queue.
|
||||
pub trait BlockChainClient : Sync + Send {
|
||||
@@ -130,6 +131,6 @@ pub trait BlockChainClient : Sync + Send {
|
||||
fn call(&self, t: &SignedTransaction) -> Result<Executed, Error>;
|
||||
|
||||
/// Executes a function providing it with a reference to an engine.
|
||||
fn with_engine<F>(&self, _f: F) where F: FnOnce(&Engine) {}
|
||||
fn engine(&self) -> &Engine;
|
||||
}
|
||||
|
||||
|
||||
@@ -31,6 +31,7 @@ use block_queue::BlockQueueInfo;
|
||||
use block::{SealedBlock, ClosedBlock};
|
||||
use executive::Executed;
|
||||
use error::Error;
|
||||
use engine::Engine;
|
||||
|
||||
/// Test client.
|
||||
pub struct TestBlockChainClient {
|
||||
@@ -249,7 +250,7 @@ impl BlockChainClient for TestBlockChainClient {
|
||||
}
|
||||
|
||||
fn prepare_sealing(&self, _author: Address, _gas_floor_target: U256, _extra_data: Bytes, _transactions: Vec<SignedTransaction>) -> (Option<ClosedBlock>, HashSet<H256>) {
|
||||
(None, vec![])
|
||||
(None, HashSet::new())
|
||||
}
|
||||
|
||||
fn try_seal(&self, block: ClosedBlock, _seal: Vec<Bytes>) -> Result<SealedBlock, ClosedBlock> {
|
||||
@@ -404,4 +405,8 @@ impl BlockChainClient for TestBlockChainClient {
|
||||
best_block_number: self.blocks.read().unwrap().len() as BlockNumber - 1,
|
||||
}
|
||||
}
|
||||
|
||||
fn engine(&self) -> &Engine {
|
||||
unimplemented!();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -101,7 +101,7 @@ impl Engine for Ethash {
|
||||
/// This assumes that all uncles are valid uncles (i.e. of at least one generation before the current).
|
||||
fn on_close_block(&self, block: &mut ExecutedBlock) {
|
||||
let reward = self.spec().engine_params.get("blockReward").map_or(U256::from(0u64), |a| decode(&a));
|
||||
let fields = block.fields();
|
||||
let fields = block.fields_mut();
|
||||
|
||||
// Bestow block reward
|
||||
fields.state.add_balance(&fields.header.author, &(reward + reward / U256::from(32) * U256::from(fields.uncles.len())));
|
||||
|
||||
Reference in New Issue
Block a user