Skip to content

Commit

Permalink
Merged in CITA_1823_fix_latest_hashes_base_0.20.1 (pull request #1513)
Browse files Browse the repository at this point in the history
remove cached latest hashes
  • Loading branch information
Zhiwei committed Nov 27, 2018
2 parents c011688 + 99a5068 commit cbfb5e4
Showing 1 changed file with 18 additions and 46 deletions.
64 changes: 18 additions & 46 deletions cita-executor/core/src/libexecutor/executor.rs
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,8 @@
use bloomchain::group::{BloomGroup, BloomGroupDatabase, GroupPosition};
pub use byteorder::{BigEndian, ByteOrder};
use call_analytics::CallAnalytics;
use cita_types::traits::LowerHex;
use cita_types::{Address, H256, U256};
use contracts::{
native::factory::Factory as NativeFactory,
solc::{
Expand All @@ -35,23 +37,19 @@ use evm::Schedule;
use executive::{Executed, Executive, TransactOptions};
use factory::*;
use header::*;
use jsonrpc_types::rpctypes::EconomicalModel as RpcEconomicalModel;
use libexecutor::blacklist::BlackList;
pub use libexecutor::block::*;
use libexecutor::call_request::CallRequest;
use libexecutor::genesis::Genesis;

use libproto::blockchain::{Proof as ProtoProof, ProofType, RichStatus};
use libproto::router::{MsgType, RoutingKey, SubModules};
use libproto::{ConsensusConfig, ExecutedResult, Message};

use cita_types::traits::LowerHex;
use cita_types::{Address, H256, U256};
use jsonrpc_types::rpctypes::EconomicalModel as RpcEconomicalModel;
use state::State;
use state_db::StateDB;
use std::cmp::min;
use std::collections::btree_map::{Keys, Values};
use std::collections::{BTreeMap, HashMap, HashSet, VecDeque};
use std::collections::{BTreeMap, HashMap, HashSet};
use std::convert::{From, Into, TryInto};
use std::sync::atomic::{AtomicBool, AtomicUsize, Ordering};
use std::sync::mpsc::Sender;
Expand Down Expand Up @@ -234,8 +232,6 @@ pub struct Executor {
pub db: RwLock<Arc<KeyValueDB>>,
pub state_db: RwLock<StateDB>,
pub factories: Factories,
/// Hash of the given block - only works for 256 most recent blocks excluding current
pub last_hashes: RwLock<VecDeque<H256>>,

/// Cache results after block that executed
pub executed_result: RwLock<BTreeMap<u64, ExecutedResult>>,
Expand Down Expand Up @@ -314,7 +310,6 @@ impl Executor {
db: RwLock::new(db),
state_db: RwLock::new(state_db),
factories,
last_hashes: RwLock::new(VecDeque::new()),

executed_result: RwLock::new(executed_map),
prooftype: executor_config.prooftype,
Expand All @@ -324,9 +319,6 @@ impl Executor {
engine: Box::new(NullEngine::cita()),
};

// Build executor config
executor.build_last_hashes(Some(header.hash()), header.number());

let conf = executor.load_config(BlockId::Pending);
{
*executor.global_config.write() = conf;
Expand Down Expand Up @@ -387,10 +379,6 @@ impl Executor {
self.db.read().read(db::COL_HEADERS, &hash)
}

fn last_hashes(&self) -> LastHashes {
LastHashes::from(self.last_hashes.read().clone())
}

#[inline]
pub fn get_latest_height(&self) -> u64 {
self.current_header.read().number().saturating_sub(1)
Expand Down Expand Up @@ -480,46 +468,31 @@ impl Executor {
}

/// Build last 256 block hashes.
fn build_last_hashes(&self, prevhash: Option<H256>, parent_height: u64) -> Arc<LastHashes> {
fn build_last_hashes(&self, prevhash: Option<H256>, parent_height: u64) -> LastHashes {
let parent_hash = prevhash.unwrap_or_else(|| {
self.block_hash(parent_height)
.expect("Block height always valid.")
});
{
let hashes = self.last_hashes.read();
if hashes.front().map_or(false, |h| h == &parent_hash) {
let mut res = Vec::from(hashes.clone());
res.resize(256, H256::default());
return Arc::new(res);
}
}

let mut last_hashes = LastHashes::new();
last_hashes.resize(256, H256::default());
last_hashes[0] = parent_hash;
for i in 0..255 {
if parent_height < i + 1 {
break;
};
let height = parent_height - i - 1;
for (i, last_hash) in last_hashes
.iter_mut()
.enumerate()
.take(255 as usize)
.skip(1)
{
let height = parent_height - i as u64;
match self.block_hash(height) {
Some(hash) => {
let index = (i + 1) as usize;
last_hashes[index] = hash;
*last_hash = hash;
}
None => break,
}
}
let mut cached_hashes = self.last_hashes.write();
*cached_hashes = VecDeque::from(last_hashes.clone());
Arc::new(last_hashes)
}

fn update_last_hashes(&self, hash: &H256) {
let mut hashes = self.last_hashes.write();
if hashes.len() > 255 {
hashes.pop_back();
}
hashes.push_front(*hash);
last_hashes
}

fn prune_ancient(&self, mut state_db: StateDB) -> Result<(), UtilError> {
Expand Down Expand Up @@ -629,7 +602,7 @@ impl Executor {
author: *header.proposer(),
timestamp: header.timestamp(),
difficulty: U256::default(),
last_hashes,
last_hashes: Arc::new(last_hashes),
gas_used: *header.quota_used(),
gas_limit: *header.quota_limit(),
account_gas_limit: u64::max_value().into(),
Expand Down Expand Up @@ -790,7 +763,6 @@ impl Executor {
{
*self.current_header.write() = header;
}
self.update_last_hashes(&self.get_current_hash());
self.write_batch(closed_block.clone());

self.reorg_config(&closed_block);
Expand Down Expand Up @@ -922,7 +894,7 @@ impl Executor {
pub fn execute_block(&self, block: Block, ctx_pub: &Sender<(String, Vec<u8>)>) {
let now = Instant::now();
let current_state_root = self.current_state_root();
let last_hashes = self.last_hashes();
let last_hashes = self.build_last_hashes(None, block.number() - 1);
let conf = { self.global_config.read().clone() };
let parent_hash = *block.parent_hash();
let check_options = CheckOptions {
Expand Down Expand Up @@ -960,7 +932,7 @@ impl Executor {
pub fn execute_proposal(&self, block: Block) -> Option<ClosedBlock> {
let now = Instant::now();
let current_state_root = self.current_state_root();
let last_hashes = self.last_hashes();
let last_hashes = self.build_last_hashes(None, block.number() - 1);
let conf = self.global_config.read().clone();
let chain_owner = conf.chain_owner;
let parent_hash = *block.parent_hash();
Expand Down

0 comments on commit cbfb5e4

Please sign in to comment.