From 90c340e74b8d7788d64c87c19abb29848499bb3d Mon Sep 17 00:00:00 2001 From: MSNTCS Date: Tue, 14 Jan 2020 17:01:50 +0900 Subject: [PATCH 01/55] Execute self-nomination transactions on a new thread Currently, we have a tool written in TypeScript to run auto-self-nominate. In this new patch, codechain is able to run auto-self-nominate in a different thread. In order to test the functionality of auto-self-nominate, a new `selfnomination` test is added in `e2e.dynval/2/selfnomination.test.ts`. --- Cargo.lock | 1 + Cargo.toml | 1 + codechain/auto_self_nominate.rs | 196 +++++++++++++++++++ codechain/codechain.yml | 15 ++ codechain/config/mod.rs | 29 +++ codechain/config/presets/config.dev.toml | 1 + codechain/config/presets/config.prod.toml | 1 + codechain/main.rs | 1 + codechain/run_node.rs | 17 +- core/src/consensus/mod.rs | 2 +- core/src/consensus/stake/mod.rs | 4 +- core/src/consensus/tendermint/mod.rs | 2 +- core/src/lib.rs | 7 +- core/src/miner/miner.rs | 4 + core/src/miner/mod.rs | 3 + keystore/src/account/decrypted_account.rs | 1 + test/src/config/mem-pool-min-fee1.toml | 1 + test/src/config/mem-pool-min-fee2.toml | 1 + test/src/e2e.dynval/2/selfnomination.test.ts | 125 ++++++++++++ test/src/e2e.dynval/setup.ts | 29 ++- 20 files changed, 425 insertions(+), 16 deletions(-) create mode 100644 codechain/auto_self_nominate.rs create mode 100644 test/src/e2e.dynval/2/selfnomination.test.ts diff --git a/Cargo.lock b/Cargo.lock index b156e752fc..60ed909782 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -281,6 +281,7 @@ dependencies = [ "panic_hook", "parking_lot 0.6.4", "primitives", + "rlp", "rpassword", "rustc-serialize", "serde", diff --git a/Cargo.toml b/Cargo.toml index 753c49c770..ba2ada2085 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -43,6 +43,7 @@ never-type = "0.1.0" panic_hook = { path = "util/panic_hook" } parking_lot = "0.6.0" primitives = { git = "https://github.com/CodeChain-io/rust-codechain-primitives.git", version = "0.4" } +rlp = { git = "https://github.com/CodeChain-io/rlp.git", version = "0.4" } rpassword = "2.0.0" rustc-serialize = "0.3" serde = "1.0" diff --git a/codechain/auto_self_nominate.rs b/codechain/auto_self_nominate.rs new file mode 100644 index 0000000000..dc0598e1d0 --- /dev/null +++ b/codechain/auto_self_nominate.rs @@ -0,0 +1,196 @@ +// Copyright 2020 Kodebox, Inc. +// This file is part of CodeChain. +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU Affero General Public License as +// published by the Free Software Foundation, either version 3 of the +// License, or (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU Affero General Public License for more details. +// +// You should have received a copy of the GNU Affero General Public License +// along with this program. If not, see . + +use crate::config::load_config; +use ccore::stake::Action::SelfNominate; +use ccore::stake::{Banned, Candidates, Jail, CUSTOM_ACTION_HANDLER_ID}; +use ccore::{ + AccountProvider, AccountProviderError, BlockId, ConsensusClient, SignedTransaction, UnverifiedTransaction, +}; +use ckey::PlatformAddress; +use ckey::{Address, Public, Signature}; +use ckeystore::DecryptedAccount; +use clap::ArgMatches; +use codechain_types::transaction::{Action, Transaction}; +use primitives::{Bytes, H256}; +use rlp::Encodable; +use std::sync::Arc; +use std::thread; +use std::time::Duration; + +const NEED_NOMINATION_UNDER_TERM_LEFT: u64 = 1; +#[derive(Clone)] +struct SelfSigner { + account_provider: Arc, + signer: Option<(Address, Public)>, + decrypted_account: Option, +} +impl SelfSigner { + pub fn new(ap: Arc, address: Address) -> Self { + let public = { + let account = ap.get_unlocked_account(&address).expect("The address must be registered in AccountProvider"); + account.public().expect("Cannot get public from account") + }; + Self { + account_provider: ap, + signer: Some((address, public)), + decrypted_account: None, + } + } + + pub fn sign_ecdsa(&self, hash: H256) -> Result { + let address = self.signer.map(|(address, _public)| address).unwrap_or_else(Default::default); + let result = match &self.decrypted_account { + Some(account) => account.sign(&hash)?, + None => { + let account = self.account_provider.get_unlocked_account(&address)?; + account.sign(&hash)? + } + }; + Ok(result) + } + + pub fn address(&self) -> Option<&Address> { + self.signer.as_ref().map(|(address, _)| address) + } +} + +pub struct AutoSelfNomination { + client: Arc, + signer: SelfSigner, +} + +impl AutoSelfNomination { + pub fn new(client: Arc, ap: Arc, address: Address) -> Arc { + Arc::new(Self { + client, + signer: SelfSigner::new(ap, address), + }) + } + + pub fn send_self_nominate_transaction(&self, matches: &ArgMatches) { + let config = load_config(matches).unwrap(); + let account_address = config.mining.engine_signer.unwrap(); + let defualt_metadata = config.mining.self_nomination_metadata.unwrap(); + let target_deposite = config.mining.self_target_deposit.unwrap(); + let interval = config.mining.self_nomination_interval.unwrap(); + let self_client = self.client.clone(); + let self_signer = self.signer.clone(); + thread::Builder::new() + .name("Auto Self Nomination".to_string()) + .spawn(move || loop { + AutoSelfNomination::send( + &self_client, + &self_signer, + &account_address, + &defualt_metadata, + target_deposite, + ); + thread::sleep(Duration::from_millis(interval)); + }) + .unwrap(); + } + + fn send( + client: &Arc, + signer: &SelfSigner, + account_address: &PlatformAddress, + metadata: &str, + targetdep: u64, + ) { + let metabytes = metadata.rlp_bytes(); + let mut dep = targetdep; + let address = account_address.address(); + let block_id = BlockId::Latest; + let state = client.state_at(block_id).unwrap(); + let current_term = client.current_term_id(block_id).unwrap(); + let banned = Banned::load_from_state(&state).unwrap(); + if banned.is_banned(address) { + cwarn!(ENGINE, "Account is banned"); + return + } + let jailed = Jail::load_from_state(&state).unwrap(); + if jailed.get_prisoner(&address).is_some() { + let prisoner = jailed.get_prisoner(&address).unwrap(); + + if prisoner.custody_until <= (current_term) { + cwarn!(ENGINE, "Account is still in custody"); + return + } + } + let candidate = Candidates::load_from_state(&state).unwrap(); + if candidate.get_candidate(&address).is_some() { + let candidate_need_nomination = candidate.get_candidate(&address).unwrap(); + if candidate_need_nomination.nomination_ends_at <= current_term + NEED_NOMINATION_UNDER_TERM_LEFT { + cdebug!(ENGINE, "No need self nominate"); + return + } + if candidate_need_nomination.deposit.lt(&targetdep) { + dep = targetdep.min(targetdep); + } else { + dep = 0 as u64; + } + } + + AutoSelfNomination::self_nomination_transaction(&client, &signer, dep, metabytes); + } + + fn self_nomination_transaction( + client: &Arc, + signer: &SelfSigner, + deposit: u64, + metadata: Bytes, + ) { + let network_id = client.network_id(); + let seq = match signer.address() { + Some(address) => client.latest_seq(address), + None => { + cwarn!(ENGINE, "Signer was not assigned"); + return + } + }; + let selfnominate = SelfNominate { + deposit, + metadata, + }; + let tx = Transaction { + seq, + fee: 0, + network_id, + action: Action::Custom { + handler_id: CUSTOM_ACTION_HANDLER_ID, + bytes: selfnominate.rlp_bytes(), + }, + }; + + let signature = match signer.sign_ecdsa(*tx.hash()) { + Ok(signature) => signature, + Err(e) => { + cerror!(ENGINE, "Could not sign the message:{}", e); + return + } + }; + let unverified = UnverifiedTransaction::new(tx, signature); + let signed = SignedTransaction::try_new(unverified).expect("secret is valid so it's recoverable"); + + match client.queue_own_transaction(signed) { + Ok(_) => {} + Err(e) => { + cerror!(ENGINE, "Failed to queue self nominate transaction: {}", e); + } + } + } +} diff --git a/codechain/codechain.yml b/codechain/codechain.yml index 0558880d58..00a88b0a71 100644 --- a/codechain/codechain.yml +++ b/codechain/codechain.yml @@ -160,6 +160,21 @@ args: long: engine-signer help: Specify the address which should be used to sign consensus messages and issue blocks. takes_value: true + - self-nomination-metadata: + long: self-nomination-metadata + help: Specify metadata which should be used to do self nomination. + takes_value: true + - self-nomination-target-deposit: + long: self-nomination-target-deposit + help: Specify the amount of deposit need to provide deposite for candidatory in the process of self nomination. + takes_value: true + - self-nomination-interval: + long: self-nomination-interval + help: Specify the time(ms) interval for self nomination process. + takes_value: true + - enable-auto-self-nomination: + long: enable-auto-self-nomination + help: Run auto self nomination thread. - password-path: long: password-path help: Specify the password file path. diff --git a/codechain/config/mod.rs b/codechain/config/mod.rs index d126f37692..1a3fbc39a2 100644 --- a/codechain/config/mod.rs +++ b/codechain/config/mod.rs @@ -236,6 +236,10 @@ pub struct Mining { pub engine_signer: Option, pub mem_pool_size: Option, pub mem_pool_mem_limit: Option, + pub self_nomination_metadata: Option, + pub self_target_deposit: Option, + pub self_nomination_enable: bool, + pub self_nomination_interval: Option, pub mem_pool_fee_bump_shift: Option, pub allow_create_shard: Option, pub notify_work: Option>, @@ -411,6 +415,15 @@ impl Mining { if other.engine_signer.is_some() { self.engine_signer = other.engine_signer; } + if other.self_nomination_metadata.is_some() { + self.self_nomination_metadata = other.self_nomination_metadata.clone(); + } + if other.self_target_deposit.is_some() { + self.self_target_deposit = other.self_target_deposit; + } + if other.self_nomination_interval.is_some() { + self.self_nomination_interval = other.self_nomination_interval; + } if other.mem_pool_size.is_some() { self.mem_pool_size = other.mem_pool_size; } @@ -492,6 +505,22 @@ impl Mining { if let Some(engine_signer) = matches.value_of("engine-signer") { self.engine_signer = Some(engine_signer.parse().map_err(|_| "Invalid address format")?); } + if let Some(self_nomination_metadata) = matches.value_of("self-nomination-metadata") { + self.self_nomination_metadata = + Some(self_nomination_metadata.parse().map_err(|_| "Invalid self nomination metadata format")?); + } + if let Some(self_nomination_target_deposit) = matches.value_of("self-nomination-target-deposit") { + self.self_target_deposit = Some( + self_nomination_target_deposit.parse().map_err(|_| "Invalid self nomination target deposit format")?, + ); + } + if let Some(self_nomination_interval) = matches.value_of("self-nomination-interval") { + self.self_nomination_interval = + Some(self_nomination_interval.parse().map_err(|_| "Invalid self nomination interval format")?); + } + if matches.is_present("enable-auto-self-nomination") { + self.self_nomination_enable = true; + } if matches.is_present("no-miner") { self.author = None; self.engine_signer = None; diff --git a/codechain/config/presets/config.dev.toml b/codechain/config/presets/config.dev.toml index 2b8890b4f7..1d700136d8 100644 --- a/codechain/config/presets/config.dev.toml +++ b/codechain/config/presets/config.dev.toml @@ -15,6 +15,7 @@ reseal_min_period = 0 reseal_max_period = 120000 no_reseal_timer = false work_queue_size = 20 +self_nomination_enable = false allowed_past_gap = 30000 allowed_future_gap = 5000 diff --git a/codechain/config/presets/config.prod.toml b/codechain/config/presets/config.prod.toml index b67e2746bb..dcd415ea82 100644 --- a/codechain/config/presets/config.prod.toml +++ b/codechain/config/presets/config.prod.toml @@ -6,6 +6,7 @@ chain = "mainnet" [mining] mem_pool_mem_limit = 512 # MB mem_pool_size = 524288 +self_nomination_enable = false mem_pool_fee_bump_shift = 3 # 12.5% allow_create_shard = false notify_work = [] diff --git a/codechain/main.rs b/codechain/main.rs index 4c7f6691f8..e372f5027f 100644 --- a/codechain/main.rs +++ b/codechain/main.rs @@ -54,6 +54,7 @@ extern crate primitives; extern crate rpassword; extern crate toml; +mod auto_self_nominate; mod config; mod constants; mod dummy_network_service; diff --git a/codechain/run_node.rs b/codechain/run_node.rs index c6f0e4e4b8..c5f2a32115 100644 --- a/codechain/run_node.rs +++ b/codechain/run_node.rs @@ -14,6 +14,7 @@ // You should have received a copy of the GNU Affero General Public License // along with this program. If not, see . +use crate::auto_self_nominate::AutoSelfNomination; use crate::config::{self, load_config}; use crate::constants::{DEFAULT_DB_PATH, DEFAULT_KEYS_PATH}; use crate::dummy_network_service::DummyNetworkService; @@ -21,8 +22,9 @@ use crate::json::PasswordFile; use crate::rpc::{rpc_http_start, rpc_ipc_start, rpc_ws_start}; use crate::rpc_apis::ApiDependencies; use ccore::{ - AccountProvider, AccountProviderError, BlockId, ChainNotify, Client, ClientConfig, ClientService, EngineClient, - EngineInfo, EngineType, Miner, MinerService, PeerDb, Scheme, Stratum, StratumConfig, StratumError, NUM_COLUMNS, + AccountProvider, AccountProviderError, BlockId, ChainNotify, Client, ClientConfig, ClientService, ConsensusClient, + EngineClient, EngineInfo, EngineType, Miner, MinerService, PeerDb, Scheme, Stratum, StratumConfig, StratumError, + NUM_COLUMNS, }; use cdiscovery::{Config, Discovery}; use ckey::{Address, NetworkId, PlatformAddress}; @@ -69,6 +71,11 @@ fn network_start( Ok(service) } +fn self_nominate_start(c: Arc, matches: &ArgMatches, ap: Arc, address: Address) { + let auto_self_nominate = AutoSelfNomination::new(c, ap, address); + auto_self_nominate.send_self_nominate_transaction(matches); +} + fn discovery_start( service: &NetworkService, cfg: &config::Network, @@ -316,6 +323,12 @@ pub fn run_node(matches: &ArgMatches) -> Result<(), String> { Arc::new(DummyNetworkService::new()) } }; + if config.mining.self_nomination_enable { + let c = client.client(); + let address = miner.get_author_address(); + let accountp = ap.clone(); + self_nominate_start(c, matches, accountp, address); + } let rpc_apis_deps = ApiDependencies { client: client.client(), diff --git a/core/src/consensus/mod.rs b/core/src/consensus/mod.rs index 7adf4d6328..fa9d338402 100644 --- a/core/src/consensus/mod.rs +++ b/core/src/consensus/mod.rs @@ -18,7 +18,7 @@ mod bit_set; mod blake_pow; mod cuckoo; mod null_engine; -mod signer; +pub(crate) mod signer; mod simple_poa; mod solo; pub mod stake; diff --git a/core/src/consensus/stake/mod.rs b/core/src/consensus/stake/mod.rs index ee7601b4ee..4c7a636f06 100644 --- a/core/src/consensus/stake/mod.rs +++ b/core/src/consensus/stake/mod.rs @@ -32,8 +32,8 @@ use std::collections::btree_map::BTreeMap; use std::collections::HashMap; use std::sync::{Arc, Weak}; -pub use self::action_data::{Banned, Validator, Validators}; -use self::action_data::{Candidates, Delegation, IntermediateRewards, Jail, ReleaseResult, StakeAccount, Stakeholders}; +pub use self::action_data::{Banned, Candidates, Jail, Validator, Validators}; +use self::action_data::{Delegation, IntermediateRewards, ReleaseResult, StakeAccount, Stakeholders}; pub use self::actions::Action; pub use self::distribute::fee_distribute; use super::ValidatorSet; diff --git a/core/src/consensus/tendermint/mod.rs b/core/src/consensus/tendermint/mod.rs index 87c6d37b11..bf197086a2 100644 --- a/core/src/consensus/tendermint/mod.rs +++ b/core/src/consensus/tendermint/mod.rs @@ -29,7 +29,7 @@ use self::chain_notify::TendermintChainNotify; pub use self::message::{ConsensusMessage, VoteOn, VoteStep}; pub use self::params::{TendermintParams, TimeGapParams, TimeoutParams}; pub use self::types::{Height, Step, View}; -use super::{stake, ValidatorSet}; +pub use super::{stake, ValidatorSet}; use crate::client::ConsensusClient; use crate::codechain_machine::CodeChainMachine; use crate::ChainNotify; diff --git a/core/src/lib.rs b/core/src/lib.rs index 9e378dca47..76a9eab980 100644 --- a/core/src/lib.rs +++ b/core/src/lib.rs @@ -82,10 +82,11 @@ mod tests; pub use crate::account_provider::{AccountProvider, Error as AccountProviderError}; pub use crate::block::Block; pub use crate::client::{ - AccountData, AssetClient, BlockChainClient, BlockChainTrait, ChainNotify, Client, ClientConfig, DatabaseClient, - EngineClient, EngineInfo, ExecuteClient, ImportBlock, MiningBlockChainClient, Shard, StateInfo, TermInfo, - TestBlockChainClient, TextClient, + AccountData, AssetClient, BlockChainClient, BlockChainTrait, ChainNotify, Client, ClientConfig, ConsensusClient, + DatabaseClient, EngineClient, EngineInfo, ExecuteClient, ImportBlock, MiningBlockChainClient, Shard, StateInfo, + TermInfo, TestBlockChainClient, TextClient, }; +pub use crate::consensus::stake; pub use crate::consensus::{EngineType, TimeGapParams}; pub use crate::db::{COL_STATE, NUM_COLUMNS}; pub use crate::error::{BlockImportError, Error, ImportError}; diff --git a/core/src/miner/miner.rs b/core/src/miner/miner.rs index cc865d20b8..ac3b2976a9 100644 --- a/core/src/miner/miner.rs +++ b/core/src/miner/miner.rs @@ -854,6 +854,10 @@ impl MinerService for Miner { } } + fn get_author_address(&self) -> Address { + self.params.get().author + } + fn set_extra_data(&self, extra_data: Bytes) { self.params.apply(|params| params.extra_data = extra_data); } diff --git a/core/src/miner/mod.rs b/core/src/miner/mod.rs index 10d37fa3eb..339abeb92e 100644 --- a/core/src/miner/mod.rs +++ b/core/src/miner/mod.rs @@ -58,6 +58,9 @@ pub trait MinerService: Send + Sync { /// Set the author that we will seal blocks as. fn set_author(&self, author: Address) -> Result<(), AccountProviderError>; + ///Get the address that sealed the block. + fn get_author_address(&self) -> Address; + /// Set the extra_data that we will seal blocks with. fn set_extra_data(&self, extra_data: Bytes); diff --git a/keystore/src/account/decrypted_account.rs b/keystore/src/account/decrypted_account.rs index d9b4ce08ec..6169da3bd4 100644 --- a/keystore/src/account/decrypted_account.rs +++ b/keystore/src/account/decrypted_account.rs @@ -19,6 +19,7 @@ use ckey::{ }; /// An opaque wrapper for secret. +#[derive(Clone)] pub struct DecryptedAccount { secret: Secret, } diff --git a/test/src/config/mem-pool-min-fee1.toml b/test/src/config/mem-pool-min-fee1.toml index 7211ead60e..8b567b86d7 100644 --- a/test/src/config/mem-pool-min-fee1.toml +++ b/test/src/config/mem-pool-min-fee1.toml @@ -2,6 +2,7 @@ [mining] min_pay_transaction_cost = 150 +self_nomination_enable = false [network] diff --git a/test/src/config/mem-pool-min-fee2.toml b/test/src/config/mem-pool-min-fee2.toml index f7dab7f1f3..21abdf674d 100644 --- a/test/src/config/mem-pool-min-fee2.toml +++ b/test/src/config/mem-pool-min-fee2.toml @@ -2,6 +2,7 @@ [mining] min_pay_transaction_cost = 200 +self_nomination_enable = false [network] diff --git a/test/src/e2e.dynval/2/selfnomination.test.ts b/test/src/e2e.dynval/2/selfnomination.test.ts new file mode 100644 index 0000000000..d9da990d48 --- /dev/null +++ b/test/src/e2e.dynval/2/selfnomination.test.ts @@ -0,0 +1,125 @@ +// Copyright 2020 Kodebox, Inc. +// This file is part of CodeChain. +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU Affero General Public License as +// published by the Free Software Foundation, either version 3 of the +// License, or (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU Affero General Public License for more details. +// +// You should have received a copy of the GNU Affero General Public License +// along with this program. If not, see . + +import { expect } from "chai"; +import { H512 } from "codechain-primitives/lib"; +import * as stake from "codechain-stakeholder-sdk"; +import "mocha"; + +import { validators } from "../../../tendermint.dynval/constants"; +import { PromiseExpect } from "../../helper/promise"; +import { + findNode, + selfNominate, + setTermTestTimeout, + withNodes +} from "../setup"; + +describe("Auto Self Nomination", function() { + const promiseExpect = new PromiseExpect(); + const NOMINATION_EXPIRATION = 2; + const TERM_SECOND = 30; + + describe("Alice doesn't self nominate in NOMINATION_EXPIRATION, Bob sends auto self nomination", async function() { + const initialValidators = validators.slice(0, 3); + const alice = validators[3]; + const bob = validators[4]; + const { nodes } = withNodes(this, { + promiseExpect, + overrideParams: { + termSeconds: TERM_SECOND, + nominationExpiration: NOMINATION_EXPIRATION + }, + validators: [ + ...initialValidators.map((validator, index) => ({ + signer: validator, + delegation: 5000 - index, + deposit: 100000 + })), + { signer: alice, autoSelfNominate: false }, + { signer: bob, autoSelfNominate: true } + ] + }); + it("Alice be eligible after 2 terms and Bob did auto self nomination", async function() { + const termWaiter = setTermTestTimeout(this, { + terms: 3, + params: { + termSeconds: TERM_SECOND + } + }); + + const aliceNode = findNode(nodes, alice); + const bobNode = findNode(nodes, bob); + const selfNominationHash = await selfNominate( + aliceNode.sdk, + alice, + 10 + ); + const bobselfNomination = await selfNominate(bobNode.sdk, bob, 10); + await aliceNode.waitForTx(selfNominationHash); + await bobNode.waitForTx(bobselfNomination); + + const beforeCandidates = await stake.getCandidates(nodes[0].sdk); + + expect( + beforeCandidates.map(candidate => candidate.pubkey.toString()) + ).to.includes(H512.ensure(alice.publicKey).toString()); + expect( + beforeCandidates.map(candidate => candidate.pubkey.toString()) + ).to.includes(H512.ensure(bob.publicKey).toString()); + + await termWaiter.waitNodeUntilTerm(nodes[0], { + target: 4, + termPeriods: 3 + }); + + const [ + currentValidators, + banned, + candidates, + jailed + ] = await Promise.all([ + stake.getValidators(nodes[0].sdk), + stake.getBanned(nodes[0].sdk), + stake.getCandidates(nodes[0].sdk), + stake.getJailed(nodes[0].sdk) + ]); + + expect( + currentValidators.map(validator => validator.pubkey.toString()) + ).not.to.includes(alice.publicKey); + expect( + banned.map(ban => ban.getAccountId().toString()) + ).not.to.includes(alice.accountId); + expect( + candidates.map(candidate => candidate.pubkey.toString()) + ).not.to.includes(alice.publicKey); + expect(jailed.map(jail => jail.address)).not.to.includes( + alice.platformAddress.toString() + ); + expect( + currentValidators.map(validator => validator.pubkey.toString()) + ).not.to.includes(bob.publicKey); + expect( + candidates.map(candidate => candidate.pubkey.toString()) + ).to.includes(bob.publicKey); + }); + }); + + afterEach(function() { + promiseExpect.checkFulfilled(); + }); +}); diff --git a/test/src/e2e.dynval/setup.ts b/test/src/e2e.dynval/setup.ts index 493f6ef602..84ae2cd0a1 100644 --- a/test/src/e2e.dynval/setup.ts +++ b/test/src/e2e.dynval/setup.ts @@ -37,6 +37,7 @@ interface ValidatorConfig { signer: Signer; deposit?: U64Value; delegation?: U64Value; + autoSelfNominate?: boolean; } export function withNodes( @@ -127,15 +128,29 @@ async function createNodes(options: { const nodes: CodeChain[] = []; for (let i = 0; i < validators.length; i++) { const { signer: validator } = validators[i]; + const argv = [ + "--engine-signer", + validator.platformAddress.value, + "--password-path", + `test/tendermint.dynval/${validator.platformAddress.value}/password.json`, + "--force-sealing" + ]; + + if (validators[i].autoSelfNominate) { + argv.push( + "--enable-auto-self-nomination", + "--self-nomination-metadata", + "", + "--self-nomination-target-deposit", + "10", + "--self-nomination-interval", + "10" + ); + } + nodes[i] = new CodeChain({ chain, - argv: [ - "--engine-signer", - validator.platformAddress.value, - "--password-path", - `test/tendermint.dynval/${validator.platformAddress.value}/password.json`, - "--force-sealing" - ], + argv, additionalKeysPath: `tendermint.dynval/${validator.platformAddress.value}/keys` }); nodes[i].signer = validator; From 86b3c9b909d2ed2249e1c226e5546efad40c7c7e Mon Sep 17 00:00:00 2001 From: MSNTCS Date: Mon, 20 Jan 2020 17:47:49 +0900 Subject: [PATCH 02/55] Change some functions due to the clippy restrictions Implementing the auto self-nomination thread led to some clippy problems which we had to change some part of `consensus/stake`. --- core/src/consensus/stake/action_data.rs | 6 ++++++ core/src/consensus/stake/distribute.rs | 5 ++++- network/src/p2p/handler.rs | 8 ++++---- 3 files changed, 14 insertions(+), 5 deletions(-) diff --git a/core/src/consensus/stake/action_data.rs b/core/src/consensus/stake/action_data.rs index 170774b541..d798f0fe49 100644 --- a/core/src/consensus/stake/action_data.rs +++ b/core/src/consensus/stake/action_data.rs @@ -510,6 +510,9 @@ impl Candidates { pub fn len(&self) -> usize { self.0.len() } + pub fn is_empty(&self) -> bool { + self.0.len() == 0 + } #[cfg(test)] pub fn get_index(&self, account: &Address) -> Option { @@ -628,6 +631,9 @@ impl Jail { pub fn len(&self) -> usize { self.0.len() } + pub fn is_empty(&self) -> bool { + self.0.len() == 0 + } pub fn add(&mut self, candidate: Candidate, custody_until: u64, released_at: u64) { assert!(custody_until <= released_at); diff --git a/core/src/consensus/stake/distribute.rs b/core/src/consensus/stake/distribute.rs index 1c5dd55ea0..d76d13bac6 100644 --- a/core/src/consensus/stake/distribute.rs +++ b/core/src/consensus/stake/distribute.rs @@ -19,7 +19,10 @@ use std::collections::hash_map; use std::collections::HashMap; use std::convert::TryFrom; -pub fn fee_distribute(total_min_fee: u64, stakes: &HashMap) -> FeeDistributeIter { +pub fn fee_distribute( + total_min_fee: u64, + stakes: &HashMap, +) -> FeeDistributeIter { FeeDistributeIter { total_stakes: stakes.values().sum(), total_min_fee, diff --git a/network/src/p2p/handler.rs b/network/src/p2p/handler.rs index 4a1498ff16..025725e804 100644 --- a/network/src/p2p/handler.rs +++ b/network/src/p2p/handler.rs @@ -242,7 +242,7 @@ impl Handler { let mut result = HashMap::with_capacity(network_usage_in_10_seconds.len()); let now = Instant::now(); for (name, times) in &mut *network_usage_in_10_seconds { - remove_outdated_network_usage(times, &now); + remove_outdated_network_usage(times, now); let total = times.iter().map(|(_, usage)| usage).sum(); if total != 0 { result.insert(name.clone(), total); @@ -1198,9 +1198,9 @@ impl ::std::fmt::Display for Error { } } -fn remove_outdated_network_usage(usage_per_extension: &mut VecDeque<(Instant, usize)>, now: &Instant) { +fn remove_outdated_network_usage(usage_per_extension: &mut VecDeque<(Instant, usize)>, now: Instant) { while let Some((time, size)) = usage_per_extension.pop_front() { - if *now < time { + if now < time { usage_per_extension.push_front((time, size)); break } @@ -1209,6 +1209,6 @@ fn remove_outdated_network_usage(usage_per_extension: &mut VecDeque<(Instant, us fn insert_network_usage(usage_per_extension: &mut VecDeque<(Instant, usize)>, network_message_size: usize) { let now = Instant::now(); - remove_outdated_network_usage(usage_per_extension, &now); + remove_outdated_network_usage(usage_per_extension, now); usage_per_extension.push_back((now + Duration::from_secs(10), network_message_size)); } From caf1198c8c0155d3d237097771879b94fadfddfe Mon Sep 17 00:00:00 2001 From: Seulgi Kim Date: Sun, 26 Jan 2020 22:40:55 +0900 Subject: [PATCH 03/55] Refactor BodyDownloader There are 5 states for block hashes. 1. listed, but no request sent 2. sent the request 3. received the response 4. drained from the list 5. imported on the chain Currently, these states are implicit with the combination of targets, downloading, and downloaded fields. This patch merges downloading and downloaded fields, and make the states explicit. --- sync/src/block/downloader/body.rs | 133 +++++++++++++++++------------- sync/src/block/extension.rs | 20 +++-- 2 files changed, 89 insertions(+), 64 deletions(-) diff --git a/sync/src/block/downloader/body.rs b/sync/src/block/downloader/body.rs index 9a75c45b57..49cf068bad 100644 --- a/sync/src/block/downloader/body.rs +++ b/sync/src/block/downloader/body.rs @@ -17,7 +17,25 @@ use super::super::message::RequestMessage; use ccore::UnverifiedTransaction; use ctypes::{BlockHash, Header}; -use std::collections::{HashMap, HashSet}; +use std::collections::hash_map::Entry; +use std::collections::HashMap; +use std::mem::replace; + +#[derive(Debug, PartialEq)] +enum State { + Queued, + Downloading, + Downloaded { + transactions: Vec, + }, + Drained, +} + +impl Default for State { + fn default() -> Self { + State::Queued + } +} #[derive(Clone)] struct Target { @@ -28,8 +46,7 @@ struct Target { #[derive(Default)] pub struct BodyDownloader { targets: Vec, - downloading: HashSet, - downloaded: HashMap>, + states: HashMap, } impl BodyDownloader { @@ -37,9 +54,12 @@ impl BodyDownloader { const MAX_BODY_REQEUST_LENGTH: usize = 128; let mut hashes = Vec::new(); for t in &self.targets { - if !self.downloading.contains(&t.hash) && !self.downloaded.contains_key(&t.hash) { - hashes.push(t.hash); + let state = self.states.entry(t.hash).or_default(); + if *state != State::Queued { + continue } + *state = State::Downloading; + hashes.push(t.hash); if hashes.len() >= MAX_BODY_REQEUST_LENGTH { break } @@ -47,97 +67,96 @@ impl BodyDownloader { if hashes.is_empty() { None } else { - self.downloading.extend(&hashes); Some(RequestMessage::Bodies(hashes)) } } pub fn import_bodies(&mut self, hashes: Vec, bodies: Vec>) { - for (hash, body) in hashes.into_iter().zip(bodies) { - if self.downloading.remove(&hash) { - let target = self.targets.iter().find(|t| t.hash == hash).expect("Downloading target must exist"); - if body.is_empty() { - if !target.is_empty { - cwarn!(SYNC, "Invalid body of {}. It should be not empty.", hash); - continue - } - } else if target.is_empty { - cwarn!(SYNC, "Invalid body of {}. It should be empty.", hash); + assert_eq!(hashes.len(), bodies.len()); + for (hash, transactions) in hashes.into_iter().zip(bodies) { + if let Some(state) = self.states.get_mut(&hash) { + if state != &State::Downloading { continue } - self.downloaded.insert(hash, body); + *state = State::Downloaded { + transactions, + } } } - self.downloading.shrink_to_fit(); } pub fn add_target(&mut self, header: &Header, is_empty: bool) { cdebug!(SYNC, "Add download target: {}", header.hash()); + self.states.insert(header.hash(), State::Queued); self.targets.push(Target { hash: header.hash(), is_empty, }); } - pub fn remove_target(&mut self, targets: &[BlockHash]) { + pub fn remove_targets(&mut self, targets: &[BlockHash]) { if targets.is_empty() { return } cdebug!(SYNC, "Remove download targets: {:?}", targets); - for hash in targets { - if let Some(index) = self.targets.iter().position(|t| t.hash == *hash) { - self.targets.remove(index); - } - self.downloading.remove(hash); - self.downloaded.remove(hash); - } + // XXX: It can be slow. + self.states.retain(|hash, _| !targets.contains(hash)); + self.targets.retain(|target| !targets.contains(&target.hash)); + self.states.shrink_to_fit(); self.targets.shrink_to_fit(); - self.downloading.shrink_to_fit(); - self.downloaded.shrink_to_fit(); } pub fn reset_downloading(&mut self, hashes: &[BlockHash]) { cdebug!(SYNC, "Remove downloading by timeout {:?}", hashes); for hash in hashes { - self.downloading.remove(&hash); + if let Some(state) = self.states.get_mut(hash) { + if *state == State::Downloading { + *state = State::Queued; + } + } } - self.downloading.shrink_to_fit(); } pub fn drain(&mut self) -> Vec<(BlockHash, Vec)> { let mut result = Vec::new(); for t in &self.targets { - if let Some(body) = self.downloaded.remove(&t.hash) { - result.push((t.hash, body)); - } else { - break + let entry = self.states.entry(t.hash); + let state = match entry { + Entry::Vacant(_) => unreachable!(), + Entry::Occupied(mut entry) => match entry.get_mut() { + state @ State::Downloaded { + .. + } => replace(state, State::Drained), + _ => break, + }, + }; + match state { + State::Downloaded { + transactions, + } => { + result.push((t.hash, transactions)); + } + _ => unreachable!(), } } - self.downloaded.shrink_to_fit(); - self.targets.drain(0..result.len()); - self.targets.shrink_to_fit(); result } - pub fn re_request( - &mut self, - hash: BlockHash, - is_empty: bool, - remains: Vec<(BlockHash, Vec)>, - ) { - let mut new_targets = vec![Target { - hash, - is_empty, - }]; - new_targets.extend(remains.into_iter().map(|(hash, transactions)| { - let is_empty = transactions.is_empty(); - self.downloaded.insert(hash, transactions); - Target { - hash, - is_empty, - } - })); - new_targets.append(&mut self.targets); - self.targets = new_targets; + pub fn re_request(&mut self, hash: BlockHash, remains: Vec<(BlockHash, Vec)>) { + #[inline] + fn insert(states: &mut HashMap, hash: BlockHash, state: State) { + let old = states.insert(hash, state); + debug_assert_ne!(None, old); + } + // The implementation of extend method allocates an additional memory for new items. + // However, our implementation guarantees that new items are already in the map and it just + // update the states. So iterating over new items and calling the insert method is faster + // than using the extend method and uses less memory. + for (hash, transactions) in remains { + insert(&mut self.states, hash, State::Downloaded { + transactions, + }); + } + insert(&mut self.states, hash, State::Queued); } } diff --git a/sync/src/block/extension.rs b/sync/src/block/extension.rs index 751e992d60..ddd97865f5 100644 --- a/sync/src/block/extension.rs +++ b/sync/src/block/extension.rs @@ -391,6 +391,7 @@ impl Extension { peer.mark_as_imported(imported.clone()); } } + let mut headers_to_download: Vec<_> = enacted .into_iter() .map(|hash| self.client.block_header(&BlockId::Hash(hash)).expect("Enacted header must exist")) @@ -404,6 +405,7 @@ impl Extension { .into_iter() .filter(|header| self.client.block_body(&BlockId::Hash(header.hash())).is_none()) .collect(); // FIXME: No need to collect here if self is not borrowed. + for header in headers { let parent = self .client @@ -412,12 +414,12 @@ impl Extension { let is_empty = header.transactions_root() == parent.transactions_root(); self.body_downloader.add_target(&header.decode(), is_empty); } - self.body_downloader.remove_target(&retracted); + self.body_downloader.remove_targets(&retracted); } fn new_blocks(&mut self, imported: Vec, invalid: Vec) { - self.body_downloader.remove_target(&imported); - self.body_downloader.remove_target(&invalid); + self.body_downloader.remove_targets(&imported); + self.body_downloader.remove_targets(&invalid); let chain_info = self.client.chain_info(); @@ -708,6 +710,7 @@ impl Extension { } fn import_blocks(&mut self, blocks: Vec<(BlockHash, Vec)>) { + let mut imported = Vec::new(); let mut remains = Vec::new(); let mut error_target = None; for (hash, transactions) in blocks { @@ -727,7 +730,7 @@ impl Extension { skewed_merkle_root(parent_transactions_root, transactions.iter().map(Encodable::rlp_bytes)); if *header.transactions_root() != calculated_transactions_root { cwarn!(SYNC, "Received corrupted body for ${}({}", header.number(), hash); - error_target = Some((hash, transactions.is_empty())); + error_target = Some(hash); continue } @@ -748,12 +751,15 @@ impl Extension { cwarn!(SYNC, "Cannot import block({}): {:?}", hash, err); break } - Ok(_) => {} + Ok(_) => { + imported.push(hash); + } } } - if let Some((hash, is_empty)) = error_target { - self.body_downloader.re_request(hash, is_empty, remains); + if let Some(hash) = error_target { + self.body_downloader.re_request(hash, remains); } + self.body_downloader.remove_targets(&imported); } fn on_body_response(&mut self, hashes: Vec, bodies: Vec>) { From c49804abe6c90f1fe5fea8554753667c7518f0b7 Mon Sep 17 00:00:00 2001 From: Byeongjee Kang Date: Tue, 28 Jan 2020 14:50:15 +0900 Subject: [PATCH 04/55] Add RPCs for checking peer best blocks & target blocks --- rpc/src/v1/impls/devel.rs | 24 +++++++++- rpc/src/v1/traits/devel.rs | 9 +++- spec/JSON-RPC.md | 73 ++++++++++++++++++++++++++++- sync/src/block/downloader/body.rs | 6 ++- sync/src/block/downloader/header.rs | 4 ++ sync/src/block/extension.rs | 15 +++++- 6 files changed, 125 insertions(+), 6 deletions(-) diff --git a/rpc/src/v1/impls/devel.rs b/rpc/src/v1/impls/devel.rs index fb39ecf846..8231b5cd63 100644 --- a/rpc/src/v1/impls/devel.rs +++ b/rpc/src/v1/impls/devel.rs @@ -1,4 +1,4 @@ -// Copyright 2018-2019 Kodebox, Inc. +// Copyright 2018-2020 Kodebox, Inc. // This file is part of CodeChain. // // This program is free software: you can redistribute it and/or modify @@ -29,7 +29,7 @@ use csync::BlockSyncEvent; use ctypes::transaction::{ Action, AssetMintOutput, AssetOutPoint, AssetTransferInput, AssetTransferOutput, Transaction, }; -use ctypes::{Tracker, TxHash}; +use ctypes::{BlockHash, Tracker, TxHash}; use jsonrpc_core::Result; use kvdb::KeyValueDB; use primitives::{H160, H256}; @@ -106,6 +106,26 @@ where } } + fn get_peer_best_block_hashes(&self) -> Result> { + if let Some(block_sync) = self.block_sync.as_ref() { + let (sender, receiver) = unbounded_event_callback(); + block_sync.send(BlockSyncEvent::GetPeerBestBlockHashes(sender)).unwrap(); + Ok(receiver.iter().collect()) + } else { + Ok(Vec::new()) + } + } + + fn get_target_block_hashes(&self) -> Result> { + if let Some(block_sync) = self.block_sync.as_ref() { + let (sender, receiver) = unbounded_event_callback(); + block_sync.send(BlockSyncEvent::GetTargetBlockHashes(sender)).unwrap(); + Ok(receiver.iter().collect()) + } else { + Ok(Vec::new()) + } + } + fn test_tps(&self, setting: TPSTestSetting) -> Result { let common_params = self.client.common_params(BlockId::Latest).unwrap(); let mint_fee = common_params.min_asset_mint_cost(); diff --git a/rpc/src/v1/traits/devel.rs b/rpc/src/v1/traits/devel.rs index 351c1ab096..8ea0f735f0 100644 --- a/rpc/src/v1/traits/devel.rs +++ b/rpc/src/v1/traits/devel.rs @@ -1,4 +1,4 @@ -// Copyright 2018 Kodebox, Inc. +// Copyright 2018-2020 Kodebox, Inc. // This file is part of CodeChain. // // This program is free software: you can redistribute it and/or modify @@ -16,6 +16,7 @@ use super::super::types::TPSTestSetting; use cjson::bytes::Bytes; +use ctypes::BlockHash; use jsonrpc_core::Result; use primitives::H256; use std::net::SocketAddr; @@ -37,6 +38,12 @@ pub trait Devel { #[rpc(name = "devel_getBlockSyncPeers")] fn get_block_sync_peers(&self) -> Result>; + #[rpc(name = "devel_getPeerBestBlockHashes")] + fn get_peer_best_block_hashes(&self) -> Result>; + + #[rpc(name = "devel_getTargetBlockHashes")] + fn get_target_block_hashes(&self) -> Result>; + #[rpc(name = "devel_testTPS")] fn test_tps(&self, setting: TPSTestSetting) -> Result; } diff --git a/spec/JSON-RPC.md b/spec/JSON-RPC.md index 486a0cdb0b..92e6130d9a 100644 --- a/spec/JSON-RPC.md +++ b/spec/JSON-RPC.md @@ -370,7 +370,8 @@ When `Transaction` is included in any response, there will be an additional fiel * [devel_startSealing](#devel_startsealing) * [devel_stopSealing](#devel_stopsealing) * [devel_getBlockSyncPeers](#devel_getblocksyncpeers) - + * [devel_getPeerBestBlockHashes](#devel_getpeerbestblockhases) + * [devel_getTargetBlockHashes](#devel_gettargetblockhashes) # Specification @@ -3093,6 +3094,76 @@ No parameters [Back to **List of methods**](#list-of-methods) +## devel_getPeerBestBlockHashes + +Get IP address and best block hash of each peer. + +### Params + +No parameters + +### Returns + +[ 'string', 'H256' ][] + +### Request Example + +``` + curl \ + -H 'Content-Type: application/json' \ + -d '{"jsonrpc": "2.0", "method": "devel_getPeerBestBlockHashes", "params": [], "id": 3}' \ + localhost:8080 +``` + +### Response Example +``` +{ + "jsonrpc":"2.0", + "result": [ + ["1.2.3.4:3485", "0x56642f04d519ae3262c7ba6facf1c5b11450ebaeb7955337cfbc45420d573077"], + ["1.2.3.5:3485", "0x7f7104b580f9418d444560009e5a92a4573d42d2c51cd0c6045afdc761826249"] + ], + "id":3 +} +``` + +[Back to **List of methods**](#list-of-methods) + +## devel_getTargetBlockHashes + +Get hashes of target blocks + +### Params + +No parameters + +### Returns + +'`H256[]` + +### Request Example + +``` + curl \ + -H 'Content-Type: application/json' \ + -d '{"jsonrpc": "2.0", "method": "devel_getTargetBlockHashes", "params": [], "id": 3}' \ + localhost:8080 +``` + +### Response Example +``` +{ + "jsonrpc":"2.0", + "result": [ + "0x56642f04d519ae3262c7ba6facf1c5b11450ebaeb7955337cfbc45420d573077", + "0x7f7104b580f9418d444560009e5a92a4573d42d2c51cd0c6045afdc761826249" + ], + "id":3 +} +``` + +[Back to **List of methods**](#list-of-methods) + ## devel_testTPS Test TPS as the parameters. diff --git a/sync/src/block/downloader/body.rs b/sync/src/block/downloader/body.rs index 49cf068bad..bdd32cbe86 100644 --- a/sync/src/block/downloader/body.rs +++ b/sync/src/block/downloader/body.rs @@ -1,4 +1,4 @@ -// Copyright 2018-2019 Kodebox, Inc. +// Copyright 2018-2020 Kodebox, Inc. // This file is part of CodeChain. // // This program is free software: you can redistribute it and/or modify @@ -85,6 +85,10 @@ impl BodyDownloader { } } + pub fn get_target_hashes(&self) -> Vec { + self.targets.iter().map(|t| t.hash).collect() + } + pub fn add_target(&mut self, header: &Header, is_empty: bool) { cdebug!(SYNC, "Add download target: {}", header.hash()); self.states.insert(header.hash(), State::Queued); diff --git a/sync/src/block/downloader/header.rs b/sync/src/block/downloader/header.rs index fff1bfe56e..29d49b7ead 100644 --- a/sync/src/block/downloader/header.rs +++ b/sync/src/block/downloader/header.rs @@ -119,6 +119,10 @@ impl HeaderDownloader { self.pivot.total_score } + pub fn best_hash(&self) -> BlockHash { + self.best_hash + } + pub fn is_idle(&self) -> bool { let can_request = self.request_time.is_none() && self.total_score > self.pivot.total_score; diff --git a/sync/src/block/extension.rs b/sync/src/block/extension.rs index ddd97865f5..4be801d614 100644 --- a/sync/src/block/extension.rs +++ b/sync/src/block/extension.rs @@ -21,7 +21,7 @@ use ccore::{ Block, BlockChainClient, BlockChainTrait, BlockId, BlockImportError, ChainNotify, Client, ImportBlock, ImportError, UnverifiedTransaction, }; -use cnetwork::{Api, EventSender, NetworkExtension, NodeId}; +use cnetwork::{Api, EventSender, IntoSocketAddr, NetworkExtension, NodeId}; use cstate::FindActionHandler; use ctimer::TimerToken; use ctypes::header::{Header, Seal}; @@ -34,6 +34,7 @@ use rand::thread_rng; use rlp::{Encodable, Rlp}; use std::collections::hash_map::Entry; use std::collections::{HashMap, HashSet}; +use std::net::SocketAddr; use std::sync::Arc; use std::time::Duration; use token_generator::TokenGenerator; @@ -353,6 +354,16 @@ impl NetworkExtension for Extension { channel.send(*peer).unwrap(); } } + Event::GetPeerBestBlockHashes(channel) => { + for (node_id, header_downloader) in self.header_downloaders.iter() { + channel.send((SocketAddr::from(node_id.into_addr()), header_downloader.best_hash())).unwrap(); + } + } + Event::GetTargetBlockHashes(channel) => { + for target in self.body_downloader.get_target_hashes() { + channel.send(target).unwrap(); + } + } Event::NewHeaders { imported, enacted, @@ -372,6 +383,8 @@ impl NetworkExtension for Extension { pub enum Event { GetPeers(EventSender), + GetPeerBestBlockHashes(EventSender<(SocketAddr, BlockHash)>), + GetTargetBlockHashes(EventSender), NewHeaders { imported: Vec, enacted: Vec, From 56550b4bac1f6adcbe2695274a1061f5424d86a8 Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Wed, 29 Jan 2020 10:50:18 +0900 Subject: [PATCH 05/55] Use proper NEED_NOMINATION_UNDER_TERM_LEFT value CodeChain should send a self-nomination transaction before too late --- codechain/auto_self_nominate.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/codechain/auto_self_nominate.rs b/codechain/auto_self_nominate.rs index dc0598e1d0..3e829c8d75 100644 --- a/codechain/auto_self_nominate.rs +++ b/codechain/auto_self_nominate.rs @@ -31,7 +31,7 @@ use std::sync::Arc; use std::thread; use std::time::Duration; -const NEED_NOMINATION_UNDER_TERM_LEFT: u64 = 1; +const NEED_NOMINATION_UNDER_TERM_LEFT: u64 = 3; #[derive(Clone)] struct SelfSigner { account_provider: Arc, From 0bcd5dee25aa278e39f4ddc42430cef388e477e8 Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Wed, 29 Jan 2020 11:15:35 +0900 Subject: [PATCH 06/55] Fix the wrong condition in the auto_self_nominate.rs file CodeChain should send a self-nomination transaction before the nomination ends. --- codechain/auto_self_nominate.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/codechain/auto_self_nominate.rs b/codechain/auto_self_nominate.rs index 3e829c8d75..4cc73f7c84 100644 --- a/codechain/auto_self_nominate.rs +++ b/codechain/auto_self_nominate.rs @@ -134,7 +134,7 @@ impl AutoSelfNomination { let candidate = Candidates::load_from_state(&state).unwrap(); if candidate.get_candidate(&address).is_some() { let candidate_need_nomination = candidate.get_candidate(&address).unwrap(); - if candidate_need_nomination.nomination_ends_at <= current_term + NEED_NOMINATION_UNDER_TERM_LEFT { + if candidate_need_nomination.nomination_ends_at + NEED_NOMINATION_UNDER_TERM_LEFT <= current_term { cdebug!(ENGINE, "No need self nominate"); return } From dd4f69fee132aee6b8e2d04bd45cdf59fc540644 Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Wed, 29 Jan 2020 11:17:38 +0900 Subject: [PATCH 07/55] Add more log in the auto_self_nominate file --- codechain/auto_self_nominate.rs | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) diff --git a/codechain/auto_self_nominate.rs b/codechain/auto_self_nominate.rs index 4cc73f7c84..58a4887cd9 100644 --- a/codechain/auto_self_nominate.rs +++ b/codechain/auto_self_nominate.rs @@ -135,7 +135,12 @@ impl AutoSelfNomination { if candidate.get_candidate(&address).is_some() { let candidate_need_nomination = candidate.get_candidate(&address).unwrap(); if candidate_need_nomination.nomination_ends_at + NEED_NOMINATION_UNDER_TERM_LEFT <= current_term { - cdebug!(ENGINE, "No need self nominate"); + cdebug!( + ENGINE, + "No need self nominate. nomination_ends_at: {}, current_term: {}", + candidate_need_nomination.nomination_ends_at, + current_term + ); return } if candidate_need_nomination.deposit.lt(&targetdep) { @@ -187,7 +192,9 @@ impl AutoSelfNomination { let signed = SignedTransaction::try_new(unverified).expect("secret is valid so it's recoverable"); match client.queue_own_transaction(signed) { - Ok(_) => {} + Ok(_) => { + cinfo!(ENGINE, "Send self nominate transaction"); + } Err(e) => { cerror!(ENGINE, "Failed to queue self nominate transaction: {}", e); } From b2cbc3d7cc137596383d19371022981fe51d0a4f Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Wed, 29 Jan 2020 11:09:00 +0900 Subject: [PATCH 08/55] Fix the selfnomination.test.ts Since the bob is using the auto-self-nomination, we don't need to send the self-nomination transaction manually in the test. Occasionally, the test failed because of the seq conflict with auto-selfnomination and the manual transaction. --- test/src/e2e.dynval/2/selfnomination.test.ts | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/test/src/e2e.dynval/2/selfnomination.test.ts b/test/src/e2e.dynval/2/selfnomination.test.ts index d9da990d48..7b3af2f0d7 100644 --- a/test/src/e2e.dynval/2/selfnomination.test.ts +++ b/test/src/e2e.dynval/2/selfnomination.test.ts @@ -62,16 +62,13 @@ describe("Auto Self Nomination", function() { }); const aliceNode = findNode(nodes, alice); - const bobNode = findNode(nodes, bob); const selfNominationHash = await selfNominate( aliceNode.sdk, alice, 10 ); - const bobselfNomination = await selfNominate(bobNode.sdk, bob, 10); await aliceNode.waitForTx(selfNominationHash); - await bobNode.waitForTx(bobselfNomination); - + // bob will send self-nomination transaction automatically. const beforeCandidates = await stake.getCandidates(nodes[0].sdk); expect( From 2bc8d938e8ac3066cd09db35c03754687aed457b Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Wed, 29 Jan 2020 11:10:16 +0900 Subject: [PATCH 09/55] Use auto-self-nomination-interval as 1 second 10ms was too short. --- test/src/e2e.dynval/setup.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/src/e2e.dynval/setup.ts b/test/src/e2e.dynval/setup.ts index 84ae2cd0a1..58217433c6 100644 --- a/test/src/e2e.dynval/setup.ts +++ b/test/src/e2e.dynval/setup.ts @@ -144,7 +144,7 @@ async function createNodes(options: { "--self-nomination-target-deposit", "10", "--self-nomination-interval", - "10" + "1000" ); } From 953b57c0ff3a18e7105a3096793ff02673ecd670 Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Wed, 29 Jan 2020 11:23:05 +0900 Subject: [PATCH 10/55] Rename selfnomination.test.ts to autoselfnomination.test.ts The purpose of the test is testing auto-self-nomination. --- .../2/{selfnomination.test.ts => autoselfnomination.test.ts} | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename test/src/e2e.dynval/2/{selfnomination.test.ts => autoselfnomination.test.ts} (100%) diff --git a/test/src/e2e.dynval/2/selfnomination.test.ts b/test/src/e2e.dynval/2/autoselfnomination.test.ts similarity index 100% rename from test/src/e2e.dynval/2/selfnomination.test.ts rename to test/src/e2e.dynval/2/autoselfnomination.test.ts From a86d20ed672aac2b3dbee4f36f9afa034fe12be2 Mon Sep 17 00:00:00 2001 From: Byeongjee Kang Date: Mon, 3 Feb 2020 13:28:56 +0900 Subject: [PATCH 11/55] Rename MemPoolFees into MemPoolMinFees --- codechain/config/mod.rs | 6 +++--- core/src/lib.rs | 2 +- core/src/miner/mem_pool.rs | 12 ++++++------ core/src/miner/mem_pool_types.rs | 6 +++--- core/src/miner/miner.rs | 8 ++++---- core/src/miner/mod.rs | 2 +- 6 files changed, 18 insertions(+), 18 deletions(-) diff --git a/codechain/config/mod.rs b/codechain/config/mod.rs index 1a3fbc39a2..b11977f93e 100644 --- a/codechain/config/mod.rs +++ b/codechain/config/mod.rs @@ -16,7 +16,7 @@ mod chain_type; -use ccore::{MemPoolFees, MinerOptions, StratumConfig, TimeGapParams}; +use ccore::{MemPoolMinFees, MinerOptions, StratumConfig, TimeGapParams}; use cidr::IpCidr; use ckey::PlatformAddress; use clap; @@ -74,7 +74,7 @@ impl Config { None => unreachable!(), }; - let mem_pool_fees = MemPoolFees::create_from_options( + let mem_pool_min_fees = MemPoolMinFees::create_from_options( self.mining.min_pay_transaction_cost, self.mining.min_set_regular_key_transaction_cost, self.mining.min_create_shard_transaction_cost, @@ -107,7 +107,7 @@ impl Config { reseal_max_period: Duration::from_millis(self.mining.reseal_max_period.unwrap()), no_reseal_timer: self.mining.no_reseal_timer.unwrap(), work_queue_size: self.mining.work_queue_size.unwrap(), - mem_pool_fees, + mem_pool_min_fees, }) } diff --git a/core/src/lib.rs b/core/src/lib.rs index 76a9eab980..f748b5d7df 100644 --- a/core/src/lib.rs +++ b/core/src/lib.rs @@ -90,7 +90,7 @@ pub use crate::consensus::stake; pub use crate::consensus::{EngineType, TimeGapParams}; pub use crate::db::{COL_STATE, NUM_COLUMNS}; pub use crate::error::{BlockImportError, Error, ImportError}; -pub use crate::miner::{MemPoolFees, Miner, MinerOptions, MinerService, Stratum, StratumConfig, StratumError}; +pub use crate::miner::{MemPoolMinFees, Miner, MinerOptions, MinerService, Stratum, StratumConfig, StratumError}; pub use crate::peer_db::PeerDb; pub use crate::scheme::Scheme; pub use crate::service::ClientService; diff --git a/core/src/miner/mem_pool.rs b/core/src/miner/mem_pool.rs index c7aca0cb99..329f26094b 100644 --- a/core/src/miner/mem_pool.rs +++ b/core/src/miner/mem_pool.rs @@ -16,8 +16,8 @@ use super::backup; use super::mem_pool_types::{ - AccountDetails, CurrentQueue, FutureQueue, MemPoolFees, MemPoolInput, MemPoolItem, MemPoolStatus, PoolingInstant, - QueueTag, TransactionOrder, TransactionOrderWithTag, TxOrigin, TxTimelock, + AccountDetails, CurrentQueue, FutureQueue, MemPoolInput, MemPoolItem, MemPoolMinFees, MemPoolStatus, + PoolingInstant, QueueTag, TransactionOrder, TransactionOrderWithTag, TxOrigin, TxTimelock, }; use super::TransactionImportResult; use crate::client::{AccountData, BlockChainTrait}; @@ -74,7 +74,7 @@ impl From for Error { pub struct MemPool { /// Fee threshold for transactions that can be imported to this pool - minimum_fees: MemPoolFees, + minimum_fees: MemPoolMinFees, /// A value which is used to check whether a new transaciton can replace a transaction in the memory pool with the same signer and seq. /// If the fee of the new transaction is `new_fee` and the fee of the transaction in the memory pool is `old_fee`, /// then `new_fee > old_fee + old_fee >> mem_pool_fee_bump_shift` should be satisfied to replace. @@ -119,7 +119,7 @@ impl MemPool { memory_limit: usize, fee_bump_shift: usize, db: Arc, - minimum_fees: MemPoolFees, + minimum_fees: MemPoolMinFees, ) -> Self { MemPool { minimum_fees, @@ -1669,7 +1669,7 @@ pub mod test { let test_client = TestBlockChainClient::new(); // Set the pay transaction minimum fee - let fees = MemPoolFees::create_from_options( + let fees = MemPoolMinFees::create_from_options( Some(150), None, None, @@ -1724,7 +1724,7 @@ pub mod test { fn external_transactions_whose_fees_are_under_the_mem_pool_min_fee_are_rejected() { let test_client = TestBlockChainClient::new(); // Set the pay transaction minimum fee - let fees = MemPoolFees::create_from_options( + let fees = MemPoolMinFees::create_from_options( Some(150), None, None, diff --git a/core/src/miner/mem_pool_types.rs b/core/src/miner/mem_pool_types.rs index bc1eb7094f..c6a72cd789 100644 --- a/core/src/miner/mem_pool_types.rs +++ b/core/src/miner/mem_pool_types.rs @@ -440,7 +440,7 @@ pub struct AccountDetails { #[derive(Default, Clone, Copy, Debug, PartialEq)] /// Minimum fee thresholds defined not by network but by Mempool -pub struct MemPoolFees { +pub struct MemPoolMinFees { min_pay_transaction_cost: u64, min_set_regular_key_transaction_cost: u64, min_create_shard_transaction_cost: u64, @@ -457,7 +457,7 @@ pub struct MemPoolFees { min_asset_unwrap_ccc_cost: u64, } -impl MemPoolFees { +impl MemPoolMinFees { #[allow(clippy::too_many_arguments)] pub fn create_from_options( min_pay_cost_option: Option, @@ -475,7 +475,7 @@ impl MemPoolFees { min_asset_supply_increase_cost_option: Option, min_asset_unwrap_ccc_cost_option: Option, ) -> Self { - MemPoolFees { + MemPoolMinFees { min_pay_transaction_cost: min_pay_cost_option.unwrap_or_default(), min_set_regular_key_transaction_cost: min_set_regular_key_cost_option.unwrap_or_default(), min_create_shard_transaction_cost: min_create_shard_cost_option.unwrap_or_default(), diff --git a/core/src/miner/miner.rs b/core/src/miner/miner.rs index ac3b2976a9..203ab5d55b 100644 --- a/core/src/miner/miner.rs +++ b/core/src/miner/miner.rs @@ -15,7 +15,7 @@ // along with this program. If not, see . use super::mem_pool::{Error as MemPoolError, MemPool}; -pub use super::mem_pool_types::MemPoolFees; +pub use super::mem_pool_types::MemPoolMinFees; use super::mem_pool_types::{MemPoolInput, TxOrigin, TxTimelock}; use super::sealing_queue::SealingQueue; use super::work_notify::{NotifyWork, WorkPoster}; @@ -78,7 +78,7 @@ pub struct MinerOptions { /// How many historical work packages can we store before running out? pub work_queue_size: usize, /// Minimum fees configured by the machine. - pub mem_pool_fees: MemPoolFees, + pub mem_pool_min_fees: MemPoolMinFees, } impl Default for MinerOptions { @@ -96,7 +96,7 @@ impl Default for MinerOptions { mem_pool_fee_bump_shift: 3, allow_create_shard: false, work_queue_size: 20, - mem_pool_fees: Default::default(), + mem_pool_min_fees: Default::default(), } } } @@ -288,7 +288,7 @@ impl Miner { mem_limit, options.mem_pool_fee_bump_shift, db, - options.mem_pool_fees, + options.mem_pool_min_fees, ))); let notifiers: Vec> = if options.new_work_notify.is_empty() { diff --git a/core/src/miner/mod.rs b/core/src/miner/mod.rs index 339abeb92e..34a54478ac 100644 --- a/core/src/miner/mod.rs +++ b/core/src/miner/mod.rs @@ -24,7 +24,7 @@ mod stratum; mod work_notify; use self::mem_pool_types::AccountDetails; -pub use self::mem_pool_types::MemPoolFees; +pub use self::mem_pool_types::MemPoolMinFees; pub use self::miner::{AuthoringParams, Miner, MinerOptions}; pub use self::stratum::{Config as StratumConfig, Error as StratumError, Stratum}; use crate::account_provider::{AccountProvider, Error as AccountProviderError}; From 6fe2c0b69e8024481d25dd949403893e10165b05 Mon Sep 17 00:00:00 2001 From: Byeongjee Kang Date: Thu, 30 Jan 2020 10:51:43 +0900 Subject: [PATCH 12/55] Add an RPC getting minimum fees confiugred by each machine --- codechain/config/mod.rs | 2 +- core/src/client/client.rs | 5 +++ core/src/client/mod.rs | 3 ++ core/src/client/test_client.rs | 6 +++- core/src/miner/mem_pool_types.rs | 28 +++++++-------- rpc/src/v1/impls/mempool.rs | 6 +++- rpc/src/v1/traits/mempool.rs | 5 ++- rpc/src/v1/types/mem_pool.rs | 55 +++++++++++++++++++++++++++++ rpc/src/v1/types/mod.rs | 4 ++- spec/JSON-RPC.md | 60 ++++++++++++++++++++++++++++++++ 10 files changed, 155 insertions(+), 19 deletions(-) create mode 100644 rpc/src/v1/types/mem_pool.rs diff --git a/codechain/config/mod.rs b/codechain/config/mod.rs index b11977f93e..c6f0a09d0a 100644 --- a/codechain/config/mod.rs +++ b/codechain/config/mod.rs @@ -1,4 +1,4 @@ -// Copyright 2018-2019 Kodebox, Inc. +// Copyright 2018-2020 Kodebox, Inc. // This file is part of CodeChain. // // This program is free software: you can redistribute it and/or modify diff --git a/core/src/client/client.rs b/core/src/client/client.rs index c9e6feb6ee..5185274f18 100644 --- a/core/src/client/client.rs +++ b/core/src/client/client.rs @@ -31,6 +31,7 @@ use crate::scheme::Scheme; use crate::service::ClientIoMessage; use crate::transaction::{LocalizedTransaction, PendingSignedTransactions, SignedTransaction, UnverifiedTransaction}; use crate::types::{BlockId, BlockStatus, TransactionId, VerificationQueueInfo as BlockQueueInfo}; +use crate::MemPoolMinFees; use cdb::{new_journaldb, Algorithm, AsHashDB, DatabaseError}; use cio::IoChannel; use ckey::{Address, NetworkId, PlatformAddress, Public}; @@ -925,6 +926,10 @@ impl MiningBlockChainClient for Client { fn register_immune_users(&self, immune_user_vec: Vec
) { self.importer.miner.register_immune_users(immune_user_vec) } + + fn mem_pool_min_fees(&self) -> MemPoolMinFees { + self.importer.miner.get_options().mem_pool_min_fees + } } impl ChainTimeInfo for Client { diff --git a/core/src/client/mod.rs b/core/src/client/mod.rs index 32aea185c4..54717354fd 100644 --- a/core/src/client/mod.rs +++ b/core/src/client/mod.rs @@ -32,6 +32,7 @@ use crate::blockchain_info::BlockChainInfo; use crate::consensus::EngineError; use crate::encoded; use crate::error::{BlockImportError, Error as GenericError}; +use crate::miner::MemPoolMinFees; use crate::transaction::{LocalizedTransaction, PendingSignedTransactions, SignedTransaction}; use crate::types::{BlockId, BlockStatus, TransactionId, VerificationQueueInfo as BlockQueueInfo}; use cdb::DatabaseError; @@ -294,6 +295,8 @@ pub trait MiningBlockChainClient: BlockChainClient + BlockProducer + FindActionH /// Append designated users to the immune user list. fn register_immune_users(&self, immune_user_vec: Vec
); + + fn mem_pool_min_fees(&self) -> MemPoolMinFees; } /// Provides methods to access database. diff --git a/core/src/client/test_client.rs b/core/src/client/test_client.rs index e30e84d069..ad27928a2b 100644 --- a/core/src/client/test_client.rs +++ b/core/src/client/test_client.rs @@ -41,7 +41,7 @@ use crate::consensus::EngineError; use crate::db::{COL_STATE, NUM_COLUMNS}; use crate::encoded; use crate::error::{BlockImportError, Error as GenericError}; -use crate::miner::{Miner, MinerService, TransactionImportResult}; +use crate::miner::{MemPoolMinFees, Miner, MinerService, TransactionImportResult}; use crate::scheme::Scheme; use crate::transaction::{LocalizedTransaction, PendingSignedTransactions, SignedTransaction}; use crate::types::{BlockId, TransactionId, VerificationQueueInfo as QueueInfo}; @@ -378,6 +378,10 @@ impl MiningBlockChainClient for TestBlockChainClient { fn register_immune_users(&self, immune_user_vec: Vec
) { self.miner.register_immune_users(immune_user_vec) } + + fn mem_pool_min_fees(&self) -> MemPoolMinFees { + self.miner.get_options().mem_pool_min_fees + } } impl AccountData for TestBlockChainClient { diff --git a/core/src/miner/mem_pool_types.rs b/core/src/miner/mem_pool_types.rs index c6a72cd789..26a85eb4f6 100644 --- a/core/src/miner/mem_pool_types.rs +++ b/core/src/miner/mem_pool_types.rs @@ -441,20 +441,20 @@ pub struct AccountDetails { #[derive(Default, Clone, Copy, Debug, PartialEq)] /// Minimum fee thresholds defined not by network but by Mempool pub struct MemPoolMinFees { - min_pay_transaction_cost: u64, - min_set_regular_key_transaction_cost: u64, - min_create_shard_transaction_cost: u64, - min_set_shard_owners_transaction_cost: u64, - min_set_shard_users_transaction_cost: u64, - min_wrap_ccc_transaction_cost: u64, - min_custom_transaction_cost: u64, - min_store_transaction_cost: u64, - min_remove_transaction_cost: u64, - min_asset_mint_cost: u64, - min_asset_transfer_cost: u64, - min_asset_scheme_change_cost: u64, - min_asset_supply_increase_cost: u64, - min_asset_unwrap_ccc_cost: u64, + pub min_pay_transaction_cost: u64, + pub min_set_regular_key_transaction_cost: u64, + pub min_create_shard_transaction_cost: u64, + pub min_set_shard_owners_transaction_cost: u64, + pub min_set_shard_users_transaction_cost: u64, + pub min_wrap_ccc_transaction_cost: u64, + pub min_custom_transaction_cost: u64, + pub min_store_transaction_cost: u64, + pub min_remove_transaction_cost: u64, + pub min_asset_mint_cost: u64, + pub min_asset_transfer_cost: u64, + pub min_asset_scheme_change_cost: u64, + pub min_asset_supply_increase_cost: u64, + pub min_asset_unwrap_ccc_cost: u64, } impl MemPoolMinFees { diff --git a/rpc/src/v1/impls/mempool.rs b/rpc/src/v1/impls/mempool.rs index c5cb2c2db9..9a386a5eac 100644 --- a/rpc/src/v1/impls/mempool.rs +++ b/rpc/src/v1/impls/mempool.rs @@ -16,7 +16,7 @@ use super::super::errors; use super::super::traits::Mempool; -use super::super::types::PendingTransactions; +use super::super::types::{MemPoolMinFees, PendingTransactions}; use ccore::{BlockChainClient, EngineInfo, MiningBlockChainClient, SignedTransaction}; use cjson::bytes::Bytes; use ckey::{Address, PlatformAddress}; @@ -132,4 +132,8 @@ where self.client.register_immune_users(immune_user_vec); Ok(()) } + + fn get_machine_minimum_fees(&self) -> Result { + Ok(MemPoolMinFees::from(self.client.mem_pool_min_fees())) + } } diff --git a/rpc/src/v1/traits/mempool.rs b/rpc/src/v1/traits/mempool.rs index 8ea69d4e25..392cd06a3a 100644 --- a/rpc/src/v1/traits/mempool.rs +++ b/rpc/src/v1/traits/mempool.rs @@ -14,7 +14,7 @@ // You should have received a copy of the GNU Affero General Public License // along with this program. If not, see . -use super::super::types::PendingTransactions; +use super::super::types::{MemPoolMinFees, PendingTransactions}; use cjson::bytes::Bytes; use ckey::PlatformAddress; use ctypes::{Tracker, TxHash}; @@ -70,4 +70,7 @@ pub trait Mempool { #[rpc(name = "mempool_registerImmuneAccounts")] fn register_immune_accounts(&self, immune_user_list: Vec) -> Result<()>; + + #[rpc(name = "mempool_getMachineMinimumFees")] + fn get_machine_minimum_fees(&self) -> Result; } diff --git a/rpc/src/v1/types/mem_pool.rs b/rpc/src/v1/types/mem_pool.rs new file mode 100644 index 0000000000..6ba73aa20d --- /dev/null +++ b/rpc/src/v1/types/mem_pool.rs @@ -0,0 +1,55 @@ +// Copyright 2020 Kodebox, Inc. +// This file is part of CodeChain. +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU Affero General Public License as +// published by the Free Software Foundation, either version 3 of the +// License, or (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU Affero General Public License for more details. +// +// You should have received a copy of the GNU Affero General Public License +// along with this program. If not, see . + +#[derive(Debug, Serialize)] +#[serde(rename_all = "camelCase")] +pub struct MemPoolMinFees { + min_pay_transaction_cost: u64, + min_set_regular_key_transaction_cost: u64, + min_create_shard_transaction_cost: u64, + min_set_shard_owners_transaction_cost: u64, + min_set_shard_users_transaction_cost: u64, + min_wrap_ccc_transaction_cost: u64, + min_custom_transaction_cost: u64, + min_store_transaction_cost: u64, + min_remove_transaction_cost: u64, + min_asset_mint_cost: u64, + min_asset_transfer_cost: u64, + min_asset_scheme_change_cost: u64, + min_asset_supply_increase_cost: u64, + min_asset_unwrap_ccc_cost: u64, +} + +impl From for MemPoolMinFees { + fn from(fees: ccore::MemPoolMinFees) -> Self { + Self { + min_pay_transaction_cost: fees.min_pay_transaction_cost, + min_set_regular_key_transaction_cost: fees.min_set_regular_key_transaction_cost, + min_create_shard_transaction_cost: fees.min_create_shard_transaction_cost, + min_set_shard_owners_transaction_cost: fees.min_set_shard_owners_transaction_cost, + min_set_shard_users_transaction_cost: fees.min_set_shard_users_transaction_cost, + min_wrap_ccc_transaction_cost: fees.min_wrap_ccc_transaction_cost, + min_custom_transaction_cost: fees.min_custom_transaction_cost, + min_store_transaction_cost: fees.min_store_transaction_cost, + min_remove_transaction_cost: fees.min_remove_transaction_cost, + min_asset_mint_cost: fees.min_asset_mint_cost, + min_asset_transfer_cost: fees.min_asset_transfer_cost, + min_asset_scheme_change_cost: fees.min_asset_scheme_change_cost, + min_asset_supply_increase_cost: fees.min_asset_supply_increase_cost, + min_asset_unwrap_ccc_cost: fees.min_asset_unwrap_ccc_cost, + } + } +} diff --git a/rpc/src/v1/types/mod.rs b/rpc/src/v1/types/mod.rs index 66d9b30ba5..8f73c25e24 100644 --- a/rpc/src/v1/types/mod.rs +++ b/rpc/src/v1/types/mod.rs @@ -1,4 +1,4 @@ -// Copyright 2018-2019 Kodebox, Inc. +// Copyright 2018-2020 Kodebox, Inc. // This file is part of CodeChain. // // This program is free software: you can redistribute it and/or modify @@ -20,6 +20,7 @@ mod asset_input; mod asset_output; mod asset_scheme; mod block; +mod mem_pool; mod text; mod transaction; mod unsigned_transaction; @@ -34,6 +35,7 @@ pub use self::asset::OwnedAsset; pub use self::asset_scheme::AssetScheme; pub use self::block::Block; pub use self::block::BlockNumberAndHash; +pub use self::mem_pool::MemPoolMinFees; pub use self::text::Text; pub use self::transaction::{PendingTransactions, Transaction}; pub use self::unsigned_transaction::UnsignedTransaction; diff --git a/spec/JSON-RPC.md b/spec/JSON-RPC.md index 92e6130d9a..8e9f3f5d73 100644 --- a/spec/JSON-RPC.md +++ b/spec/JSON-RPC.md @@ -328,6 +328,7 @@ When `Transaction` is included in any response, there will be an additional fiel * [mempool_banAccounts](#mempool_banaccounts) * [mempool_registerImmuneAccounts](#mempool_registerimmuneaccounts) * [mempool_getRegisteredImmuneAccounts](#mempool_getregisteredimmuneaccounts) + * [mempool_getMachineMinimumFees](#mempool_getmachineminimumfees) *** * [engine_getCoinbase](#engine_getcoinbase) * [engine_getBlockReward](#engine_getblockreward) @@ -1988,6 +1989,65 @@ curl \ [Back to **List of methods**](#list-of-methods) +## mempool_getMachineMinimumFees +Get minimum fees configured by the machine. + +### Params +No parameters + +### Returns +{ + "minAssetMintCost": `number`, + "minAssetSchemeChangeCost":`number`, + "minAssetSupplyIncreaseCost": `number`, + "minAssetTransferCost":`number`, + "minAssetUnwrapCccCost":`number`, + "minCreateShardTransactionCost":`number`, + "minCustomTransactionCost":`number`, + "minStoreTransactionCost": `number`, + "minRemoveTransactionCost": `number`, + "minPayTransactionCost":`number`, + "minSetRegularKeyTransactionCost":`number`, + "minSetShardOwnersTransactionCost":`number`, + "minSetShardUsersTransactionCost":`number`, + "minWrapCccTransactionCost":`number` +} + +### Request Example +``` +curl \ + -H 'Content-Type: application/json' \ + -d '{"jsonrpc": "2.0", "method": "mempool_getMachineMinimumFees", "params": [], "id": null}' \ + localhost:8080 +``` + +### Response Example +``` +{ + "jsonrpc":"2.0", + "result":{ + "minAssetMintCost":0, + "minAssetSchemeChangeCost":0, + "minAssetSupplyIncreaseCost":0, + "minAssetTransferCost":0, + "minAssetUnwrapCccCost":0, + "minCreateShardTransactionCost":0, + "minCustomTransactionCost":0, + "minStoreTransactionCost": 0, + "minRemoveTransactionCost": 0, + "minPayTransactionCost":0, + "minSetRegularKeyTransactionCost":0, + "minSetShardOwnersTransactionCost":0, + "minSetShardUsersTransactionCost":0, + "minWrapCccTransactionCost":0 + }, + "id":null +} + +``` + +[Back to **List of methods**](#list-of-methods) + ## engine_getCoinbase Gets coinbase's account id. From c1dc53122e8e6fd0fe8cebc84016dba3668c26ae Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Fri, 31 Jan 2020 19:22:45 +0900 Subject: [PATCH 13/55] Remove duplicated TermInfo --- core/src/miner/mod.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/core/src/miner/mod.rs b/core/src/miner/mod.rs index 34a54478ac..64e69c9210 100644 --- a/core/src/miner/mod.rs +++ b/core/src/miner/mod.rs @@ -123,7 +123,7 @@ pub trait MinerService: Send + Sync { ) -> Vec>; /// Imports own (node owner) transaction to mem pool. - fn import_own_transaction( + fn import_own_transaction( &self, chain: &C, tx: SignedTransaction, From cda62773c4170eef9770c734b0d7bd2cd900908a Mon Sep 17 00:00:00 2001 From: Seulgi Kim Date: Thu, 9 Jan 2020 16:36:59 +0900 Subject: [PATCH 14/55] Change constants to enumerations --- state/src/item/account.rs | 2 +- state/src/item/asset.rs | 2 +- state/src/item/asset_scheme.rs | 2 +- state/src/item/metadata.rs | 2 +- state/src/item/mod.rs | 18 +++-- state/src/item/regular_account.rs | 2 +- state/src/item/shard.rs | 2 +- state/src/item/text.rs | 2 +- types/src/transaction/action.rs | 125 +++++++++++++++++++----------- 9 files changed, 96 insertions(+), 61 deletions(-) diff --git a/state/src/item/account.rs b/state/src/item/account.rs index 9907d2b18d..a89d94ab78 100644 --- a/state/src/item/account.rs +++ b/state/src/item/account.rs @@ -123,7 +123,7 @@ impl CacheableItem for Account { } } -const PREFIX: u8 = super::ADDRESS_PREFIX; +const PREFIX: u8 = super::Prefix::Account as u8; impl Encodable for Account { fn rlp_append(&self, s: &mut RlpStream) { diff --git a/state/src/item/asset.rs b/state/src/item/asset.rs index 0647798150..1cd292d057 100644 --- a/state/src/item/asset.rs +++ b/state/src/item/asset.rs @@ -99,7 +99,7 @@ impl CacheableItem for OwnedAsset { } } -const PREFIX: u8 = super::OWNED_ASSET_PREFIX; +const PREFIX: u8 = super::Prefix::OwnedAsset as u8; impl Encodable for OwnedAsset { fn rlp_append(&self, s: &mut RlpStream) { diff --git a/state/src/item/asset_scheme.rs b/state/src/item/asset_scheme.rs index a8be675e7f..3dd5ed1bed 100644 --- a/state/src/item/asset_scheme.rs +++ b/state/src/item/asset_scheme.rs @@ -148,7 +148,7 @@ impl AssetScheme { } } -const PREFIX: u8 = super::ASSET_SCHEME_PREFIX; +const PREFIX: u8 = super::Prefix::AssetScheme as u8; impl Default for AssetScheme { fn default() -> Self { diff --git a/state/src/item/metadata.rs b/state/src/item/metadata.rs index dc65cde376..69340f7f74 100644 --- a/state/src/item/metadata.rs +++ b/state/src/item/metadata.rs @@ -121,7 +121,7 @@ impl CacheableItem for Metadata { } } -const PREFIX: u8 = super::METADATA_PREFIX; +const PREFIX: u8 = super::Prefix::Metadata as u8; impl Encodable for Metadata { fn rlp_append(&self, s: &mut RlpStream) { diff --git a/state/src/item/mod.rs b/state/src/item/mod.rs index 6eb88c9a7b..79f8f221a4 100644 --- a/state/src/item/mod.rs +++ b/state/src/item/mod.rs @@ -26,10 +26,14 @@ pub mod regular_account; pub mod shard; pub mod text; -const OWNED_ASSET_PREFIX: u8 = b'A'; -const ADDRESS_PREFIX: u8 = b'C'; -const SHARD_PREFIX: u8 = b'H'; -const METADATA_PREFIX: u8 = b'M'; -const REGULAR_ACCOUNT_PREFIX: u8 = b'R'; -const ASSET_SCHEME_PREFIX: u8 = b'S'; -const TEXT_PREFIX: u8 = b'T'; +#[derive(Clone, Copy)] +#[repr(u8)] +enum Prefix { + OwnedAsset = b'A', + Account = b'C', + Shard = b'H', + Metadata = b'M', + RegularAccount = b'R', + AssetScheme = b'S', + Text = b'T', +} diff --git a/state/src/item/regular_account.rs b/state/src/item/regular_account.rs index c185aa5781..18ae925506 100644 --- a/state/src/item/regular_account.rs +++ b/state/src/item/regular_account.rs @@ -54,7 +54,7 @@ impl CacheableItem for RegularAccount { } } -const PREFIX: u8 = super::REGULAR_ACCOUNT_PREFIX; +const PREFIX: u8 = super::Prefix::RegularAccount as u8; impl Encodable for RegularAccount { fn rlp_append(&self, s: &mut RlpStream) { diff --git a/state/src/item/shard.rs b/state/src/item/shard.rs index 694d3838bb..64ad1bcd7e 100644 --- a/state/src/item/shard.rs +++ b/state/src/item/shard.rs @@ -78,7 +78,7 @@ impl CacheableItem for Shard { } } -const PREFIX: u8 = super::SHARD_PREFIX; +const PREFIX: u8 = super::Prefix::Shard as u8; impl Encodable for Shard { fn rlp_append(&self, s: &mut RlpStream) { diff --git a/state/src/item/text.rs b/state/src/item/text.rs index cda8f3c4fb..6bc2e588a0 100644 --- a/state/src/item/text.rs +++ b/state/src/item/text.rs @@ -62,7 +62,7 @@ impl CacheableItem for Text { } } -const PREFIX: u8 = super::TEXT_PREFIX; +const PREFIX: u8 = super::Prefix::Text as u8; impl Encodable for Text { fn rlp_append(&self, s: &mut RlpStream) { diff --git a/types/src/transaction/action.rs b/types/src/transaction/action.rs index 3d46389a69..973680c39f 100644 --- a/types/src/transaction/action.rs +++ b/types/src/transaction/action.rs @@ -23,25 +23,57 @@ use primitives::{Bytes, H160, H256}; use rlp::{Decodable, DecoderError, Encodable, Rlp, RlpStream}; use std::collections::{HashMap, HashSet}; -const PAY: u8 = 0x02; -const SET_REGULAR_KEY: u8 = 0x03; -const CREATE_SHARD: u8 = 0x04; -const SET_SHARD_OWNERS: u8 = 0x05; -const SET_SHARD_USERS: u8 = 0x06; -const WRAP_CCC: u8 = 0x07; -const STORE: u8 = 0x08; -const REMOVE: u8 = 0x09; -const UNWRAP_CCC: u8 = 0x11; -const MINT_ASSET: u8 = 0x13; -const TRANSFER_ASSET: u8 = 0x14; -const CHANGE_ASSET_SCHEME: u8 = 0x15; -// Derepcated -//const COMPOSE_ASSET: u8 = 0x16; -// Derepcated -//const DECOMPOSE_ASSET: u8 = 0x17; -const INCREASE_ASSET_SUPPLY: u8 = 0x18; +#[derive(Clone, Copy)] +#[repr(u8)] +enum ActionTag { + Pay = 0x02, + SetRegularKey = 0x03, + CreateShard = 0x04, + SetShardOwners = 0x05, + SetShardUsers = 0x06, + WrapCcc = 0x07, + Store = 0x08, + Remove = 0x09, + UnwrapCcc = 0x11, + MintAsset = 0x13, + TransferAsset = 0x14, + ChangeAssetScheme = 0x15, + // Derepcated + // ComposeAsset = 0x16, + // Derepcated + // DecomposeAsset = 0x17, + IncreaseAssetSupply = 0x18, + Custom = 0xFF, +} -const CUSTOM: u8 = 0xFF; +impl Encodable for ActionTag { + fn rlp_append(&self, s: &mut RlpStream) { + (*self as u8).rlp_append(s) + } +} + +impl Decodable for ActionTag { + fn decode(rlp: &Rlp) -> Result { + let tag = rlp.as_val()?; + match tag { + 0x02u8 => Ok(Self::Pay), + 0x03u8 => Ok(Self::SetRegularKey), + 0x04u8 => Ok(Self::CreateShard), + 0x05u8 => Ok(Self::SetShardOwners), + 0x06u8 => Ok(Self::SetShardUsers), + 0x07u8 => Ok(Self::WrapCcc), + 0x08u8 => Ok(Self::Store), + 0x09u8 => Ok(Self::Remove), + 0x11u8 => Ok(Self::UnwrapCcc), + 0x13u8 => Ok(Self::MintAsset), + 0x14u8 => Ok(Self::TransferAsset), + 0x15u8 => Ok(Self::ChangeAssetScheme), + 0x18u8 => Ok(Self::IncreaseAssetSupply), + 0xFFu8 => Ok(Self::Custom), + _ => Err(DecoderError::Custom("Unexpected action prefix")), + } + } +} #[derive(Debug, Clone, PartialEq, Eq)] pub enum Action { @@ -464,7 +496,7 @@ impl Encodable for Action { approvals, } => { s.begin_list(11) - .append(&MINT_ASSET) + .append(&ActionTag::MintAsset) .append(network_id) .append(shard_id) .append(metadata) @@ -487,7 +519,7 @@ impl Encodable for Action { } => { let empty: Vec = vec![]; s.begin_list(9) - .append(&TRANSFER_ASSET) + .append(&ActionTag::TransferAsset) .append(network_id) .append_list(burns) .append_list(inputs) @@ -510,7 +542,7 @@ impl Encodable for Action { approvals, } => { s.begin_list(10) - .append(&CHANGE_ASSET_SCHEME) + .append(&ActionTag::ChangeAssetScheme) .append(network_id) .append(shard_id) .append(asset_type) @@ -530,7 +562,7 @@ impl Encodable for Action { approvals, } => { s.begin_list(9) - .append(&INCREASE_ASSET_SUPPLY) + .append(&ActionTag::IncreaseAssetSupply) .append(network_id) .append(shard_id) .append(asset_type) @@ -545,14 +577,14 @@ impl Encodable for Action { burn, receiver, } => { - s.begin_list(4).append(&UNWRAP_CCC).append(network_id).append(burn).append(receiver); + s.begin_list(4).append(&ActionTag::UnwrapCcc).append(network_id).append(burn).append(receiver); } Action::Pay { receiver, quantity, } => { s.begin_list(3); - s.append(&PAY); + s.append(&ActionTag::Pay); s.append(receiver); s.append(quantity); } @@ -560,14 +592,14 @@ impl Encodable for Action { key, } => { s.begin_list(2); - s.append(&SET_REGULAR_KEY); + s.append(&ActionTag::SetRegularKey); s.append(key); } Action::CreateShard { users, } => { s.begin_list(2); - s.append(&CREATE_SHARD); + s.append(&ActionTag::CreateShard); s.append_list(users); } Action::SetShardOwners { @@ -575,7 +607,7 @@ impl Encodable for Action { owners, } => { s.begin_list(3); - s.append(&SET_SHARD_OWNERS); + s.append(&ActionTag::SetShardOwners); s.append(shard_id); s.append_list(owners); } @@ -584,7 +616,7 @@ impl Encodable for Action { users, } => { s.begin_list(3); - s.append(&SET_SHARD_USERS); + s.append(&ActionTag::SetShardUsers); s.append(shard_id); s.append_list(users); } @@ -596,7 +628,7 @@ impl Encodable for Action { payer, } => { s.begin_list(6); - s.append(&WRAP_CCC); + s.append(&ActionTag::WrapCcc); s.append(shard_id); s.append(lock_script_hash); s.append(parameters); @@ -609,7 +641,7 @@ impl Encodable for Action { signature, } => { s.begin_list(4); - s.append(&STORE); + s.append(&ActionTag::Store); s.append(content); s.append(certifier); s.append(signature); @@ -619,7 +651,7 @@ impl Encodable for Action { signature, } => { s.begin_list(3); - s.append(&REMOVE); + s.append(&ActionTag::Remove); s.append(hash); s.append(signature); } @@ -628,7 +660,7 @@ impl Encodable for Action { bytes, } => { s.begin_list(3); - s.append(&CUSTOM); + s.append(&ActionTag::Custom); s.append(handler_id); s.append(bytes); } @@ -639,7 +671,7 @@ impl Encodable for Action { impl Decodable for Action { fn decode(rlp: &Rlp) -> Result { match rlp.val_at(0)? { - MINT_ASSET => { + ActionTag::MintAsset => { let item_count = rlp.item_count()?; if item_count != 11 { return Err(DecoderError::RlpIncorrectListLen { @@ -662,7 +694,7 @@ impl Decodable for Action { approvals: rlp.list_at(10)?, }) } - TRANSFER_ASSET => { + ActionTag::TransferAsset => { let item_count = rlp.item_count()?; if item_count != 9 { return Err(DecoderError::RlpIncorrectListLen { @@ -680,7 +712,7 @@ impl Decodable for Action { expiration: rlp.val_at(8)?, }) } - CHANGE_ASSET_SCHEME => { + ActionTag::ChangeAssetScheme => { let item_count = rlp.item_count()?; if item_count != 10 { return Err(DecoderError::RlpIncorrectListLen { @@ -700,7 +732,7 @@ impl Decodable for Action { approvals: rlp.list_at(9)?, }) } - INCREASE_ASSET_SUPPLY => { + ActionTag::IncreaseAssetSupply => { let item_count = rlp.item_count()?; if item_count != 9 { return Err(DecoderError::RlpIncorrectListLen { @@ -721,7 +753,7 @@ impl Decodable for Action { approvals: rlp.list_at(8)?, }) } - UNWRAP_CCC => { + ActionTag::UnwrapCcc => { let item_count = rlp.item_count()?; if item_count != 4 { return Err(DecoderError::RlpIncorrectListLen { @@ -735,7 +767,7 @@ impl Decodable for Action { receiver: rlp.val_at(3)?, }) } - PAY => { + ActionTag::Pay => { let item_count = rlp.item_count()?; if item_count != 3 { return Err(DecoderError::RlpIncorrectListLen { @@ -748,7 +780,7 @@ impl Decodable for Action { quantity: rlp.val_at(2)?, }) } - SET_REGULAR_KEY => { + ActionTag::SetRegularKey => { let item_count = rlp.item_count()?; if item_count != 2 { return Err(DecoderError::RlpIncorrectListLen { @@ -760,7 +792,7 @@ impl Decodable for Action { key: rlp.val_at(1)?, }) } - CREATE_SHARD => { + ActionTag::CreateShard => { let item_count = rlp.item_count()?; if item_count != 2 { return Err(DecoderError::RlpIncorrectListLen { @@ -772,7 +804,7 @@ impl Decodable for Action { users: rlp.list_at(1)?, }) } - SET_SHARD_OWNERS => { + ActionTag::SetShardOwners => { let item_count = rlp.item_count()?; if item_count != 3 { return Err(DecoderError::RlpIncorrectListLen { @@ -785,7 +817,7 @@ impl Decodable for Action { owners: rlp.list_at(2)?, }) } - SET_SHARD_USERS => { + ActionTag::SetShardUsers => { let item_count = rlp.item_count()?; if item_count != 3 { return Err(DecoderError::RlpIncorrectListLen { @@ -798,7 +830,7 @@ impl Decodable for Action { users: rlp.list_at(2)?, }) } - WRAP_CCC => { + ActionTag::WrapCcc => { let item_count = rlp.item_count()?; if item_count != 6 { return Err(DecoderError::RlpIncorrectListLen { @@ -814,7 +846,7 @@ impl Decodable for Action { payer: rlp.val_at(5)?, }) } - STORE => { + ActionTag::Store => { let item_count = rlp.item_count()?; if item_count != 4 { return Err(DecoderError::RlpIncorrectListLen { @@ -828,7 +860,7 @@ impl Decodable for Action { signature: rlp.val_at(3)?, }) } - REMOVE => { + ActionTag::Remove => { let item_count = rlp.item_count()?; if item_count != 3 { return Err(DecoderError::RlpIncorrectListLen { @@ -841,7 +873,7 @@ impl Decodable for Action { signature: rlp.val_at(2)?, }) } - CUSTOM => { + ActionTag::Custom => { let item_count = rlp.item_count()?; if item_count != 3 { return Err(DecoderError::RlpIncorrectListLen { @@ -854,7 +886,6 @@ impl Decodable for Action { bytes: rlp.val_at(2)?, }) } - _ => Err(DecoderError::Custom("Unexpected action prefix")), } } } From 6cbc5414b0001b9d112e1ab1fa124e4e4d8d1b2d Mon Sep 17 00:00:00 2001 From: Byeongjee Kang Date: Wed, 5 Feb 2020 16:12:00 +0900 Subject: [PATCH 15/55] Fix typos --- codechain/auto_self_nominate.rs | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/codechain/auto_self_nominate.rs b/codechain/auto_self_nominate.rs index 58a4887cd9..70c616706a 100644 --- a/codechain/auto_self_nominate.rs +++ b/codechain/auto_self_nominate.rs @@ -84,8 +84,8 @@ impl AutoSelfNomination { pub fn send_self_nominate_transaction(&self, matches: &ArgMatches) { let config = load_config(matches).unwrap(); let account_address = config.mining.engine_signer.unwrap(); - let defualt_metadata = config.mining.self_nomination_metadata.unwrap(); - let target_deposite = config.mining.self_target_deposit.unwrap(); + let default_metadata = config.mining.self_nomination_metadata.unwrap(); + let target_deposit = config.mining.self_target_deposit.unwrap(); let interval = config.mining.self_nomination_interval.unwrap(); let self_client = self.client.clone(); let self_signer = self.signer.clone(); @@ -96,8 +96,8 @@ impl AutoSelfNomination { &self_client, &self_signer, &account_address, - &defualt_metadata, - target_deposite, + &default_metadata, + target_deposit, ); thread::sleep(Duration::from_millis(interval)); }) From 0a305a3dc87919d43177ee95394af52517a47d22 Mon Sep 17 00:00:00 2001 From: Seulgi Kim Date: Fri, 7 Feb 2020 10:11:42 +0900 Subject: [PATCH 16/55] Upgrade codechain-crypto to 0.2.0 The version replaced the dependency of underlying crypto libraries. To upgrade the version, it also upgrades codechain-db, merkle-trie and trie-standardmap which use codechain-crypto. --- Cargo.lock | 225 +++++++++++++++++++++++++-- Cargo.toml | 2 +- core/Cargo.toml | 6 +- discovery/Cargo.toml | 2 +- key/Cargo.toml | 2 +- keystore/Cargo.toml | 2 +- network/Cargo.toml | 2 +- network/src/p2p/connection/mod.rs | 10 +- network/src/p2p/handler.rs | 10 +- network/src/p2p/message/extension.rs | 9 +- network/src/routing_table.rs | 23 +-- network/src/session/session.rs | 11 +- rpc/Cargo.toml | 2 +- state/Cargo.toml | 6 +- stratum/Cargo.toml | 2 +- sync/Cargo.toml | 7 +- types/Cargo.toml | 2 +- vm/Cargo.toml | 2 +- 18 files changed, 260 insertions(+), 65 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 60ed909782..9f8bd8707f 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -6,6 +6,38 @@ version = "1.0.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7e522997b529f05601e05166c07ed17789691f562762c7f3b987263d2dedee5c" +[[package]] +name = "aes" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "54eb1d8fe354e5fc611daf4f2ea97dd45a765f4f1e4512306ec183ae2e8f20c9" +dependencies = [ + "aes-soft", + "aesni", + "block-cipher-trait", +] + +[[package]] +name = "aes-soft" +version = "0.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cfd7e7ae3f9a1fb5c03b389fc6bb9a51400d0c13053f0dca698c832bfd893a0d" +dependencies = [ + "block-cipher-trait", + "byteorder", + "opaque-debug", +] + +[[package]] +name = "aesni" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2f70a6b5f971e473091ab7cfb5ffac6cde81666c4556751d8d5620ead8abf100" +dependencies = [ + "block-cipher-trait", + "opaque-debug", +] + [[package]] name = "aho-corasick" version = "0.6.4" @@ -122,6 +154,18 @@ version = "0.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3e54f7b7a46d7b183eb41e2d82965261fa8a1597c68b50aced268ee1fc70272d" +[[package]] +name = "blake2" +version = "0.8.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "94cb07b0da6a73955f8fb85d24c466778e70cda767a568229b104f0264089330" +dependencies = [ + "byte-tools", + "crypto-mac", + "digest", + "opaque-debug", +] + [[package]] name = "block-buffer" version = "0.7.3" @@ -134,6 +178,25 @@ dependencies = [ "generic-array", ] +[[package]] +name = "block-cipher-trait" +version = "0.6.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1c924d49bd09e7c06003acda26cd9742e796e34282ec6c1189404dee0c1f4774" +dependencies = [ + "generic-array", +] + +[[package]] +name = "block-modes" +version = "0.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "31aa8410095e39fdb732909fb5730a48d5bd7c2e3cd76bd1b07b3dbea130c529" +dependencies = [ + "block-cipher-trait", + "block-padding", +] + [[package]] name = "block-padding" version = "0.1.4" @@ -333,19 +396,29 @@ dependencies = [ [[package]] name = "codechain-crypto" -version = "0.1.0" -source = "git+https://github.com/CodeChain-io/rust-codechain-crypto.git#2857470de2f5480b7d61ff57fb652f9d9fc5585b" +version = "0.2.0" +source = "git+https://github.com/CodeChain-io/rust-codechain-crypto.git#565c1eebf3abc909ed297bee584dddb84784d838" dependencies = [ + "aes", + "blake2", + "block-modes", + "ctr", + "digest", + "hex", "primitives", "quick-error", "ring", - "rust-crypto", + "ripemd160", + "scrypt", + "sha-1", + "sha2", + "sha3", ] [[package]] name = "codechain-db" -version = "0.1.0" -source = "git+https://github.com/CodeChain-io/rust-codechain-db.git#9948464d24f3432f70fcb12df97c81ec8eab7bfa" +version = "0.2.0" +source = "git+https://github.com/CodeChain-io/rust-codechain-db.git#08bd8ceeb360a1e17e011b4dcb084333ddda5cab" dependencies = [ "codechain-crypto", "kvdb", @@ -567,6 +640,7 @@ name = "codechain-sync" version = "0.1.0" dependencies = [ "codechain-core", + "codechain-crypto", "codechain-db", "codechain-key", "codechain-logger", @@ -742,6 +816,26 @@ version = "0.2.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7a81dae078cea95a014a339291cec439d2f232ebe854a9d672b796c6afafa9b7" +[[package]] +name = "crypto-mac" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4434400df11d95d556bac068ddfedd482915eb18fe8bea89bc80b6e4b1c179e5" +dependencies = [ + "generic-array", + "subtle", +] + +[[package]] +name = "ctr" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "022cd691704491df67d25d006fe8eca083098253c4d43516c2206479c58c6736" +dependencies = [ + "block-cipher-trait", + "stream-cipher", +] + [[package]] name = "ctrlc" version = "1.1.1" @@ -1136,6 +1230,22 @@ dependencies = [ "libc", ] +[[package]] +name = "hex" +version = "0.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "644f9158b2f133fd50f5fb3242878846d9eb792e445c893805ff0e3824006e35" + +[[package]] +name = "hmac" +version = "0.7.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5dcb5e64cda4c23119ab41ba960d1e170a774c8e4b9d9e6a9bc18aabf5e59695" +dependencies = [ + "crypto-mac", + "digest", +] + [[package]] name = "http" version = "0.1.17" @@ -1361,6 +1471,12 @@ dependencies = [ "ws", ] +[[package]] +name = "keccak" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "67c21572b4949434e4fc1e1978b99c5f77064153c59d998bf13ecd96fb5ecba7" + [[package]] name = "kernel32-sys" version = "0.2.2" @@ -1563,11 +1679,12 @@ checksum = "0f9dc261e2b62d7a622bf416ea3c5245cdd5d9a7fcc428c0d06804dfce1775b3" [[package]] name = "merkle-trie" -version = "0.1.0" -source = "git+https://github.com/CodeChain-io/rust-merkle-trie.git#a6e067fe71c232d9024952ee63905ab4f5c4407d" +version = "0.4.0" +source = "git+https://github.com/CodeChain-io/rust-merkle-trie.git#c2a84172e9c212bee1a29ae2e056d3ea988115ce" dependencies = [ "codechain-crypto", "codechain-db", + "lru-cache", "primitives", "rand 0.6.1", "rlp", @@ -1951,6 +2068,16 @@ dependencies = [ "winapi 0.3.6", ] +[[package]] +name = "pbkdf2" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "006c038a43a45995a9670da19e67600114740e8511d4333bf97a56e66a7542d9" +dependencies = [ + "byteorder", + "crypto-mac", +] + [[package]] name = "percent-encoding" version = "1.0.1" @@ -2026,7 +2153,7 @@ checksum = "e3cbf9f658cdb5000fcf6f362b8ea2ba154b9f146a61c7a20d647034c6b6561b" [[package]] name = "primitives" version = "0.4.0" -source = "git+https://github.com/CodeChain-io/rust-codechain-primitives.git#9dbda1bcc2b8f68c00e6426754800fb806e8117a" +source = "git+https://github.com/CodeChain-io/rust-codechain-primitives.git#eb8da500a77fa84e53750e8661a8603a78a2a7b3" dependencies = [ "ethereum-types", ] @@ -2182,7 +2309,7 @@ version = "0.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "771b009e3a508cb67e8823dda454aaa5368c7bc1c16829fb77d3e980440dd34a" dependencies = [ - "rand_core 0.3.0", + "rand_core 0.2.2", "rustc_version", ] @@ -2226,7 +2353,7 @@ version = "0.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7b40677c7be09ae76218dc623efbf7b18e34bced3f38883af07bb75630a21bc4" dependencies = [ - "rand_core 0.3.0", + "rand_core 0.2.2", ] [[package]] @@ -2263,7 +2390,7 @@ version = "0.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "effa3fcaa47e18db002bdde6060944b6d2f9cfd8db471c30e873448ad9187be3" dependencies = [ - "rand_core 0.3.0", + "rand_core 0.2.2", ] [[package]] @@ -2349,10 +2476,21 @@ dependencies = [ "winapi 0.3.6", ] +[[package]] +name = "ripemd160" +version = "0.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ad5112e0dbbb87577bfbc56c42450235e3012ce336e29c5befd7807bd626da4a" +dependencies = [ + "block-buffer", + "digest", + "opaque-debug", +] + [[package]] name = "rlp" version = "0.4.0" -source = "git+https://github.com/CodeChain-io/rlp.git#339cc6aa02d91635199178e7c7be07b347054697" +source = "git+https://github.com/CodeChain-io/rlp.git#64fdbc5758e05483f62fae99521520f566eaca9d" dependencies = [ "primitives", "rustc-hex 1.0.0", @@ -2370,7 +2508,7 @@ dependencies = [ [[package]] name = "rlp_derive" version = "0.2.0" -source = "git+https://github.com/CodeChain-io/rlp.git#339cc6aa02d91635199178e7c7be07b347054697" +source = "git+https://github.com/CodeChain-io/rlp.git#64fdbc5758e05483f62fae99521520f566eaca9d" dependencies = [ "proc-macro2 0.4.30", "quote 0.6.12", @@ -2480,6 +2618,19 @@ version = "1.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "b42e15e59b18a828bbf5c58ea01debb36b9b096346de35d941dcb89009f24a0d" +[[package]] +name = "scrypt" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "656c79d0e90d0ab28ac86bf3c3d10bfbbac91450d3f190113b4e76d9fec3cfdd" +dependencies = [ + "byte-tools", + "byteorder", + "hmac", + "pbkdf2", + "sha2", +] + [[package]] name = "secp256k1" version = "0.6.0" @@ -2585,9 +2736,21 @@ dependencies = [ [[package]] name = "sha-1" -version = "0.8.1" +version = "0.8.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f7d94d0bede923b3cea61f3f1ff57ff8cdfd77b400fb8f9998949e0cf04163df" +dependencies = [ + "block-buffer", + "digest", + "fake-simd", + "opaque-debug", +] + +[[package]] +name = "sha2" +version = "0.8.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "23962131a91661d643c98940b20fcaffe62d776a823247be80a48fcb8b6fce68" +checksum = "a256f46ea78a0c0d9ff00077504903ac881a1dafdc20da66545699e7776b3e69" dependencies = [ "block-buffer", "digest", @@ -2595,6 +2758,19 @@ dependencies = [ "opaque-debug", ] +[[package]] +name = "sha3" +version = "0.8.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dd26bc0e7a2e3a7c959bc494caf58b72ee0c71d67704e9520f736ca7e4853ecf" +dependencies = [ + "block-buffer", + "byte-tools", + "digest", + "keccak", + "opaque-debug", +] + [[package]] name = "shell32-sys" version = "0.1.2" @@ -2688,6 +2864,15 @@ version = "1.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "15132e0e364248108c5e2c02e3ab539be8d6f5d52a01ca9bbf27ed657316f02b" +[[package]] +name = "stream-cipher" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8131256a5896cabcf5eb04f4d6dacbe1aefda854b0d9896e09cb58829ec5638c" +dependencies = [ + "generic-array", +] + [[package]] name = "string" version = "0.1.3" @@ -2700,6 +2885,12 @@ version = "0.7.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "bb4f380125926a99e52bc279241539c018323fab05ad6368b56f93d9369ff550" +[[package]] +name = "subtle" +version = "1.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2d67a5a62ba6e01cb2192ff309324cb4875d0c451d55fe2319433abe7a05a8ee" + [[package]] name = "syn" version = "0.13.11" @@ -3095,8 +3286,8 @@ dependencies = [ [[package]] name = "trie-standardmap" -version = "0.2.0" -source = "git+https://github.com/CodeChain-io/trie-standardmap.git#f2cdd24acb7f00e44566d86af6102c5d16b02921" +version = "0.3.0" +source = "git+https://github.com/CodeChain-io/trie-standardmap.git#190b7a3b43adc063e0d7c5043afc1ff9d981c870" dependencies = [ "codechain-crypto", "primitives", diff --git a/Cargo.toml b/Cargo.toml index ba2ada2085..ab5ab8f2fb 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -18,7 +18,7 @@ edition = "2018" app_dirs = "^1.2.1" clap = { version = "2", features = ["yaml"] } codechain-core = { path = "core" } -codechain-crypto = { git = "https://github.com/CodeChain-io/rust-codechain-crypto.git", version = "0.1" } +codechain-crypto = { git = "https://github.com/CodeChain-io/rust-codechain-crypto.git", version = "0.2" } codechain-discovery = { path = "discovery" } codechain-logger = { path = "util/logger" } codechain-key = { path = "key" } diff --git a/core/Cargo.toml b/core/Cargo.toml index ee8ec36be0..df178c9c35 100644 --- a/core/Cargo.toml +++ b/core/Cargo.toml @@ -5,8 +5,8 @@ authors = ["CodeChain Team "] edition = "2018" [dependencies] -codechain-crypto = { git = "https://github.com/CodeChain-io/rust-codechain-crypto.git", version = "0.1" } -codechain-db = { git = "https://github.com/CodeChain-io/rust-codechain-db.git", version = "0.1" } +codechain-crypto = { git = "https://github.com/CodeChain-io/rust-codechain-crypto.git", version = "0.2" } +codechain-db = { git = "https://github.com/CodeChain-io/rust-codechain-db.git", version = "0.2" } codechain-io = { path = "../util/io" } codechain-json = { path = "../json" } codechain-key = { path = "../key" } @@ -27,7 +27,7 @@ kvdb-memorydb = "0.1" linked-hash-map = "0.5" log = "0.4.6" lru-cache = "0.1.2" -merkle-trie = { git = "https://github.com/CodeChain-io/rust-merkle-trie.git", version = "0.1" } +merkle-trie = { git = "https://github.com/CodeChain-io/rust-merkle-trie.git", version = "0.4" } num-rational = "0.2.1" parking_lot = "0.6.0" primitives = { git = "https://github.com/CodeChain-io/rust-codechain-primitives.git", version = "0.4" } diff --git a/discovery/Cargo.toml b/discovery/Cargo.toml index f04144ecce..d330626fa7 100644 --- a/discovery/Cargo.toml +++ b/discovery/Cargo.toml @@ -5,7 +5,7 @@ authors = ["CodeChain Team "] edition = "2018" [dependencies] -codechain-crypto = { git = "https://github.com/CodeChain-io/rust-codechain-crypto.git", version = "0.1" } +codechain-crypto = { git = "https://github.com/CodeChain-io/rust-codechain-crypto.git", version = "0.2" } codechain-key = { path = "../key" } codechain-logger = { path = "../util/logger" } codechain-network = { path = "../network" } diff --git a/key/Cargo.toml b/key/Cargo.toml index 8a3b6cadad..1e65fbb30b 100644 --- a/key/Cargo.toml +++ b/key/Cargo.toml @@ -10,7 +10,7 @@ rustc-hex = "1.0" rustc-serialize = "0.3" lazy_static = "1.2" bech32 = "0.2.2" -codechain-crypto = { git = "https://github.com/CodeChain-io/rust-codechain-crypto.git", version = "0.1" } +codechain-crypto = { git = "https://github.com/CodeChain-io/rust-codechain-crypto.git", version = "0.2" } never-type = "0.1.0" parking_lot = "0.6.0" primitives = { git = "https://github.com/CodeChain-io/rust-codechain-primitives.git", version = "0.4" } diff --git a/keystore/Cargo.toml b/keystore/Cargo.toml index 8c091d432a..48212e89f7 100644 --- a/keystore/Cargo.toml +++ b/keystore/Cargo.toml @@ -17,7 +17,7 @@ serde_derive = "1.0" rustc-hex = "1.0" time = "0.1.34" parking_lot = "0.6.0" -codechain-crypto = { git = "https://github.com/CodeChain-io/rust-codechain-crypto.git", version = "0.1" } +codechain-crypto = { git = "https://github.com/CodeChain-io/rust-codechain-crypto.git", version = "0.2" } smallvec = "0.4" tempdir = "0.3" diff --git a/network/Cargo.toml b/network/Cargo.toml index c3c89e7502..3916a0f519 100644 --- a/network/Cargo.toml +++ b/network/Cargo.toml @@ -5,7 +5,7 @@ authors = ["CodeChain Team "] edition = "2018" [dependencies] -codechain-crypto = { git = "https://github.com/CodeChain-io/rust-codechain-crypto.git", version = "0.1" } +codechain-crypto = { git = "https://github.com/CodeChain-io/rust-codechain-crypto.git", version = "0.2" } codechain-io = { path = "../util/io" } codechain-key = { path = "../key" } codechain-logger = { path = "../util/logger" } diff --git a/network/src/p2p/connection/mod.rs b/network/src/p2p/connection/mod.rs index edacbc470f..4be1cc72e5 100644 --- a/network/src/p2p/connection/mod.rs +++ b/network/src/p2p/connection/mod.rs @@ -1,4 +1,4 @@ -// Copyright 2019 Kodebox, Inc. +// Copyright 2019-2020 Kodebox, Inc. // This file is part of CodeChain. // // This program is free software: you can redistribute it and/or modify @@ -19,7 +19,7 @@ mod incoming; mod message; mod outgoing; -use ccrypto::aes::SymmetricCipherError; +use ccrypto::error::SymmError; use rlp::DecoderError; use std::fmt; use std::io; @@ -36,7 +36,7 @@ use super::stream::Error as P2pStreamError; #[derive(Debug)] pub enum Error { - SymmetricCipher(SymmetricCipherError), + SymmetricCipher(SymmError), IoError(io::Error), Decoder(DecoderError), InvalidSign, @@ -78,8 +78,8 @@ impl From for Error { } } -impl From for Error { - fn from(err: SymmetricCipherError) -> Self { +impl From for Error { + fn from(err: SymmError) -> Self { Error::SymmetricCipher(err) } } diff --git a/network/src/p2p/handler.rs b/network/src/p2p/handler.rs index 025725e804..a5e440d9d2 100644 --- a/network/src/p2p/handler.rs +++ b/network/src/p2p/handler.rs @@ -1,4 +1,4 @@ -// Copyright 2018-2019 Kodebox, Inc. +// Copyright 2018-2020 Kodebox, Inc. // This file is part of CodeChain. // // This program is free software: you can redistribute it and/or modify @@ -23,7 +23,7 @@ use crate::client::Client; use crate::session::Session; use crate::stream::Stream; use crate::{FiltersControl, NodeId, RoutingTable, SocketAddr}; -use ccrypto::aes::SymmetricCipherError; +use ccrypto::error::SymmError; use cio::{IoChannel, IoContext, IoHandler, IoHandlerResult, IoManager, StreamToken, TimerToken}; use ckey::NetworkId; use finally_block::finally; @@ -1155,8 +1155,8 @@ impl IoHandler for Handler { } } -impl From for Error { - fn from(err: SymmetricCipherError) -> Self { +impl From for Error { + fn from(err: SymmError) -> Self { Error::SymmetricCipher(err) } } @@ -1186,7 +1186,7 @@ pub enum Message { #[derive(Debug)] enum Error { InvalidNode(NodeId), - SymmetricCipher(SymmetricCipherError), + SymmetricCipher(SymmError), } impl ::std::fmt::Display for Error { diff --git a/network/src/p2p/message/extension.rs b/network/src/p2p/message/extension.rs index bb74bc98ce..121dc1e92b 100644 --- a/network/src/p2p/message/extension.rs +++ b/network/src/p2p/message/extension.rs @@ -1,4 +1,4 @@ -// Copyright 2018-2019 Kodebox, Inc. +// Copyright 2018-2020 Kodebox, Inc. // This file is part of CodeChain. // // This program is free software: you can redistribute it and/or modify @@ -17,7 +17,8 @@ use super::ENCRYPTED_ID; use super::UNENCRYPTED_ID; use crate::session::Session; -use ccrypto::aes::{self, SymmetricCipherError}; +use ccrypto::aes; +use ccrypto::error::SymmError; use primitives::Bytes; use rlp::{Decodable, DecoderError, Encodable, Rlp, RlpStream}; use std::sync::Arc; @@ -47,7 +48,7 @@ impl Message { extension_name: String, unencrypted_data: &[u8], session: &Session, - ) -> Result { + ) -> Result { let encrypted = aes::encrypt(unencrypted_data, session.secret(), &session.nonce())?; Ok(Self::encrypted(extension_name, encrypted)) } @@ -73,7 +74,7 @@ impl Message { } } - pub fn unencrypted_data(&self, session: &Session) -> Result, SymmetricCipherError> { + pub fn unencrypted_data(&self, session: &Session) -> Result, SymmError> { match self { Message::Encrypted { encrypted, diff --git a/network/src/routing_table.rs b/network/src/routing_table.rs index dd8ed4d1b1..cb33539f57 100644 --- a/network/src/routing_table.rs +++ b/network/src/routing_table.rs @@ -1,4 +1,4 @@ -// Copyright 2018-2019 Kodebox, Inc. +// Copyright 2018-2020 Kodebox, Inc. // This file is part of CodeChain. // // This program is free software: you can redistribute it and/or modify @@ -16,7 +16,8 @@ use crate::session::{Nonce, Session}; use crate::SocketAddr; -use ccrypto::aes::{self, SymmetricCipherError}; +use ccrypto::aes; +use ccrypto::error::SymmError; use ckey::{exchange, Generator, KeyPair, Public, Random, Secret}; use parking_lot::{Mutex, RwLock}; use primitives::Bytes; @@ -506,8 +507,7 @@ impl RoutingTable { State::Establishing1(local_key_pair) => { let shared_secret = exchange(&remote_public, local_key_pair.private()) .map_err(|e| format!("Cannot exchange key: {:?}", e))?; - let nonce = decrypt_nonce(encrypted_nonce, &shared_secret) - .map_err(|e| format!("Cannot decrypt nonce: {:?}", e))?; + let nonce = decrypt_nonce(encrypted_nonce, &shared_secret)?; State::Established { local_key_pair: *local_key_pair, remote_public, @@ -529,8 +529,7 @@ impl RoutingTable { )) } debug_assert_eq!(*shared_secret, exchange(&remote_public, local_key_pair.private()).unwrap()); - let nonce = decrypt_nonce(encrypted_nonce, &shared_secret) - .map_err(|e| format!("Cannot decrypt nonce: {:?}", e))?; + let nonce = decrypt_nonce(encrypted_nonce, &shared_secret)?; State::Established { local_key_pair: *local_key_pair, remote_public, @@ -618,19 +617,23 @@ impl RoutingTable { } } -fn decrypt_nonce(encrypted_bytes: &[u8], shared_secret: &Secret) -> Result { +fn decrypt_nonce(encrypted_bytes: &[u8], shared_secret: &Secret) -> Result { let iv = 0; // FIXME: Use proper iv - let unecrypted = aes::decrypt(encrypted_bytes, shared_secret, &iv)?; + let unecrypted = + aes::decrypt(encrypted_bytes, shared_secret, &iv).map_err(|e| format!("Cannot decrypt nonce: {:?}", e))?; debug_assert_eq!(std::mem::size_of::(), 16); if unecrypted.len() != 16 { - return Err(SymmetricCipherError::InvalidLength) // FIXME + return Err(format!( + "Cannot decrpyt nonce: 16 length bytes expected but, {} length bytes received", + unecrypted.len() + )) // FIXME } let mut nonce_bytes = [0u8; 16]; nonce_bytes.copy_from_slice(&unecrypted); Ok(Nonce::from_be_bytes(nonce_bytes)) } -fn encrypt_nonce(nonce: Nonce, shared_secret: &Secret) -> Result { +fn encrypt_nonce(nonce: Nonce, shared_secret: &Secret) -> Result { let iv = 0; // FIXME: Use proper iv Ok(aes::encrypt(&nonce.to_be_bytes(), shared_secret, &iv)?) } diff --git a/network/src/session/session.rs b/network/src/session/session.rs index 21b4993a3e..1f3967dc06 100644 --- a/network/src/session/session.rs +++ b/network/src/session/session.rs @@ -1,4 +1,4 @@ -// Copyright 2018-2019 Kodebox, Inc. +// Copyright 2018-2020 Kodebox, Inc. // This file is part of CodeChain. // // This program is free software: you can redistribute it and/or modify @@ -15,7 +15,8 @@ // along with this program. If not, see . use super::Nonce; -use ccrypto::aes::{self, SymmetricCipherError}; +use ccrypto::aes; +use ccrypto::error::SymmError; use ccrypto::Blake; use ckey::Secret; use primitives::H256; @@ -26,8 +27,6 @@ pub struct Session { nonce: Nonce, } -type Error = SymmetricCipherError; - impl Session { pub fn new_with_zero_nonce(secret: Secret) -> Self { Self::new(secret, 0) @@ -52,11 +51,11 @@ impl Session { self.nonce } - pub fn encrypt(&self, data: &[u8]) -> Result, Error> { + pub fn encrypt(&self, data: &[u8]) -> Result, SymmError> { Ok(aes::encrypt(&data, &self.secret, &self.nonce())?) } - pub fn decrypt(&self, data: &[u8]) -> Result, Error> { + pub fn decrypt(&self, data: &[u8]) -> Result, SymmError> { Ok(aes::decrypt(&data, &self.secret, &self.nonce())?) } diff --git a/rpc/Cargo.toml b/rpc/Cargo.toml index aea4fc5467..f71ebdd4f9 100644 --- a/rpc/Cargo.toml +++ b/rpc/Cargo.toml @@ -9,7 +9,7 @@ edition = "2018" [dependencies] cidr = "0.0.4" codechain-core = { path = "../core" } -codechain-crypto = { git = "https://github.com/CodeChain-io/rust-codechain-crypto.git", version = "0.1" } +codechain-crypto = { git = "https://github.com/CodeChain-io/rust-codechain-crypto.git", version = "0.2" } codechain-json = { path = "../json" } codechain-key = { path = "../key" } codechain-keystore = { path = "../keystore" } diff --git a/state/Cargo.toml b/state/Cargo.toml index 6124dd69d5..0ab2a58d2c 100644 --- a/state/Cargo.toml +++ b/state/Cargo.toml @@ -5,8 +5,8 @@ authors = ["CodeChain Team "] edition = "2018" [dependencies] -codechain-crypto = { git = "https://github.com/CodeChain-io/rust-codechain-crypto.git", version = "0.1" } -codechain-db = { git = "https://github.com/CodeChain-io/rust-codechain-db.git", version = "0.1" } +codechain-crypto = { git = "https://github.com/CodeChain-io/rust-codechain-crypto.git", version = "0.2" } +codechain-db = { git = "https://github.com/CodeChain-io/rust-codechain-db.git", version = "0.2" } codechain-logger = { path = "../util/logger" } codechain-key = { path = "../key" } codechain-types = { path = "../types" } @@ -15,7 +15,7 @@ kvdb = "0.1" kvdb-memorydb = "0.1" log = "0.4.6" lru-cache = "0.1.1" -merkle-trie = { git = "https://github.com/CodeChain-io/rust-merkle-trie.git", version = "0.1" } +merkle-trie = { git = "https://github.com/CodeChain-io/rust-merkle-trie.git", version = "0.4" } parking_lot = "0.6.0" primitives = { git = "https://github.com/CodeChain-io/rust-codechain-primitives.git", version = "0.4" } rlp = { git = "https://github.com/CodeChain-io/rlp.git", version = "0.4" } diff --git a/stratum/Cargo.toml b/stratum/Cargo.toml index 5b8ff7136c..8c162d6018 100644 --- a/stratum/Cargo.toml +++ b/stratum/Cargo.toml @@ -7,7 +7,7 @@ authors = ["Parity Technologies ", "CodeChain Team "] edition = "2018" [dependencies] -codechain-crypto = { git = "https://github.com/CodeChain-io/rust-codechain-crypto.git", version = "0.1" } +codechain-crypto = { git = "https://github.com/CodeChain-io/rust-codechain-crypto.git", version = "0.2" } codechain-json = { path = "../json" } codechain-key = { path = "../key" } primitives = { git = "https://github.com/CodeChain-io/rust-codechain-primitives.git", version = "0.4" } diff --git a/vm/Cargo.toml b/vm/Cargo.toml index c3ee936994..71514e49ab 100644 --- a/vm/Cargo.toml +++ b/vm/Cargo.toml @@ -7,7 +7,7 @@ edition = "2018" [lib] [dependencies] -codechain-crypto = { git = "https://github.com/CodeChain-io/rust-codechain-crypto.git", version = "0.1" } +codechain-crypto = { git = "https://github.com/CodeChain-io/rust-codechain-crypto.git", version = "0.2" } codechain-key = { path = "../key" } codechain-types = { path = "../types" } primitives = { git = "https://github.com/CodeChain-io/rust-codechain-primitives.git", version = "0.4" } From 682abb359469cadb62a3ee3c6d7175376913071f Mon Sep 17 00:00:00 2001 From: Byeongjee Kang Date: Mon, 10 Feb 2020 17:49:16 +0900 Subject: [PATCH 17/55] Fix typo --- network/src/p2p/message/extension.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/network/src/p2p/message/extension.rs b/network/src/p2p/message/extension.rs index 121dc1e92b..5d3d7e0fce 100644 --- a/network/src/p2p/message/extension.rs +++ b/network/src/p2p/message/extension.rs @@ -125,7 +125,7 @@ impl Decodable for Message { let item_count = rlp.item_count()?; if item_count != 3 { return Err(DecoderError::RlpInvalidLength { - expected: 5, + expected: 3, got: item_count, }) } From a806f3ab69b8d42e7e88cb235e08bd05baeeb491 Mon Sep 17 00:00:00 2001 From: Byeongjee Kang Date: Tue, 18 Feb 2020 10:49:04 +0900 Subject: [PATCH 18/55] Rename double vote variable Some DoubleVote type variables should be renamed for consistency. --- core/src/consensus/tendermint/worker.rs | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/core/src/consensus/tendermint/worker.rs b/core/src/consensus/tendermint/worker.rs index 763250873e..6aaed11267 100644 --- a/core/src/consensus/tendermint/worker.rs +++ b/core/src/consensus/tendermint/worker.rs @@ -1432,9 +1432,9 @@ impl Worker { self.votes_received.set(vote_index); } - if let Err(double) = self.votes.collect(message.clone()) { - cerror!(ENGINE, "Double vote found {:?}", double); - self.report_double_vote(&double); + if let Err(double_vote) = self.votes.collect(message.clone()) { + cerror!(ENGINE, "Double vote found {:?}", double_vote); + self.report_double_vote(&double_vote); return Err(EngineError::DoubleVote(sender)) } ctrace!(ENGINE, "Handling a valid {:?} from {}.", message, sender); @@ -1821,9 +1821,9 @@ impl Worker { ); } - if let Err(double) = self.votes.collect(message) { - cerror!(ENGINE, "Double Vote found {:?}", double); - self.report_double_vote(&double); + if let Err(double_vote) = self.votes.collect(message) { + cerror!(ENGINE, "Double Vote found {:?}", double_vote); + self.report_double_vote(&double_vote); return None } } From 6d595141e1f2d9974b65a630a1eb87c771a659c8 Mon Sep 17 00:00:00 2001 From: Byeongjee Kang Date: Tue, 18 Feb 2020 10:55:03 +0900 Subject: [PATCH 19/55] Report double votes found in commit messages --- core/src/consensus/tendermint/worker.rs | 2 ++ 1 file changed, 2 insertions(+) diff --git a/core/src/consensus/tendermint/worker.rs b/core/src/consensus/tendermint/worker.rs index 6aaed11267..fb399d075e 100644 --- a/core/src/consensus/tendermint/worker.rs +++ b/core/src/consensus/tendermint/worker.rs @@ -956,6 +956,7 @@ impl Worker { if !self.votes.is_old_or_known(&message) { if let Err(double_vote) = self.votes.collect(message) { cerror!(ENGINE, "Double vote found on_commit_message: {:?}", double_vote); + self.report_double_vote(&double_vote); } } } @@ -2162,6 +2163,7 @@ impl Worker { if !self.votes.is_old_or_known(&vote) { if let Err(double_vote) = self.votes.collect(vote) { cerror!(ENGINE, "Double vote found on_commit_message: {:?}", double_vote); + self.report_double_vote(&double_vote); } } } From 94f17d8cd0bf64f6dd9815931635f779fee110b1 Mon Sep 17 00:00:00 2001 From: Seonpyo Kim Date: Mon, 2 Mar 2020 21:14:05 +0900 Subject: [PATCH 20/55] Fix typo in test helper's constants --- test/src/e2e/unwrap.test.ts | 6 +++--- test/src/e2e/verification.test.ts | 4 ++-- test/src/e2e/wrap.test.ts | 12 ++++++------ test/src/helper/constants.ts | 4 ++-- 4 files changed, 13 insertions(+), 13 deletions(-) diff --git a/test/src/e2e/unwrap.test.ts b/test/src/e2e/unwrap.test.ts index e5a1db6127..65d3b33276 100644 --- a/test/src/e2e/unwrap.test.ts +++ b/test/src/e2e/unwrap.test.ts @@ -25,7 +25,7 @@ import { import "mocha"; import { aliceAddress, - faucetAccointId, + faucetAccountId, faucetAddress, faucetSecret } from "../helper/constants"; @@ -50,7 +50,7 @@ describe("Unwrap CCC", function() { shardId: 0, recipient, quantity, - payer: PlatformAddress.fromAccountId(faucetAccointId, { + payer: PlatformAddress.fromAccountId(faucetAccountId, { networkId: "tc" }) }) @@ -107,7 +107,7 @@ describe("Unwrap CCC", function() { shardId: 0, recipient, quantity, - payer: PlatformAddress.fromAccountId(faucetAccointId, { + payer: PlatformAddress.fromAccountId(faucetAccountId, { networkId: "tc" }) }) diff --git a/test/src/e2e/verification.test.ts b/test/src/e2e/verification.test.ts index 8e78b9a00a..85f51c5039 100644 --- a/test/src/e2e/verification.test.ts +++ b/test/src/e2e/verification.test.ts @@ -24,7 +24,7 @@ import { import "mocha"; import { aliceAddress, - faucetAccointId, + faucetAccountId, faucetAddress, faucetSecret } from "../helper/constants"; @@ -680,7 +680,7 @@ describe("solo - 1 node", function() { shardId: 0, recipient, quantity: 10, - payer: PlatformAddress.fromAccountId(faucetAccointId, { + payer: PlatformAddress.fromAccountId(faucetAccountId, { networkId: "tc" }) }) diff --git a/test/src/e2e/wrap.test.ts b/test/src/e2e/wrap.test.ts index a8530c582e..de94f02fce 100644 --- a/test/src/e2e/wrap.test.ts +++ b/test/src/e2e/wrap.test.ts @@ -20,7 +20,7 @@ chai.use(chaiAsPromised); import { H160, PlatformAddress } from "codechain-primitives"; import "mocha"; import { - faucetAccointId, + faucetAccountId, faucetAddress, faucetSecret } from "../helper/constants"; @@ -44,7 +44,7 @@ describe("WrapCCC", function() { shardId: 0, recipient, quantity: amount, - payer: PlatformAddress.fromAccountId(faucetAccointId, { + payer: PlatformAddress.fromAccountId(faucetAccountId, { networkId: "tc" }) }) @@ -71,7 +71,7 @@ describe("WrapCCC", function() { shardId: 0, recipient, quantity: 0, - payer: PlatformAddress.fromAccountId(faucetAccointId, { + payer: PlatformAddress.fromAccountId(faucetAccountId, { networkId: "tc" }) }) @@ -95,7 +95,7 @@ describe("WrapCCC", function() { shardId, recipient: await node.createP2PKHBurnAddress(), quantity: 30, - payer: PlatformAddress.fromAccountId(faucetAccointId, { + payer: PlatformAddress.fromAccountId(faucetAccountId, { networkId: "tc" }) }); @@ -159,7 +159,7 @@ describe("WrapCCC", function() { shardId: 0, recipient: await node.createP2PKHBurnAddress(), quantity: 30, - payer: PlatformAddress.fromAccountId(faucetAccointId, { + payer: PlatformAddress.fromAccountId(faucetAccountId, { networkId: "tc" }) }); @@ -203,7 +203,7 @@ describe("WrapCCC", function() { shardId: 0, recipient: await node.createP2PKHBurnAddress(), quantity: 30, - payer: PlatformAddress.fromAccountId(faucetAccointId, { + payer: PlatformAddress.fromAccountId(faucetAccountId, { networkId: "tc" }) }); diff --git a/test/src/helper/constants.ts b/test/src/helper/constants.ts index 8f896b97f0..80af6a2476 100644 --- a/test/src/helper/constants.ts +++ b/test/src/helper/constants.ts @@ -18,9 +18,9 @@ import { SDK } from "codechain-sdk"; export const faucetSecret = "ede1d4ccb4ec9a8bbbae9a13db3f4a7b56ea04189be86ac3a6a439d9a0a1addd"; -export const faucetAccointId = SDK.util.getAccountIdFromPrivate(faucetSecret); // 6fe64ffa3a46c074226457c90ccb32dc06ccced1 +export const faucetAccountId = SDK.util.getAccountIdFromPrivate(faucetSecret); // 6fe64ffa3a46c074226457c90ccb32dc06ccced1 export const faucetAddress = SDK.Core.classes.PlatformAddress.fromAccountId( - faucetAccointId, + faucetAccountId, { networkId: "tc" } ); // tccq9h7vnl68frvqapzv3tujrxtxtwqdnxw6yamrrgd From d0d6ff03dd49305f652d24724a8689be1b65ead2 Mon Sep 17 00:00:00 2001 From: Byeongjee Kang Date: Thu, 12 Mar 2020 14:37:19 +0900 Subject: [PATCH 21/55] Assign unbound port numbers in test instances Port numbers assigned to test CodeChain instances should be unbound. If the port is already in use, the test will fail, which is not an intended behavior. --- test/package.json | 1 + test/src/helper/spawn.ts | 26 +++++++++++++++++--------- test/yarn.lock | 5 +++++ 3 files changed, 23 insertions(+), 9 deletions(-) diff --git a/test/package.json b/test/package.json index 6f23b156b3..34664680f3 100644 --- a/test/package.json +++ b/test/package.json @@ -50,6 +50,7 @@ "codechain-sdk": "https://github.com/MSNTCS/codechain-sdk-js#getPendingTransactions", "codechain-stakeholder-sdk": "^2.0.0", "elliptic": "^6.5.3", + "get-port": "^5.1.1", "lodash": "^4.17.19", "mkdirp": "^0.5.1", "ncp": "^2.0.0", diff --git a/test/src/helper/spawn.ts b/test/src/helper/spawn.ts index 4b2eb4bc95..b8c7c63a8f 100644 --- a/test/src/helper/spawn.ts +++ b/test/src/helper/spawn.ts @@ -40,6 +40,8 @@ import { createInterface as createReadline, ReadLine } from "readline"; import { faucetAddress, faucetSecret } from "./constants"; import { wait } from "./promise"; +const getPort = require("get-port"); + const projectRoot = `${__dirname}/../../..`; export type SchemeFilepath = string; @@ -77,7 +79,6 @@ export interface Signer { export default class CodeChain { private static idCounter = 0; private readonly _id: number; - private readonly _sdk: SDK; private readonly _localKeyStorePath: string; private readonly _dbPath: string; private readonly _ipcPath: string; @@ -85,9 +86,11 @@ export default class CodeChain { private readonly _logFile: string; private readonly _logPath: string; private readonly _chain: ChainType; - private readonly _rpcPort: number; private readonly argv: string[]; private readonly env: { [key: string]: string }; + private _sdk?: SDK; + private _port?: number; + private _rpcPort?: number; private process: ProcessState; private restarts: number; private _keepLogs: boolean; @@ -99,7 +102,7 @@ export default class CodeChain { } public get sdk(): SDK { if (this.process.state === "running") { - return this._sdk; + return this._sdk!; } else { throw new ProcessStateError(this.id, this.process); } @@ -123,10 +126,10 @@ export default class CodeChain { return this._logPath; } public get rpcPort(): number { - return this._rpcPort; + return this._rpcPort!; } public get port(): number { - return 3486 + this.id; + return this._port!; } public get secretKey(): number { return 1 + this.id; @@ -160,9 +163,6 @@ export default class CodeChain { const { chain, argv, additionalKeysPath, env } = options; this._id = CodeChain.idCounter++; - const { rpcPort = 8081 + this.id } = options; - this._rpcPort = rpcPort; - mkdirp.sync(`${projectRoot}/db/`); mkdirp.sync(`${projectRoot}/keys/`); mkdirp.sync(`${projectRoot}/test/log/`); @@ -188,7 +188,6 @@ export default class CodeChain { this.id }.log`; this._logPath = `${projectRoot}/test/log/${this._logFile}`; - this._sdk = new SDK({ server: `http://localhost:${this.rpcPort}` }); this._chain = chain || "solo"; this.argv = argv || []; this.env = env || {}; @@ -207,6 +206,10 @@ export default class CodeChain { throw new ProcessStateError(this.id, this.process); } + await this.initialize_port(); + + this._sdk = new SDK({ server: `http://localhost:${this.rpcPort}` }); + const { argv = [], logLevel = "trace,mio=warn,tokio=warn,hyper=warn,timer=warn", @@ -871,4 +874,9 @@ export default class CodeChain { } } } + + private async initialize_port() { + this._port = await getPort({ port: this.id + 3486 }); + this._rpcPort = await getPort({ port: this.id + 8081 }); + } } diff --git a/test/yarn.lock b/test/yarn.lock index 6c35a4396c..cc9f3cd613 100644 --- a/test/yarn.lock +++ b/test/yarn.lock @@ -778,6 +778,11 @@ get-func-name@^2.0.0: resolved "https://registry.yarnpkg.com/get-func-name/-/get-func-name-2.0.0.tgz#ead774abee72e20409433a066366023dd6887a41" integrity sha1-6td0q+5y4gQJQzoGY2YCPdaIekE= +get-port@^5.1.1: + version "5.1.1" + resolved "https://registry.yarnpkg.com/get-port/-/get-port-5.1.1.tgz#0469ed07563479de6efb986baf053dcd7d4e3193" + integrity sha512-g/Q1aTSDOxFpchXC4i8ZWvxA1lnPqx/JHqcpIw0/LX9T8x/GBbi6YnlN5nhaKIFkT8oFsscUKgDJYxfwfS6QsQ== + getpass@^0.1.1: version "0.1.7" resolved "https://registry.yarnpkg.com/getpass/-/getpass-0.1.7.tgz#5eff8e3e684d569ae4cb2b1282604e8ba62149fa" From 94c343d30ebe17b54309059eae4d31ea5630228f Mon Sep 17 00:00:00 2001 From: Byeongjee Kang Date: Tue, 17 Mar 2020 17:13:20 +0900 Subject: [PATCH 22/55] Fix a wrong argument name --- core/src/blockchain/body_db.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/core/src/blockchain/body_db.rs b/core/src/blockchain/body_db.rs index 38978b1227..7b50e40663 100644 --- a/core/src/blockchain/body_db.rs +++ b/core/src/blockchain/body_db.rs @@ -346,9 +346,9 @@ fn tx_hash_and_address_entries( fn tracker_and_addresses_entries( block_hash: BlockHash, - tx_hashes: impl IntoIterator, + transactions: impl IntoIterator, ) -> impl Iterator { - tx_hashes.into_iter().enumerate().filter_map(move |(index, tx)| { + transactions.into_iter().enumerate().filter_map(move |(index, tx)| { tx.tracker().map(|tracker| { ( tracker, From c745164379ddc7b6800453c4b3d31b82dc4e86e2 Mon Sep 17 00:00:00 2001 From: Seulgi Kim Date: Sat, 14 Mar 2020 00:12:53 +0900 Subject: [PATCH 23/55] Remove ChainNotify::transactions_received() This is not used. --- core/src/client/chain_notify.rs | 8 +------- core/src/client/client.rs | 15 +++------------ core/src/client/mod.rs | 3 +-- core/src/client/test_client.rs | 3 +-- core/src/service.rs | 7 +++---- sync/src/transaction/extension.rs | 1 - 6 files changed, 9 insertions(+), 28 deletions(-) diff --git a/core/src/client/chain_notify.rs b/core/src/client/chain_notify.rs index a4868a7571..cd964773a5 100644 --- a/core/src/client/chain_notify.rs +++ b/core/src/client/chain_notify.rs @@ -14,8 +14,7 @@ // You should have received a copy of the GNU Affero General Public License // along with this program. If not, see . -use cnetwork::NodeId; -use ctypes::{BlockHash, TxHash}; +use ctypes::BlockHash; /// Represents what has to be handled by actor listening to chain events pub trait ChainNotify: Send + Sync { @@ -43,9 +42,4 @@ pub trait ChainNotify: Send + Sync { ) { // does nothing by default } - - /// fires when new transactions are received from a peer - fn transactions_received(&self, _hashes: Vec, _peer_id: NodeId) { - // does nothing by default - } } diff --git a/core/src/client/client.rs b/core/src/client/client.rs index 5185274f18..1b3e0e80d0 100644 --- a/core/src/client/client.rs +++ b/core/src/client/client.rs @@ -35,7 +35,6 @@ use crate::MemPoolMinFees; use cdb::{new_journaldb, Algorithm, AsHashDB, DatabaseError}; use cio::IoChannel; use ckey::{Address, NetworkId, PlatformAddress, Public}; -use cnetwork::NodeId; use cstate::{ ActionHandler, AssetScheme, FindActionHandler, OwnedAsset, StateDB, StateResult, Text, TopLevelState, TopStateView, }; @@ -139,12 +138,6 @@ impl Client { self.notify.write().push(target); } - pub fn transactions_received(&self, hashes: &[TxHash], peer_id: NodeId) { - self.notify(|notify| { - notify.transactions_received(hashes.to_vec(), peer_id); - }); - } - pub fn new_blocks( &self, imported: &[BlockHash], @@ -237,13 +230,11 @@ impl Client { } /// Import transactions from the IO queue - pub fn import_queued_transactions(&self, transactions: &[Bytes], peer_id: NodeId) -> usize { + pub fn import_queued_transactions(&self, transactions: &[Bytes]) -> usize { ctrace!(EXTERNAL_TX, "Importing queued"); self.queue_transactions.fetch_sub(transactions.len(), AtomicOrdering::SeqCst); let transactions: Vec = transactions.iter().filter_map(|bytes| Rlp::new(bytes).as_val().ok()).collect(); - let hashes: Vec<_> = transactions.iter().map(UnverifiedTransaction::hash).collect(); - self.transactions_received(&hashes, peer_id); let results = self.importer.miner.import_external_transactions(self, transactions); results.len() } @@ -720,14 +711,14 @@ impl BlockChainClient for Client { Ok(()) } - fn queue_transactions(&self, transactions: Vec, peer_id: NodeId) { + fn queue_transactions(&self, transactions: Vec) { let queue_size = self.queue_transactions.load(AtomicOrdering::Relaxed); ctrace!(EXTERNAL_TX, "Queue size: {}", queue_size); if queue_size > MAX_MEM_POOL_SIZE { cwarn!(EXTERNAL_TX, "Ignoring {} transactions: queue is full", transactions.len()); } else { let len = transactions.len(); - match self.io_channel.lock().send(ClientIoMessage::NewTransactions(transactions, peer_id)) { + match self.io_channel.lock().send(ClientIoMessage::NewTransactions(transactions)) { Ok(_) => { self.queue_transactions.fetch_add(len, AtomicOrdering::SeqCst); } diff --git a/core/src/client/mod.rs b/core/src/client/mod.rs index 54717354fd..09dedcd84b 100644 --- a/core/src/client/mod.rs +++ b/core/src/client/mod.rs @@ -37,7 +37,6 @@ use crate::transaction::{LocalizedTransaction, PendingSignedTransactions, Signed use crate::types::{BlockId, BlockStatus, TransactionId, VerificationQueueInfo as BlockQueueInfo}; use cdb::DatabaseError; use ckey::{Address, NetworkId, PlatformAddress, Public}; -use cnetwork::NodeId; use cstate::{AssetScheme, FindActionHandler, OwnedAsset, StateResult, Text, TopLevelState, TopStateView}; use ctypes::transaction::{AssetTransferInput, PartialHashing, ShardTransaction}; use ctypes::{BlockHash, BlockNumber, CommonParams, ShardId, Tracker, TxHash}; @@ -218,7 +217,7 @@ pub trait BlockChainClient: Sync + Send + AccountData + BlockChainTrait + Import fn queue_own_transaction(&self, transaction: SignedTransaction) -> Result<(), GenericError>; /// Queue transactions for importing. - fn queue_transactions(&self, transactions: Vec, peer_id: NodeId); + fn queue_transactions(&self, transactions: Vec); /// Delete all pending transactions. fn delete_all_pending_transactions(&self); diff --git a/core/src/client/test_client.rs b/core/src/client/test_client.rs index ad27928a2b..448241532b 100644 --- a/core/src/client/test_client.rs +++ b/core/src/client/test_client.rs @@ -47,7 +47,6 @@ use crate::transaction::{LocalizedTransaction, PendingSignedTransactions, Signed use crate::types::{BlockId, TransactionId, VerificationQueueInfo as QueueInfo}; use cdb; use ckey::{public_to_address, Address, Generator, KeyPair, NetworkId, PlatformAddress, Private, Public, Random}; -use cnetwork::NodeId; use cstate::tests::helpers::empty_top_state; use cstate::{FindActionHandler, StateDB, TopLevelState}; use ctimer::{TimeoutHandler, TimerToken}; @@ -540,7 +539,7 @@ impl BlockChainClient for TestBlockChainClient { Ok(()) } - fn queue_transactions(&self, transactions: Vec, _peer_id: NodeId) { + fn queue_transactions(&self, transactions: Vec) { // import right here let transactions = transactions.into_iter().filter_map(|bytes| Rlp::new(&bytes).as_val().ok()).collect(); self.miner.import_external_transactions(self, transactions); diff --git a/core/src/service.rs b/core/src/service.rs index cb75c7d7f5..59347bcb66 100644 --- a/core/src/service.rs +++ b/core/src/service.rs @@ -20,7 +20,6 @@ use crate::miner::Miner; use crate::scheme::Scheme; use crate::BlockId; use cio::{IoContext, IoHandler, IoHandlerResult, IoService}; -use cnetwork::NodeId; use ctimer::TimerApi; use ctypes::BlockHash; use kvdb::KeyValueDB; @@ -71,7 +70,7 @@ pub enum ClientIoMessage { /// A header is ready HeaderVerified, /// New transaction RLPs are ready to be imported - NewTransactions(Vec, NodeId), + NewTransactions(Vec), /// Block generation is required NewBlockRequired { parent_block: BlockId, @@ -96,8 +95,8 @@ impl IoHandler for ClientIoHandler { ClientIoMessage::HeaderVerified => { self.client.import_verified_headers(); } - ClientIoMessage::NewTransactions(transactions, peer_id) => { - self.client.import_queued_transactions(&transactions, peer_id); + ClientIoMessage::NewTransactions(transactions) => { + self.client.import_queued_transactions(&transactions); } ClientIoMessage::NewBlockRequired { parent_block, diff --git a/sync/src/transaction/extension.rs b/sync/src/transaction/extension.rs index e412a9e17e..76f8369286 100644 --- a/sync/src/transaction/extension.rs +++ b/sync/src/transaction/extension.rs @@ -111,7 +111,6 @@ impl NetworkExtension for Extension { self.client.queue_transactions( transactions.iter().map(|unverified| unverified.rlp_bytes().to_vec()).collect(), - *token, ); if let Some(peer) = self.peers.get_mut(token) { let transactions: Vec<_> = transactions From 532becbc0ead78342ead59e5853c47de6c9d658d Mon Sep 17 00:00:00 2001 From: Byeongjee Kang Date: Mon, 30 Mar 2020 11:48:21 +0900 Subject: [PATCH 24/55] Fix wrong debug message --- core/src/miner/miner.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/core/src/miner/miner.rs b/core/src/miner/miner.rs index 203ab5d55b..1f463583a4 100644 --- a/core/src/miner/miner.rs +++ b/core/src/miner/miner.rs @@ -437,7 +437,7 @@ impl Miner { } _ => {} } - cdebug!(MINER, "Rejected transaction {:?} with invalid signature: {:?}", hash, e); + cdebug!(MINER, "Rejected transaction {:?} with error {:?}", hash, e); e })?; From 2a1411d7f42a74a0b5ef5638fd60a9709ad1bd0b Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Mon, 30 Mar 2020 14:16:26 +0900 Subject: [PATCH 25/55] Change the error message that CodeChain prints when account is not unlocked The previous error message was printing the wrong information that the user should specify the password-path. Although a user used the --password-path option, if the engine_signer's key is not included in the keys_path directory, or its password was not included in the password file, the same error will be thrown. --- codechain/run_node.rs | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/codechain/run_node.rs b/codechain/run_node.rs index c5f2a32115..b9c8391e94 100644 --- a/codechain/run_node.rs +++ b/codechain/run_node.rs @@ -145,8 +145,7 @@ fn new_miner( Some(ref engine_signer) => match miner.set_author((*engine_signer).into_address()) { Err(AccountProviderError::NotUnlocked) => { return Err( - "The account is not unlocked. Specify the password path using --password-path option." - .to_string(), + format!("The account {} is not unlocked. The key file should exist in the keys_path directory, and the account's password should exist in the password_path file.", engine_signer) ) } Err(e) => return Err(format!("{}", e)), From a764f43a9fe9789f9e64ad0cb64bc34ab0b9e078 Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Wed, 8 Apr 2020 15:01:45 +0900 Subject: [PATCH 26/55] Disconnect a socket If CodeChain meets EOF while reading the socket --- network/src/p2p/handler.rs | 33 +++++++++++++++++++++++++++++---- network/src/stream.rs | 8 +++++++- 2 files changed, 36 insertions(+), 5 deletions(-) diff --git a/network/src/p2p/handler.rs b/network/src/p2p/handler.rs index a5e440d9d2..6f58f93af5 100644 --- a/network/src/p2p/handler.rs +++ b/network/src/p2p/handler.rs @@ -20,6 +20,7 @@ use super::connection::{ use super::listener::Listener; use super::{NegotiationMessage, NetworkMessage}; use crate::client::Client; +use crate::p2p::connection::Error as P2PConnectionError; use crate::session::Session; use crate::stream::Stream; use crate::{FiltersControl, NodeId, RoutingTable, SocketAddr}; @@ -662,7 +663,13 @@ impl IoHandler for Handler { io.update_registration(stream_token); } }); - match con.receive()? { + let received = con.receive(); + if let Err(P2PConnectionError::IoError(ioerr)) = &received { + if ioerr.kind() == std::io::ErrorKind::ConnectionAborted { + io.deregister_stream(stream_token); + } + }; + match received? { Some(NetworkMessage::Extension(msg)) => { let remote_node_id = *self.remote_node_ids.read().get(&stream_token).unwrap_or_else(|| { unreachable!("Node id for {}:{} must exist", stream_token, con.peer_addr()) @@ -731,7 +738,13 @@ impl IoHandler for Handler { io.update_registration(stream_token); } }); - match con.receive()? { + let received = con.receive(); + if let Err(P2PConnectionError::IoError(ioerr)) = &received { + if ioerr.kind() == std::io::ErrorKind::ConnectionAborted { + io.deregister_stream(stream_token); + } + }; + match received? { Some(NetworkMessage::Extension(msg)) => { let remote_node_id = *self.remote_node_ids.read().get(&stream_token).unwrap_or_else(|| { unreachable!("Node id for {}:{} must exist", stream_token, con.peer_addr()) @@ -776,7 +789,13 @@ impl IoHandler for Handler { io.update_registration(stream_token); } }); - match con.receive()? { + let received = con.receive(); + if let Err(P2PConnectionError::IoError(ioerr)) = &received { + if ioerr.kind() == std::io::ErrorKind::ConnectionAborted { + io.deregister_stream(stream_token); + } + }; + match received? { Some(OutgoingMessage::Sync1 { initiator_pub_key, network_id, @@ -871,7 +890,13 @@ impl IoHandler for Handler { } }); let from = *con.peer_addr(); - match con.receive()? { + let received = con.receive(); + if let Err(P2PConnectionError::IoError(ioerr)) = &received { + if ioerr.kind() == std::io::ErrorKind::ConnectionAborted { + io.deregister_stream(stream_token); + } + }; + match received? { Some(IncomingMessage::Ack { recipient_pub_key, encrypted_nonce, diff --git a/network/src/stream.rs b/network/src/stream.rs index 6651def14a..ffe1f30edb 100644 --- a/network/src/stream.rs +++ b/network/src/stream.rs @@ -109,6 +109,9 @@ impl TryStream { assert!(read_size < len_of_len, "{} should be less than {}", read_size, len_of_len); if let Some(new_read_size) = self.stream.try_read(&mut bytes[(1 + read_size)..=len_of_len])? { + if new_read_size == 0 { + return Err(io::Error::new(io::ErrorKind::ConnectionAborted, "EOF")) + } read_size += new_read_size; }; if len_of_len == read_size { @@ -128,7 +131,7 @@ impl TryStream { if let Some(read_size) = self.stream.try_read(&mut bytes)? { if read_size == 0 { - return Ok(None) + return Err(io::Error::new(io::ErrorKind::ConnectionAborted, "EOF").into()) } debug_assert_eq!(1, read_size); if 0xf8 <= bytes[0] { @@ -184,6 +187,9 @@ impl TryStream { while remain_length != 0 { let to_be_read = ::std::cmp::min(remain_length, 1024); if let Some(read_size) = self.stream.try_read(&mut bytes[0..to_be_read])? { + if read_size == 0 { + return Err(io::Error::new(io::ErrorKind::ConnectionAborted, "EOF").into()) + } result.extend_from_slice(&bytes[..read_size]); debug_assert!(remain_length >= read_size); remain_length -= read_size; From d06eae211beeb07ff8bdeb759e93102a425b8165 Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Wed, 8 Apr 2020 18:07:10 +0900 Subject: [PATCH 27/55] Disconnect a connection if the send call returns BrokenPipe error --- network/src/p2p/handler.rs | 34 +++++++++++++++++++++++++++++----- 1 file changed, 29 insertions(+), 5 deletions(-) diff --git a/network/src/p2p/handler.rs b/network/src/p2p/handler.rs index 6f58f93af5..1f12b11749 100644 --- a/network/src/p2p/handler.rs +++ b/network/src/p2p/handler.rs @@ -933,32 +933,56 @@ impl IoHandler for Handler { Ok(()) } - fn stream_writable(&self, _io: &IoContext, stream: StreamToken) -> IoHandlerResult<()> { + fn stream_writable(&self, io: &IoContext, stream: StreamToken) -> IoHandlerResult<()> { match stream { FIRST_INBOUND..=LAST_INBOUND => { if let Some(con) = self.inbound_connections.write().get_mut(&stream) { - con.flush()?; + let flush_result = con.flush(); + if let Err(P2PConnectionError::IoError(io_error)) = &flush_result { + if io_error.kind() == std::io::ErrorKind::BrokenPipe { + io.deregister_stream(stream); + } + } + flush_result?; } else { cdebug!(NETWORK, "Invalid inbound token({}) on write", stream); } } FIRST_OUTBOUND..=LAST_OUTBOUND => { if let Some(con) = self.outbound_connections.write().get_mut(&stream) { - con.flush()?; + let flush_result = con.flush(); + if let Err(P2PConnectionError::IoError(io_error)) = &flush_result { + if io_error.kind() == std::io::ErrorKind::BrokenPipe { + io.deregister_stream(stream); + } + } + flush_result?; } else { cdebug!(NETWORK, "Invalid outbound token({}) on write", stream); } } FIRST_INCOMING..=LAST_INCOMING => { if let Some(con) = self.incoming_connections.write().get_mut(&stream) { - con.flush()?; + let flush_result = con.flush(); + if let Err(P2PConnectionError::IoError(io_error)) = &flush_result { + if io_error.kind() == std::io::ErrorKind::BrokenPipe { + io.deregister_stream(stream); + } + } + flush_result?; } else { cdebug!(NETWORK, "Invalid incoming token({}) on write", stream); } } FIRST_OUTGOING..=LAST_OUTGOING => { if let Some(con) = self.outgoing_connections.write().get_mut(&stream) { - con.flush()?; + let flush_result = con.flush(); + if let Err(P2PConnectionError::IoError(io_error)) = &flush_result { + if io_error.kind() == std::io::ErrorKind::BrokenPipe { + io.deregister_stream(stream); + } + } + flush_result?; } else { cdebug!(NETWORK, "Invalid outgoing token({}) on write", stream); } From a4ebd36c3312b981fc9fc65164915cbbc5a772f9 Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Thu, 9 Apr 2020 18:06:34 +0900 Subject: [PATCH 28/55] Remove unused dependencies in the sync module --- Cargo.lock | 2 -- sync/Cargo.toml | 2 -- sync/src/lib.rs | 3 --- 3 files changed, 7 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 9f8bd8707f..8e460ce469 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -653,13 +653,11 @@ dependencies = [ "log 0.4.6", "merkle-trie", "never-type", - "parking_lot 0.6.4", "primitives", "rand 0.6.1", "rlp", "snap", "tempfile", - "time", "token-generator", "trie-standardmap", ] diff --git a/sync/Cargo.toml b/sync/Cargo.toml index 55c1d28bbb..7d327b9d34 100644 --- a/sync/Cargo.toml +++ b/sync/Cargo.toml @@ -20,12 +20,10 @@ kvdb = "0.1" log = "0.4.6" merkle-trie = { git = "https://github.com/CodeChain-io/rust-merkle-trie.git", version = "0.4" } never-type = "0.1.0" -parking_lot = "0.6.0" primitives = { git = "https://github.com/CodeChain-io/rust-codechain-primitives.git", version = "0.4" } rand = "0.6.1" rlp = { git = "https://github.com/CodeChain-io/rlp.git", version = "0.4" } snap = "0.2" -time = "0.1" token-generator = "0.1.0" [dev-dependencies] diff --git a/sync/src/lib.rs b/sync/src/lib.rs index 8792691242..c3f52ea2ed 100644 --- a/sync/src/lib.rs +++ b/sync/src/lib.rs @@ -14,8 +14,6 @@ // You should have received a copy of the GNU Affero General Public License // along with this program. If not, see . -extern crate parking_lot; - extern crate codechain_core as ccore; extern crate codechain_db as cdb; #[macro_use] @@ -37,7 +35,6 @@ extern crate rlp; extern crate snap; #[cfg(test)] extern crate tempfile; -extern crate time; extern crate token_generator; #[cfg(test)] extern crate trie_standardmap; From 2b467c9ca77232191bcf0fb6641b92e184b8d978 Mon Sep 17 00:00:00 2001 From: Seulgi Kim Date: Sat, 4 Apr 2020 21:33:44 +0900 Subject: [PATCH 29/55] Remove unused methods from ConsensusEngine --- core/src/consensus/blake_pow/mod.rs | 4 -- core/src/consensus/cuckoo/mod.rs | 5 -- core/src/consensus/mod.rs | 3 - core/src/consensus/null_engine/mod.rs | 4 -- core/src/consensus/simple_poa/mod.rs | 10 --- core/src/consensus/solo/mod.rs | 4 -- core/src/consensus/tendermint/engine.rs | 5 -- core/src/consensus/tendermint/mod.rs | 93 +------------------------ 8 files changed, 1 insertion(+), 127 deletions(-) diff --git a/core/src/consensus/blake_pow/mod.rs b/core/src/consensus/blake_pow/mod.rs index 386dfa36bf..8df5d2c58e 100644 --- a/core/src/consensus/blake_pow/mod.rs +++ b/core/src/consensus/blake_pow/mod.rs @@ -83,10 +83,6 @@ impl BlakePoW { } impl ConsensusEngine for BlakePoW { - fn name(&self) -> &str { - "BlakePoW" - } - fn machine(&self) -> &CodeChainMachine { &self.machine } diff --git a/core/src/consensus/cuckoo/mod.rs b/core/src/consensus/cuckoo/mod.rs index 6aefe7c5e6..5e3dd243ee 100644 --- a/core/src/consensus/cuckoo/mod.rs +++ b/core/src/consensus/cuckoo/mod.rs @@ -89,10 +89,6 @@ impl Cuckoo { } impl ConsensusEngine for Cuckoo { - fn name(&self) -> &str { - "Cuckoo" - } - fn machine(&self) -> &CodeChainMachine { &self.machine } @@ -210,7 +206,6 @@ mod tests { fn has_valid_metadata() { let engine = Scheme::new_test_cuckoo().engine; - assert_eq!(engine.name(), "Cuckoo"); assert_eq!(engine.engine_type(), EngineType::PoW); } diff --git a/core/src/consensus/mod.rs b/core/src/consensus/mod.rs index fa9d338402..ed55ba6818 100644 --- a/core/src/consensus/mod.rs +++ b/core/src/consensus/mod.rs @@ -138,9 +138,6 @@ impl EngineType { /// A consensus mechanism for the chain. pub trait ConsensusEngine: Sync + Send { - /// The name of this engine. - fn name(&self) -> &str; - /// Get access to the underlying state machine. fn machine(&self) -> &CodeChainMachine; diff --git a/core/src/consensus/null_engine/mod.rs b/core/src/consensus/null_engine/mod.rs index cbd1a07bc7..9fba363cdf 100644 --- a/core/src/consensus/null_engine/mod.rs +++ b/core/src/consensus/null_engine/mod.rs @@ -42,10 +42,6 @@ impl NullEngine { } impl ConsensusEngine for NullEngine { - fn name(&self) -> &str { - "NullEngine" - } - fn machine(&self) -> &CodeChainMachine { &self.machine } diff --git a/core/src/consensus/simple_poa/mod.rs b/core/src/consensus/simple_poa/mod.rs index 4db084d9cf..75d08f543c 100644 --- a/core/src/consensus/simple_poa/mod.rs +++ b/core/src/consensus/simple_poa/mod.rs @@ -73,10 +73,6 @@ fn verify_external(header: &Header, validators: &dyn ValidatorSet) -> Result<(), } impl ConsensusEngine for SimplePoA { - fn name(&self) -> &str { - "SimplePoA" - } - fn machine(&self) -> &CodeChainMachine { &self.machine } @@ -159,12 +155,6 @@ mod tests { use super::*; - #[test] - fn has_valid_metadata() { - let engine = Scheme::new_test_simple_poa().engine; - assert!(!engine.name().is_empty()); - } - #[test] fn fail_to_verify_signature_when_seal_is_invalid() { let engine = Scheme::new_test_simple_poa().engine; diff --git a/core/src/consensus/solo/mod.rs b/core/src/consensus/solo/mod.rs index 69cead2f84..5faa74e6e1 100644 --- a/core/src/consensus/solo/mod.rs +++ b/core/src/consensus/solo/mod.rs @@ -61,10 +61,6 @@ impl Solo { } impl ConsensusEngine for Solo { - fn name(&self) -> &str { - "Solo" - } - fn machine(&self) -> &CodeChainMachine { &self.machine } diff --git a/core/src/consensus/tendermint/engine.rs b/core/src/consensus/tendermint/engine.rs index 6e15d3b5b9..b0b14505c6 100644 --- a/core/src/consensus/tendermint/engine.rs +++ b/core/src/consensus/tendermint/engine.rs @@ -53,10 +53,6 @@ struct WorkInfo { } impl ConsensusEngine for Tendermint { - fn name(&self) -> &str { - "Tendermint" - } - fn machine(&self) -> &CodeChainMachine { &self.machine.as_ref() } @@ -137,7 +133,6 @@ impl ConsensusEngine for Tendermint { self.inner.send(worker::Event::OnTimeout(token)).unwrap(); } - fn stop(&self) {} fn on_close_block( &self, diff --git a/core/src/consensus/tendermint/mod.rs b/core/src/consensus/tendermint/mod.rs index bf197086a2..c50b6f8d31 100644 --- a/core/src/consensus/tendermint/mod.rs +++ b/core/src/consensus/tendermint/mod.rs @@ -133,7 +133,7 @@ mod tests { use crate::account_provider::AccountProvider; use crate::block::{ClosedBlock, OpenBlock}; use crate::client::TestBlockChainClient; - use crate::consensus::{CodeChainEngine, EngineError, Seal}; + use crate::consensus::{CodeChainEngine, Seal}; use crate::error::BlockError; use crate::error::Error; use crate::scheme::Scheme; @@ -176,18 +176,6 @@ mod tests { addr } - #[test] - fn has_valid_metadata() { - use std::time::Duration; - let engine = Scheme::new_test_tendermint().engine; - let time_gap_params = TimeGapParams { - allowed_past_gap: Duration::from_millis(30000), - allowed_future_gap: Duration::from_millis(5000), - }; - engine.register_time_gap_config_to_worker(time_gap_params); - assert!(!engine.name().is_empty()); - } - #[test] #[ignore] // FIXME fn verification_fails_on_short_seal() { @@ -249,83 +237,4 @@ mod tests { println!("....."); assert!(engine.verify_block_external(&header).is_err()); } - - #[test] - #[ignore] // FIXME - fn seal_signatures_checking() { - let (spec, tap, c) = setup(); - let engine = spec.engine; - - let validator0 = insert_and_unlock(&tap, "0"); - let validator1 = insert_and_unlock(&tap, "1"); - let validator2 = insert_and_unlock(&tap, "2"); - let validator3 = insert_and_unlock(&tap, "3"); - - let block1_hash = c.add_block_with_author(Some(validator1), 1, 1); - - let mut header = Header::default(); - header.set_number(2); - let proposer = validator2; - header.set_author(proposer); - header.set_parent_hash(block1_hash); - - let vote_info = VoteOn { - step: VoteStep::new(1, 0, Step::Precommit), - block_hash: Some(*header.parent_hash()), - }; - let signature2 = tap.get_account(&proposer, None).unwrap().sign_schnorr(&vote_info.hash()).unwrap(); - - let seal = Seal::Tendermint { - prev_view: 0, - cur_view: 0, - precommits: vec![signature2], - precommit_bitset: BitSet::new_with_indices(&[2]), - } - .seal_fields() - .unwrap(); - header.set_seal(seal); - - // One good signature is not enough. - match engine.verify_block_external(&header) { - Err(Error::Engine(EngineError::BadSealFieldSize(_))) => {} - _ => panic!(), - } - - let voter = validator3; - let signature3 = tap.get_account(&voter, None).unwrap().sign_schnorr(&vote_info.hash()).unwrap(); - let voter = validator0; - let signature0 = tap.get_account(&voter, None).unwrap().sign_schnorr(&vote_info.hash()).unwrap(); - - let seal = Seal::Tendermint { - prev_view: 0, - cur_view: 0, - precommits: vec![signature0, signature2, signature3], - precommit_bitset: BitSet::new_with_indices(&[0, 2, 3]), - } - .seal_fields() - .unwrap(); - header.set_seal(seal); - - assert!(engine.verify_block_external(&header).is_ok()); - - let bad_voter = insert_and_unlock(&tap, "101"); - let bad_signature = tap.get_account(&bad_voter, None).unwrap().sign_schnorr(&vote_info.hash()).unwrap(); - - let seal = Seal::Tendermint { - prev_view: 0, - cur_view: 0, - precommits: vec![signature0, signature2, bad_signature], - precommit_bitset: BitSet::new_with_indices(&[0, 2, 3]), - } - .seal_fields() - .unwrap(); - header.set_seal(seal); - - // Two good and one bad signature. - match engine.verify_block_external(&header) { - Err(Error::Engine(EngineError::BlockNotAuthorized(_))) => {} - _ => panic!(), - }; - engine.stop(); - } } From a59449c1ace73b6a17f1ca8a434a2e13a33b48a3 Mon Sep 17 00:00:00 2001 From: Seulgi Kim Date: Wed, 8 Apr 2020 17:15:22 +0900 Subject: [PATCH 30/55] Remove unused functions --- core/src/miner/mem_pool.rs | 11 ----------- core/src/tests/helpers.rs | 13 ------------- state/src/cache/top_cache.rs | 4 ---- 3 files changed, 28 deletions(-) diff --git a/core/src/miner/mem_pool.rs b/core/src/miner/mem_pool.rs index 329f26094b..bf2a4f0d1e 100644 --- a/core/src/miner/mem_pool.rs +++ b/core/src/miner/mem_pool.rs @@ -868,17 +868,6 @@ impl MemPool { Ok(()) } - /// Removes all elements (in any state) from the pool - #[allow(dead_code)] - pub fn clear(&mut self) { - self.current.clear(); - self.future.clear(); - self.by_signer_public.clear(); - self.by_hash.clear(); - self.first_seqs.clear(); - self.next_seqs.clear(); - } - /// Returns top transactions whose timestamp are in the given range from the pool ordered by priority. // FIXME: current_timestamp should be `u64`, not `Option`. // FIXME: if range_contains becomes stable, use range.contains instead of inequality. diff --git a/core/src/tests/helpers.rs b/core/src/tests/helpers.rs index 348f547bca..57015d63bc 100644 --- a/core/src/tests/helpers.rs +++ b/core/src/tests/helpers.rs @@ -15,7 +15,6 @@ // along with this program. If not, see . use crate::scheme::Scheme; -use crate::transaction::SignedTransaction; use cstate::StateDB; use ctypes::{BlockHash, Header}; use primitives::{Bytes, U256}; @@ -28,18 +27,6 @@ pub fn create_test_block(header: &Header) -> Bytes { rlp.out() } -#[allow(dead_code)] -pub fn create_test_block_with_data(header: &Header, txs: &[SignedTransaction], uncles: &[Header]) -> Bytes { - let mut rlp = RlpStream::new_list(3); - rlp.append(header); - rlp.begin_list(txs.len()); - for t in txs { - rlp.append_raw(&rlp::encode(t), 1); - } - rlp.append_list(&uncles); - rlp.out() -} - pub fn get_good_dummy_block() -> Bytes { let (_, bytes) = get_good_dummy_block_hash(); bytes diff --git a/state/src/cache/top_cache.rs b/state/src/cache/top_cache.rs index d8efc422ad..e1b81d2b2f 100644 --- a/state/src/cache/top_cache.rs +++ b/state/src/cache/top_cache.rs @@ -128,10 +128,6 @@ impl TopCache { self.shard.get_mut(a, db) } - #[allow(dead_code)] - pub fn remove_shard(&self, address: &ShardAddress) { - self.shard.remove(address) - } pub fn text(&self, a: &H256, db: &dyn Trie) -> TrieResult> { self.text.get(a, db) From f74124be3de95baa8791cba034731b0f738a3f74 Mon Sep 17 00:00:00 2001 From: Seulgi Kim Date: Wed, 8 Apr 2020 17:15:33 +0900 Subject: [PATCH 31/55] Remove unused fields --- core/src/verification/queue/mod.rs | 6 ------ 1 file changed, 6 deletions(-) diff --git a/core/src/verification/queue/mod.rs b/core/src/verification/queue/mod.rs index 7f060a4b8a..0b060e0872 100644 --- a/core/src/verification/queue/mod.rs +++ b/core/src/verification/queue/mod.rs @@ -68,8 +68,6 @@ pub struct VerificationQueue { deleting: Arc, ready_signal: Arc, total_score: RwLock, - #[allow(dead_code)] - empty: Arc, more_to_verify: Arc, verifier_handles: Vec>, max_queue_size: usize, @@ -135,7 +133,6 @@ impl VerificationQueue { verified: AtomicUsize::new(0), }, check_seal, - empty_mutex: SMutex::new(()), more_to_verify_mutex: SMutex::new(()), }); let deleting = Arc::new(AtomicBool::new(false)); @@ -182,7 +179,6 @@ impl VerificationQueue { deleting, ready_signal, total_score: RwLock::new(0.into()), - empty, more_to_verify, verifier_handles, max_queue_size: cmp::max(config.max_queue_size, MIN_QUEUE_LIMIT), @@ -511,8 +507,6 @@ struct Verification { bad: Mutex>, sizes: Sizes, check_seal: bool, - #[allow(dead_code)] - empty_mutex: SMutex<()>, more_to_verify_mutex: SMutex<()>, } From 6a9a485d1c3f0430c60c4abe08f40ff38fd66b92 Mon Sep 17 00:00:00 2001 From: Seulgi Kim Date: Wed, 8 Apr 2020 17:17:25 +0900 Subject: [PATCH 32/55] Remove unnecessarry attributes --- sync/src/block/extension.rs | 2 -- 1 file changed, 2 deletions(-) diff --git a/sync/src/block/extension.rs b/sync/src/block/extension.rs index 4be801d614..f9b40b95c8 100644 --- a/sync/src/block/extension.rs +++ b/sync/src/block/extension.rs @@ -410,8 +410,6 @@ impl Extension { .map(|hash| self.client.block_header(&BlockId::Hash(hash)).expect("Enacted header must exist")) .collect(); headers_to_download.sort_unstable_by_key(EncodedHeader::number); - #[allow(clippy::redundant_closure)] - // False alarm. https://github.com/rust-lang/rust-clippy/issues/1439 headers_to_download.dedup_by_key(|h| h.hash()); let headers: Vec<_> = headers_to_download From c2e7e8d5271efdd78cae98a94c01ef5beee351c7 Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Mon, 13 Apr 2020 17:08:44 +0900 Subject: [PATCH 33/55] Add document in the fields of HeaderDownloader struct --- sync/src/block/downloader/header.rs | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/sync/src/block/downloader/header.rs b/sync/src/block/downloader/header.rs index 29d49b7ead..022e3b7d13 100644 --- a/sync/src/block/downloader/header.rs +++ b/sync/src/block/downloader/header.rs @@ -1,4 +1,4 @@ -// Copyright 2018 Kodebox, Inc. +// Copyright 2018-2020 Kodebox, Inc. // This file is part of CodeChain. // // This program is free software: you can redistribute it and/or modify @@ -43,9 +43,11 @@ pub struct HeaderDownloader { total_score: U256, best_hash: BlockHash, + /// The last header we downloaded from this peer. pivot: Pivot, request_time: Option, downloaded: HashMap, + /// Headers that are importing now. queued: HashMap, trial: usize, } From 1da8f5c2a9952dc8246e6179b292f45c49aebc06 Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Mon, 13 Apr 2020 17:49:48 +0900 Subject: [PATCH 34/55] Use `ctypes::Header` instead of `encoded::Header` in HeaderDownloader The purpose of the encoded type is to read a few fields from binary data when we don't want to full deserialize it. In the header sync, we already deserialized the whole struct in the verification process. We don't need to encoded Header when we have ctypes::Header. --- sync/src/block/downloader/header.rs | 7 +++---- sync/src/block/extension.rs | 7 +++---- 2 files changed, 6 insertions(+), 8 deletions(-) diff --git a/sync/src/block/downloader/header.rs b/sync/src/block/downloader/header.rs index 022e3b7d13..1dbc9f9cbc 100644 --- a/sync/src/block/downloader/header.rs +++ b/sync/src/block/downloader/header.rs @@ -15,9 +15,8 @@ // along with this program. If not, see . use super::super::message::RequestMessage; -use ccore::encoded::Header; use ccore::{BlockChainClient, BlockId}; -use ctypes::BlockHash; +use ctypes::{BlockHash, Header}; use primitives::U256; use std::cmp::Ordering; use std::collections::HashMap; @@ -112,7 +111,7 @@ impl HeaderDownloader { Some(header) => header.clone(), None => match self.downloaded.get(&self.pivot.hash) { Some(header) => header.clone(), - None => self.client.block_header(&BlockId::Hash(self.pivot.hash)).unwrap(), + None => self.client.block_header(&BlockId::Hash(self.pivot.hash)).unwrap().decode(), }, } } @@ -179,7 +178,7 @@ impl HeaderDownloader { } else if first_header_number == pivot_header.number() { if pivot_header.number() != 0 { self.pivot = Pivot { - hash: pivot_header.parent_hash(), + hash: *pivot_header.parent_hash(), total_score: self.pivot.total_score - pivot_header.score(), } } diff --git a/sync/src/block/extension.rs b/sync/src/block/extension.rs index f9b40b95c8..29b69d23ca 100644 --- a/sync/src/block/extension.rs +++ b/sync/src/block/extension.rs @@ -682,21 +682,20 @@ impl Extension { ctrace!(SYNC, "Received header response from({}) with length({})", from, headers.len()); let (mut completed, pivot_score_changed) = if let Some(peer) = self.header_downloaders.get_mut(from) { let before_pivot_score = peer.pivot_score(); - let encoded: Vec<_> = headers.iter().map(|h| EncodedHeader::new(h.rlp_bytes().to_vec())).collect(); - peer.import_headers(&encoded); + peer.import_headers(&headers); let after_pivot_score = peer.pivot_score(); (peer.downloaded(), before_pivot_score != after_pivot_score) } else { (Vec::new(), false) }; - completed.sort_unstable_by_key(EncodedHeader::number); + completed.sort_unstable_by_key(Header::number); let mut exists = Vec::new(); let mut queued = Vec::new(); for header in completed { let hash = header.hash(); - match self.client.import_header(header.clone().into_inner()) { + match self.client.import_header(header.rlp_bytes()) { Err(BlockImportError::Import(ImportError::AlreadyInChain)) => exists.push(hash), Err(BlockImportError::Import(ImportError::AlreadyQueued)) => queued.push(hash), // FIXME: handle import errors From f5debd66ff076559b9c0dbe52c7614d6efcd517b Mon Sep 17 00:00:00 2001 From: Byeongjee Kang Date: Tue, 14 Apr 2020 18:09:41 +0900 Subject: [PATCH 35/55] Remove unnecessary initialization of genesis header extra data We gain nothing from initializing extra data of genesis header with hash of common params, because the check will be done by the same node, and it will always succeed. We can just use extra_data written in scheme file. --- core/src/client/client.rs | 1 - core/src/scheme/scheme.rs | 36 ++---------------------------------- 2 files changed, 2 insertions(+), 35 deletions(-) diff --git a/core/src/client/client.rs b/core/src/client/client.rs index 1b3e0e80d0..4f684db457 100644 --- a/core/src/client/client.rs +++ b/core/src/client/client.rs @@ -103,7 +103,6 @@ impl Client { let gb = scheme.genesis_block(); let chain = BlockChain::new(&gb, db.clone()); - scheme.check_genesis_common_params(&chain)?; let engine = scheme.engine.clone(); diff --git a/core/src/scheme/scheme.rs b/core/src/scheme/scheme.rs index e35ec00fb5..7d2f7f4b88 100644 --- a/core/src/scheme/scheme.rs +++ b/core/src/scheme/scheme.rs @@ -17,11 +17,10 @@ use super::pod_state::{PodAccounts, PodShards}; use super::seal::Generic as GenericSeal; use super::Genesis; -use crate::blockchain::HeaderProvider; use crate::codechain_machine::CodeChainMachine; use crate::consensus::{BlakePoW, CodeChainEngine, Cuckoo, NullEngine, SimplePoA, Solo, Tendermint}; use crate::error::{Error, SchemeError}; -use ccrypto::{blake256, BLAKE_NULL_RLP}; +use ccrypto::BLAKE_NULL_RLP; use cdb::{AsHashDB, HashDB}; use cjson; use ckey::Address; @@ -199,19 +198,6 @@ impl Scheme { Ok(self.initialize_state(db)?) } - pub fn check_genesis_common_params(&self, chain: &HP) -> Result<(), Error> { - let genesis_header = self.genesis_header(); - let genesis_header_hash = genesis_header.hash(); - let header = - chain.block_header(&genesis_header_hash).ok_or_else(|| Error::Scheme(SchemeError::InvalidCommonParams))?; - let extra_data = header.extra_data(); - let common_params_hash = blake256(&self.genesis_params().rlp_bytes()).to_vec(); - if extra_data != &common_params_hash { - return Err(Error::Scheme(SchemeError::InvalidCommonParams)) - } - Ok(()) - } - /// Return the state root for the genesis state, memoising accordingly. pub fn state_root(&self) -> H256 { *self.state_root_memo.read() @@ -291,7 +277,7 @@ impl Scheme { header.set_number(0); header.set_author(self.author); header.set_transactions_root(self.transactions_root); - header.set_extra_data(blake256(&self.genesis_params().rlp_bytes()).to_vec()); + header.set_extra_data(self.extra_data.clone()); header.set_state_root(self.state_root()); header.set_score(self.score); header.set_seal({ @@ -354,21 +340,3 @@ fn load_from(s: cjson::scheme::Scheme) -> Result { Ok(s) } - -#[cfg(test)] -mod tests { - use ccrypto::Blake; - - use super::*; - - #[test] - fn extra_data_of_genesis_header_is_hash_of_common_params() { - let scheme = Scheme::new_test(); - let common_params = scheme.genesis_params(); - let hash_of_common_params = H256::blake(&common_params.rlp_bytes()).to_vec(); - - let genesis_header = scheme.genesis_header(); - let result = genesis_header.extra_data(); - assert_eq!(&hash_of_common_params, result); - } -} From 3255b031eedb4f34cb0583b2457d85498339c760 Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Thu, 16 Apr 2020 14:39:47 +0900 Subject: [PATCH 36/55] Remove verification_type CodeChain was using only the VerifierType::Canon. --- core/src/client/config.rs | 5 +---- core/src/client/importer.rs | 13 ++++-------- core/src/verification/mod.rs | 38 ------------------------------------ 3 files changed, 5 insertions(+), 51 deletions(-) diff --git a/core/src/client/config.rs b/core/src/client/config.rs index f64b679609..e1afbb6097 100644 --- a/core/src/client/config.rs +++ b/core/src/client/config.rs @@ -14,7 +14,7 @@ // You should have received a copy of the GNU Affero General Public License // along with this program. If not, see . -use crate::verification::{QueueConfig, VerifierType}; +use crate::verification::QueueConfig; use kvdb_rocksdb::CompactionProfile; use std::path::Path; use std::str::FromStr; @@ -71,8 +71,6 @@ pub struct ClientConfig { pub db_compaction: DatabaseCompactionProfile, /// State db cache-size. pub state_cache_size: usize, - /// Type of block verifier used by client. - pub verifier_type: VerifierType, } impl Default for ClientConfig { @@ -84,7 +82,6 @@ impl Default for ClientConfig { db_cache_size: Default::default(), db_compaction: Default::default(), state_cache_size: DEFAULT_STATE_CACHE_SIZE as usize * mb, - verifier_type: Default::default(), } } } diff --git a/core/src/client/importer.rs b/core/src/client/importer.rs index 28a080ff6b..7818162d31 100644 --- a/core/src/client/importer.rs +++ b/core/src/client/importer.rs @@ -35,6 +35,7 @@ use rlp::Encodable; use std::borrow::Borrow; use std::collections::{HashMap, HashSet}; use std::sync::Arc; +use verification::CanonVerifier; pub struct Importer { /// Lock used during block import @@ -63,19 +64,13 @@ impl Importer { message_channel: IoChannel, miner: Arc, ) -> Result { - let block_queue = BlockQueue::new( - &config.queue, - engine.clone(), - message_channel.clone(), - config.verifier_type.verifying_seal(), - ); + let block_queue = BlockQueue::new(&config.queue, engine.clone(), message_channel.clone(), true); - let header_queue = - HeaderQueue::new(&config.queue, engine.clone(), message_channel, config.verifier_type.verifying_seal()); + let header_queue = HeaderQueue::new(&config.queue, engine.clone(), message_channel, true); Ok(Importer { import_lock: Mutex::new(()), - verifier: verification::new(config.verifier_type), + verifier: Box::new(CanonVerifier), block_queue, header_queue, miner, diff --git a/core/src/verification/mod.rs b/core/src/verification/mod.rs index a13cb4a00e..c679926530 100644 --- a/core/src/verification/mod.rs +++ b/core/src/verification/mod.rs @@ -26,41 +26,3 @@ pub use self::noop_verifier::NoopVerifier; pub use self::queue::{BlockQueue, Config as QueueConfig}; pub use self::verification::*; pub use self::verifier::Verifier; - -use crate::client::BlockChainTrait; - -/// Verifier type. -#[derive(Debug, PartialEq, Clone, Copy)] -pub enum VerifierType { - /// Verifies block normally. - Canon, - /// Verifies block normally, but skips seal verification. - CanonNoSeal, - /// Does not verify block at all. - /// Used in tests. - Noop, -} - -impl VerifierType { - /// Check if seal verification is enabled for this verifier type. - pub fn verifying_seal(self) -> bool { - match self { - VerifierType::Canon => true, - VerifierType::Noop | VerifierType::CanonNoSeal => false, - } - } -} - -impl Default for VerifierType { - fn default() -> Self { - VerifierType::Canon - } -} - -/// Create a new verifier based on type. -pub fn new(v: VerifierType) -> Box> { - match v { - VerifierType::Canon | VerifierType::CanonNoSeal => Box::new(CanonVerifier), - VerifierType::Noop => Box::new(NoopVerifier), - } -} From 0f75c4d29c9327e94c3902b4875b0676d739aa07 Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Thu, 16 Apr 2020 14:41:22 +0900 Subject: [PATCH 37/55] Remove Verifier trait CodeChain is using only CanonVerifier. We are not using the `Verifier` abstraction. --- core/src/client/importer.rs | 5 ++- core/src/verification/canon_verifier.rs | 47 ------------------------- core/src/verification/mod.rs | 4 --- core/src/verification/noop_verifier.rs | 46 ------------------------ core/src/verification/verifier.rs | 30 +++++++++++++--- 5 files changed, 27 insertions(+), 105 deletions(-) delete mode 100644 core/src/verification/canon_verifier.rs delete mode 100644 core/src/verification/noop_verifier.rs diff --git a/core/src/client/importer.rs b/core/src/client/importer.rs index 7818162d31..babb9ddcdc 100644 --- a/core/src/client/importer.rs +++ b/core/src/client/importer.rs @@ -35,14 +35,13 @@ use rlp::Encodable; use std::borrow::Borrow; use std::collections::{HashMap, HashSet}; use std::sync::Arc; -use verification::CanonVerifier; pub struct Importer { /// Lock used during block import pub import_lock: Mutex<()>, // FIXME Maybe wrap the whole `Importer` instead? /// Used to verify blocks - pub verifier: Box>, + pub verifier: Verifier, /// Queue containing pending blocks pub block_queue: BlockQueue, @@ -70,7 +69,7 @@ impl Importer { Ok(Importer { import_lock: Mutex::new(()), - verifier: Box::new(CanonVerifier), + verifier: Verifier::new(), block_queue, header_queue, miner, diff --git a/core/src/verification/canon_verifier.rs b/core/src/verification/canon_verifier.rs deleted file mode 100644 index 86adff0411..0000000000 --- a/core/src/verification/canon_verifier.rs +++ /dev/null @@ -1,47 +0,0 @@ -// Copyright 2018-2019 Kodebox, Inc. -// This file is part of CodeChain. -// -// This program is free software: you can redistribute it and/or modify -// it under the terms of the GNU Affero General Public License as -// published by the Free Software Foundation, either version 3 of the -// License, or (at your option) any later version. -// -// This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU Affero General Public License for more details. -// -// You should have received a copy of the GNU Affero General Public License -// along with this program. If not, see . - -use super::verification; -use super::Verifier; -use crate::client::BlockChainTrait; -use crate::consensus::CodeChainEngine; -use crate::error::Error; -use ctypes::{CommonParams, Header}; - -/// A canonial verifier -- this does full verification. -pub struct CanonVerifier; - -impl Verifier for CanonVerifier { - fn verify_block_family( - &self, - block: &[u8], - header: &Header, - parent: &Header, - engine: &dyn CodeChainEngine, - do_full: Option>, - common_params: &CommonParams, - ) -> Result<(), Error> { - verification::verify_block_family(block, header, parent, engine, do_full, common_params) - } - - fn verify_block_final(&self, expected: &Header, got: &Header) -> Result<(), Error> { - verification::verify_block_final(expected, got) - } - - fn verify_block_external(&self, header: &Header, engine: &dyn CodeChainEngine) -> Result<(), Error> { - engine.verify_block_external(header) - } -} diff --git a/core/src/verification/mod.rs b/core/src/verification/mod.rs index c679926530..dce8ca2e85 100644 --- a/core/src/verification/mod.rs +++ b/core/src/verification/mod.rs @@ -14,15 +14,11 @@ // You should have received a copy of the GNU Affero General Public License // along with this program. If not, see . -mod canon_verifier; -mod noop_verifier; pub mod queue; #[cfg_attr(feature = "cargo-clippy", allow(clippy::module_inception))] mod verification; mod verifier; -pub use self::canon_verifier::CanonVerifier; -pub use self::noop_verifier::NoopVerifier; pub use self::queue::{BlockQueue, Config as QueueConfig}; pub use self::verification::*; pub use self::verifier::Verifier; diff --git a/core/src/verification/noop_verifier.rs b/core/src/verification/noop_verifier.rs deleted file mode 100644 index 9321de701b..0000000000 --- a/core/src/verification/noop_verifier.rs +++ /dev/null @@ -1,46 +0,0 @@ -// Copyright 2018-2019 Kodebox, Inc. -// This file is part of CodeChain. -// -// This program is free software: you can redistribute it and/or modify -// it under the terms of the GNU Affero General Public License as -// published by the Free Software Foundation, either version 3 of the -// License, or (at your option) any later version. -// -// This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU Affero General Public License for more details. -// -// You should have received a copy of the GNU Affero General Public License -// along with this program. If not, see . - -use super::{verification, Verifier}; -use crate::client::BlockChainTrait; -use crate::consensus::CodeChainEngine; -use crate::error::Error; -use ctypes::{CommonParams, Header}; - -/// A no-op verifier -- this will verify everything it's given immediately. -pub struct NoopVerifier; - -impl Verifier for NoopVerifier { - fn verify_block_family( - &self, - _block: &[u8], - _: &Header, - _t: &Header, - _: &dyn CodeChainEngine, - _: Option>, - _common_params: &CommonParams, - ) -> Result<(), Error> { - Ok(()) - } - - fn verify_block_final(&self, _expected: &Header, _got: &Header) -> Result<(), Error> { - Ok(()) - } - - fn verify_block_external(&self, _header: &Header, _engine: &dyn CodeChainEngine) -> Result<(), Error> { - Ok(()) - } -} diff --git a/core/src/verification/verifier.rs b/core/src/verification/verifier.rs index 7b032da593..4fcb058bbe 100644 --- a/core/src/verification/verifier.rs +++ b/core/src/verification/verifier.rs @@ -19,13 +19,26 @@ use crate::client::BlockChainTrait; use crate::consensus::CodeChainEngine; use crate::error::Error; use ctypes::{CommonParams, Header}; +use std::marker::PhantomData; /// Should be used to verify blocks. -pub trait Verifier: Send + Sync +pub struct Verifier where C: BlockChainTrait, { + phantom: PhantomData, +} + +impl Verifier { + pub fn new() -> Self { + Self { + phantom: Default::default(), + } + } +} + +impl Verifier { /// Verify a block relative to its parent and uncles. - fn verify_block_family( + pub fn verify_block_family( &self, block: &[u8], header: &Header, @@ -33,10 +46,17 @@ where engine: &dyn CodeChainEngine, do_full: Option>, common_params: &CommonParams, - ) -> Result<(), Error>; + ) -> Result<(), Error> { + verification::verify_block_family(block, header, parent, engine, do_full, common_params) + } /// Do a final verification check for an enacted header vs its expected counterpart. - fn verify_block_final(&self, expected: &Header, got: &Header) -> Result<(), Error>; + pub fn verify_block_final(&self, expected: &Header, got: &Header) -> Result<(), Error> { + verification::verify_block_final(expected, got) + } + /// Verify a block, inspecting external state. - fn verify_block_external(&self, header: &Header, engine: &dyn CodeChainEngine) -> Result<(), Error>; + pub fn verify_block_external(&self, header: &Header, engine: &dyn CodeChainEngine) -> Result<(), Error> { + engine.verify_block_external(header) + } } From bef8d752bf073d3c387edf86c9ed272a1b385ab5 Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Thu, 16 Apr 2020 15:52:26 +0900 Subject: [PATCH 38/55] Remove unnecessary serialize/deserialize while calling import_header --- core/src/client/client.rs | 11 ++++------- core/src/client/mod.rs | 4 ++-- core/src/client/test_client.rs | 2 +- sync/src/block/extension.rs | 4 ++-- 4 files changed, 9 insertions(+), 12 deletions(-) diff --git a/core/src/client/client.rs b/core/src/client/client.rs index 4f684db457..2365ac4003 100644 --- a/core/src/client/client.rs +++ b/core/src/client/client.rs @@ -40,7 +40,7 @@ use cstate::{ }; use ctimer::{TimeoutHandler, TimerApi, TimerScheduleError, TimerToken}; use ctypes::transaction::{AssetTransferInput, PartialHashing, ShardTransaction}; -use ctypes::{BlockHash, BlockNumber, CommonParams, ShardId, Tracker, TxHash}; +use ctypes::{BlockHash, BlockNumber, CommonParams, Header, ShardId, Tracker, TxHash}; use cvm::{decode, execute, ChainTimeInfo, ScriptResult, VMConfig}; use kvdb::{DBTransaction, KeyValueDB}; use merkle_trie::Result as TrieResult; @@ -636,12 +636,9 @@ impl ImportBlock for Client { Ok(self.importer.block_queue.import(unverified)?) } - fn import_header(&self, bytes: Bytes) -> Result { - let unverified = encoded::Header::new(bytes).decode(); - { - if self.block_chain().is_known_header(&unverified.hash()) { - return Err(BlockImportError::Import(ImportError::AlreadyInChain)) - } + fn import_header(&self, unverified: Header) -> Result { + if self.block_chain().is_known_header(&unverified.hash()) { + return Err(BlockImportError::Import(ImportError::AlreadyInChain)) } Ok(self.importer.header_queue.import(unverified)?) } diff --git a/core/src/client/mod.rs b/core/src/client/mod.rs index 09dedcd84b..9576086d85 100644 --- a/core/src/client/mod.rs +++ b/core/src/client/mod.rs @@ -39,7 +39,7 @@ use cdb::DatabaseError; use ckey::{Address, NetworkId, PlatformAddress, Public}; use cstate::{AssetScheme, FindActionHandler, OwnedAsset, StateResult, Text, TopLevelState, TopStateView}; use ctypes::transaction::{AssetTransferInput, PartialHashing, ShardTransaction}; -use ctypes::{BlockHash, BlockNumber, CommonParams, ShardId, Tracker, TxHash}; +use ctypes::{BlockHash, BlockNumber, CommonParams, Header, ShardId, Tracker, TxHash}; use cvm::ChainTimeInfo; use kvdb::KeyValueDB; use merkle_trie::Result as TrieResult; @@ -197,7 +197,7 @@ pub trait ImportBlock { fn import_block(&self, bytes: Bytes) -> Result; /// Import a header into the blockchain - fn import_header(&self, bytes: Bytes) -> Result; + fn import_header(&self, header: Header) -> Result; /// Import sealed block. Skips all verifications. fn import_sealed_block(&self, block: &SealedBlock) -> ImportResult; diff --git a/core/src/client/test_client.rs b/core/src/client/test_client.rs index 448241532b..505383725b 100644 --- a/core/src/client/test_client.rs +++ b/core/src/client/test_client.rs @@ -508,7 +508,7 @@ impl ImportBlock for TestBlockChainClient { Ok(h) } - fn import_header(&self, _bytes: Bytes) -> Result { + fn import_header(&self, _bytes: BlockHeader) -> Result { unimplemented!() } diff --git a/sync/src/block/extension.rs b/sync/src/block/extension.rs index 29b69d23ca..a471a7e793 100644 --- a/sync/src/block/extension.rs +++ b/sync/src/block/extension.rs @@ -695,12 +695,12 @@ impl Extension { for header in completed { let hash = header.hash(); - match self.client.import_header(header.rlp_bytes()) { + match self.client.import_header(header) { Err(BlockImportError::Import(ImportError::AlreadyInChain)) => exists.push(hash), Err(BlockImportError::Import(ImportError::AlreadyQueued)) => queued.push(hash), // FIXME: handle import errors Err(err) => { - cwarn!(SYNC, "Cannot import header({}): {:?}", header.hash(), err); + cwarn!(SYNC, "Cannot import header({}): {:?}", hash, err); break } _ => {} From 8f2695e0edf7a615534c6ad5f89c88e7e657860d Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Thu, 16 Apr 2020 16:12:12 +0900 Subject: [PATCH 39/55] Make on_header_response receive moved Header instead of reference --- sync/src/block/extension.rs | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/sync/src/block/extension.rs b/sync/src/block/extension.rs index a471a7e793..f533d18ddb 100644 --- a/sync/src/block/extension.rs +++ b/sync/src/block/extension.rs @@ -587,7 +587,7 @@ impl Extension { match response { ResponseMessage::Headers(headers) => { self.dismiss_request(from, id); - self.on_header_response(from, &headers) + self.on_header_response(from, headers) } ResponseMessage::Bodies(bodies) => { self.check_sync_variable(); @@ -678,7 +678,7 @@ impl Extension { } } - fn on_header_response(&mut self, from: &NodeId, headers: &[Header]) { + fn on_header_response(&mut self, from: &NodeId, headers: Vec
) { ctrace!(SYNC, "Received header response from({}) with length({})", from, headers.len()); let (mut completed, pivot_score_changed) = if let Some(peer) = self.header_downloaders.get_mut(from) { let before_pivot_score = peer.pivot_score(); @@ -689,7 +689,6 @@ impl Extension { (Vec::new(), false) }; completed.sort_unstable_by_key(Header::number); - let mut exists = Vec::new(); let mut queued = Vec::new(); From c7e423c08b12270c31f3fdaaf08b5e5f52db7ae9 Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Thu, 16 Apr 2020 17:10:48 +0900 Subject: [PATCH 40/55] Rename import_headers to import_verified_headers Client::import_header function receives a header that is not verified. Importer::import_headers assumes that received headers are verified. To reduce misunderstanding, I renamed the function. --- core/src/client/client.rs | 4 ++-- core/src/client/importer.rs | 8 ++++---- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/core/src/client/client.rs b/core/src/client/client.rs index 2365ac4003..73d9987293 100644 --- a/core/src/client/client.rs +++ b/core/src/client/client.rs @@ -189,7 +189,7 @@ impl Client { /// This is triggered by a message coming from a header queue when the header is ready for insertion pub fn import_verified_headers(&self) -> usize { - self.importer.import_verified_headers(self) + self.importer.import_verified_headers_from_queue(self) } /// This is triggered by a message coming from a block queue when the block is ready for insertion @@ -653,7 +653,7 @@ impl ImportBlock for Client { let block_data = block.rlp_bytes(); let header = block.header(); - self.importer.import_headers(vec![header], self, &import_lock); + self.importer.import_verified_headers(vec![header], self, &import_lock); let route = self.importer.commit_block(block, header, &block_data, self); cinfo!(CLIENT, "Imported sealed block #{} ({})", number, h); diff --git a/core/src/client/importer.rs b/core/src/client/importer.rs index babb9ddcdc..c98f429281 100644 --- a/core/src/client/importer.rs +++ b/core/src/client/importer.rs @@ -93,7 +93,7 @@ impl Importer { { let headers: Vec<&Header> = blocks.iter().map(|block| &block.header).collect(); - self.import_headers(headers, client, &import_lock); + self.import_verified_headers(headers, client, &import_lock); } for block in blocks { @@ -287,14 +287,14 @@ impl Importer { } /// This is triggered by a message coming from a header queue when the header is ready for insertion - pub fn import_verified_headers(&self, client: &Client) -> usize { + pub fn import_verified_headers_from_queue(&self, client: &Client) -> usize { const MAX_HEADERS_TO_IMPORT: usize = 1_000; let lock = self.import_lock.lock(); let headers = self.header_queue.drain(MAX_HEADERS_TO_IMPORT); - self.import_headers(&headers, client, &lock) + self.import_verified_headers(&headers, client, &lock) } - pub fn import_headers<'a>( + pub fn import_verified_headers<'a>( &'a self, headers: impl IntoIterator, client: &Client, From 021506ea78468c956656d594e6458715d4704df6 Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Thu, 16 Apr 2020 17:37:22 +0900 Subject: [PATCH 41/55] Rename import_sealed_block to import_generated_block The name `import_sealed_block` does not give enough context. --- core/src/client/client.rs | 2 +- core/src/client/mod.rs | 2 +- core/src/client/test_client.rs | 2 +- core/src/miner/miner.rs | 4 ++-- 4 files changed, 5 insertions(+), 5 deletions(-) diff --git a/core/src/client/client.rs b/core/src/client/client.rs index 73d9987293..d52f0cc77a 100644 --- a/core/src/client/client.rs +++ b/core/src/client/client.rs @@ -643,7 +643,7 @@ impl ImportBlock for Client { Ok(self.importer.header_queue.import(unverified)?) } - fn import_sealed_block(&self, block: &SealedBlock) -> ImportResult { + fn import_generated_block(&self, block: &SealedBlock) -> ImportResult { let h = block.header().hash(); let route = { // scope for self.import_lock diff --git a/core/src/client/mod.rs b/core/src/client/mod.rs index 9576086d85..aa4766ecd1 100644 --- a/core/src/client/mod.rs +++ b/core/src/client/mod.rs @@ -200,7 +200,7 @@ pub trait ImportBlock { fn import_header(&self, header: Header) -> Result; /// Import sealed block. Skips all verifications. - fn import_sealed_block(&self, block: &SealedBlock) -> ImportResult; + fn import_generated_block(&self, block: &SealedBlock) -> ImportResult; /// Set reseal min timer as reseal_min_period, for creating blocks with transactions which are pending because of reseal_min_period fn set_min_timer(&self); diff --git a/core/src/client/test_client.rs b/core/src/client/test_client.rs index 505383725b..7d4c97b67b 100644 --- a/core/src/client/test_client.rs +++ b/core/src/client/test_client.rs @@ -512,7 +512,7 @@ impl ImportBlock for TestBlockChainClient { unimplemented!() } - fn import_sealed_block(&self, _block: &SealedBlock) -> ImportResult { + fn import_generated_block(&self, _block: &SealedBlock) -> ImportResult { Ok(H256::default().into()) } diff --git a/core/src/miner/miner.rs b/core/src/miner/miner.rs index 1f463583a4..f06403e5d8 100644 --- a/core/src/miner/miner.rs +++ b/core/src/miner/miner.rs @@ -777,7 +777,7 @@ impl Miner { self.engine.proposal_generated(&sealed); } - chain.import_sealed_block(&sealed).is_ok() + chain.import_generated_block(&sealed).is_ok() } /// Are we allowed to do a non-mandatory reseal? @@ -1053,7 +1053,7 @@ impl MinerService for Miner { result.and_then(|sealed| { let n = sealed.header().number(); let h = sealed.header().hash(); - chain.import_sealed_block(&sealed)?; + chain.import_generated_block(&sealed)?; cinfo!(MINER, "Submitted block imported OK. #{}: {}", n, h); Ok(()) }) From 4287c1bcf16aa8e9196afc45c9eca63583857f21 Mon Sep 17 00:00:00 2001 From: Seulgi Kim Date: Thu, 16 Apr 2020 20:59:31 +0900 Subject: [PATCH 42/55] Remove the unused argument of push_transaction The h is always None. --- core/src/block.rs | 5 ++--- core/src/miner/miner.rs | 2 +- 2 files changed, 3 insertions(+), 4 deletions(-) diff --git a/core/src/block.rs b/core/src/block.rs index ebd3484fcf..7154166f4a 100644 --- a/core/src/block.rs +++ b/core/src/block.rs @@ -152,7 +152,6 @@ impl<'x> OpenBlock<'x> { pub fn push_transaction( &mut self, tx: SignedTransaction, - h: Option, client: &C, parent_block_number: BlockNumber, parent_block_timestamp: u64, @@ -173,7 +172,7 @@ impl<'x> OpenBlock<'x> { self.block.header.timestamp(), ) { Ok(()) => { - self.block.transactions_set.insert(h.unwrap_or(hash)); + self.block.transactions_set.insert(hash); self.block.transactions.push(tx); None } @@ -200,7 +199,7 @@ impl<'x> OpenBlock<'x> { parent_block_timestamp: u64, ) -> Result<(), Error> { for tx in transactions { - self.push_transaction(tx.clone(), None, client, parent_block_number, parent_block_timestamp)?; + self.push_transaction(tx.clone(), client, parent_block_number, parent_block_timestamp)?; } Ok(()) } diff --git a/core/src/miner/miner.rs b/core/src/miner/miner.rs index f06403e5d8..7570c6bbb8 100644 --- a/core/src/miner/miner.rs +++ b/core/src/miner/miner.rs @@ -661,7 +661,7 @@ impl Miner { // Check whether transaction type is allowed for sender let result = self.engine.machine().verify_transaction(&tx, open_block.header(), chain, true).and_then(|_| { - open_block.push_transaction(tx, None, chain, parent_header.number(), parent_header.timestamp()) + open_block.push_transaction(tx, chain, parent_header.number(), parent_header.timestamp()) }); match result { From 80a7d6e1206583b35d0181b2f63496c5a59a1665 Mon Sep 17 00:00:00 2001 From: Seulgi Kim Date: Sun, 12 Apr 2020 14:35:05 +0900 Subject: [PATCH 43/55] Make the miner always have AccountProvider Currently, AccountProvider in the miner is optional to support unit tests who cannot use the account provider which uses the permanent storage. This commit makes the miner uses memory back-end AccountProvider for test. --- codechain/run_node.rs | 2 +- core/src/client/test_client.rs | 2 +- core/src/miner/miner.rs | 51 +++++++++++++--------------------- 3 files changed, 22 insertions(+), 33 deletions(-) diff --git a/codechain/run_node.rs b/codechain/run_node.rs index b9c8391e94..e0c49b1b8d 100644 --- a/codechain/run_node.rs +++ b/codechain/run_node.rs @@ -131,7 +131,7 @@ fn new_miner( ap: Arc, db: Arc, ) -> Result, String> { - let miner = Miner::new(config.miner_options()?, scheme, Some(ap), db); + let miner = Miner::new(config.miner_options()?, scheme, ap, db); match miner.engine_type() { EngineType::PoW => match &config.mining.author { diff --git a/core/src/client/test_client.rs b/core/src/client/test_client.rs index 7d4c97b67b..43e164b636 100644 --- a/core/src/client/test_client.rs +++ b/core/src/client/test_client.rs @@ -150,7 +150,7 @@ impl TestBlockChainClient { seqs: RwLock::new(HashMap::new()), storage: RwLock::new(HashMap::new()), queue_size: AtomicUsize::new(0), - miner: Arc::new(Miner::with_scheme(&scheme, db)), + miner: Arc::new(Miner::with_scheme_for_test(&scheme, db)), scheme, latest_block_timestamp: RwLock::new(10_000_000), history: RwLock::new(None), diff --git a/core/src/miner/miner.rs b/core/src/miner/miner.rs index 7570c6bbb8..63903de306 100644 --- a/core/src/miner/miner.rs +++ b/core/src/miner/miner.rs @@ -124,7 +124,7 @@ pub struct Miner { sealing_enabled: AtomicBool, - accounts: Option>, + accounts: Arc, notifiers: Notifiers, malicious_users: Users, immune_users: Users, @@ -266,20 +266,20 @@ impl Miner { pub fn new( options: MinerOptions, scheme: &Scheme, - accounts: Option>, + accounts: Arc, db: Arc, ) -> Arc { Arc::new(Self::new_raw(options, scheme, accounts, db)) } - pub fn with_scheme(scheme: &Scheme, db: Arc) -> Self { - Self::new_raw(Default::default(), scheme, None, db) + pub fn with_scheme_for_test(scheme: &Scheme, db: Arc) -> Self { + Self::new_raw(Default::default(), scheme, AccountProvider::transient_provider(), db) } fn new_raw( options: MinerOptions, scheme: &Scheme, - accounts: Option>, + accounts: Arc, db: Arc, ) -> Self { let mem_limit = options.mem_pool_memory_limit.unwrap_or_else(usize::max_value); @@ -401,15 +401,11 @@ impl Miner { self.immune_users.insert(signer_address); } - let origin = self - .accounts - .as_ref() - .and_then(|accounts| match accounts.has_public(&signer_public) { - Ok(true) => Some(TxOrigin::Local), - Ok(false) => None, - Err(_) => None, - }) - .unwrap_or(default_origin); + let origin = if self.accounts.has_public(&signer_public).unwrap_or_default() { + TxOrigin::Local + } else { + default_origin + }; if self.malicious_users.contains(&signer_address) { // FIXME: just to skip, think about another way. @@ -834,24 +830,17 @@ impl MinerService for Miner { self.params.apply(|params| params.author = address); if self.engine_type().need_signer_key() && self.engine.seals_internally().is_some() { - if let Some(ref ap) = self.accounts { - ctrace!(MINER, "Set author to {:?}", address); - // Sign test message - ap.get_unlocked_account(&address)?.sign(&Default::default())?; - // Limit the scope of the locks. - { - let mut sealing_work = self.sealing_work.lock(); - sealing_work.enabled = true; - } - self.engine.set_signer(ap.clone(), address); - Ok(()) - } else { - cwarn!(MINER, "No account provider"); - Err(AccountProviderError::NotFound) + ctrace!(MINER, "Set author to {:?}", address); + // Sign test message + self.accounts.get_unlocked_account(&address)?.sign(&Default::default())?; + // Limit the scope of the locks. + { + let mut sealing_work = self.sealing_work.lock(); + sealing_work.enabled = true; } - } else { - Ok(()) + self.engine.set_signer(Arc::clone(&self.accounts), address); } + Ok(()) } fn get_author_address(&self) -> Address { @@ -1280,7 +1269,7 @@ pub mod test { fn check_add_transactions_result_idx() { let db = Arc::new(kvdb_memorydb::create(NUM_COLUMNS.unwrap())); let scheme = Scheme::new_test(); - let miner = Arc::new(Miner::with_scheme(&scheme, db.clone())); + let miner = Arc::new(Miner::with_scheme_for_test(&scheme, db.clone())); let mut mem_pool = MemPool::with_limits(8192, usize::max_value(), 3, db.clone(), Default::default()); let client = generate_test_client(db, Arc::clone(&miner), &scheme).unwrap(); From 0f87e27edee3c3d4c1509afa42113ef1304e93ce Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Wed, 6 May 2020 18:25:32 +0900 Subject: [PATCH 44/55] Run mock tests --- .github/workflows/{yarn-lint.yml => yarn.yml} | 4 +++- test/package.json | 1 + 2 files changed, 4 insertions(+), 1 deletion(-) rename .github/workflows/{yarn-lint.yml => yarn.yml} (79%) diff --git a/.github/workflows/yarn-lint.yml b/.github/workflows/yarn.yml similarity index 79% rename from .github/workflows/yarn-lint.yml rename to .github/workflows/yarn.yml index 7d481a4480..50949480b4 100644 --- a/.github/workflows/yarn-lint.yml +++ b/.github/workflows/yarn.yml @@ -1,6 +1,6 @@ on: [push, pull_request] -name: yarn-lint +name: yarn jobs: lint: @@ -14,3 +14,5 @@ jobs: run: yarn - working-directory: ./test run: yarn lint + - working-directory: ./test + run: yarn test-mock diff --git a/test/package.json b/test/package.json index 34664680f3..2120b91b30 100644 --- a/test/package.json +++ b/test/package.json @@ -19,6 +19,7 @@ "start-short-release": "cargo build --release && NODE_ENV=production mocha -r ts-node/register --timeout 5000 src/e2e/*.test.ts", "start-long-release": "cargo build --release && NODE_ENV=production mocha -r ts-node/register --timeout 10000 src/e2e.long/*.test.ts", "start-dyn-val-release": "cargo build --release && NODE_ENV=production mocha -r ts-node/register --timeout 10000 src/e2e.dynval/*.test.ts", + "test-mock": "mocha -r ts-node/register --timeout 5000 \"src/helper/mock/**/*.test.ts\"", "tendermint-test-local": "cargo build --release && NODE_ENV=production ts-node src/tendermint.test/local.ts", "tendermint-test-remote": "NODE_ENV=production ts-node src/tendermint.test/remote.ts", "lint": "tslint -p . && prettier 'src/**/*.{ts, json}' -l", From cc4f56ad824b1a2b0c5958f18d6fe316f4d8a199 Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Wed, 6 May 2020 19:05:31 +0900 Subject: [PATCH 45/55] Fix mock tests I changed the test code only. The tests were deprecated. I updated RLP encoded data from CodeChain code and it worked. --- test/src/helper/mock/test/blockSyncMessage.test.ts | 4 ++-- test/src/helper/mock/test/txSyncMessage.test.ts | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/test/src/helper/mock/test/blockSyncMessage.test.ts b/test/src/helper/mock/test/blockSyncMessage.test.ts index 6c1a2a70a4..593b8d2310 100644 --- a/test/src/helper/mock/test/blockSyncMessage.test.ts +++ b/test/src/helper/mock/test/blockSyncMessage.test.ts @@ -14,7 +14,7 @@ describe("Check BlockSyncMessage RLP encoding", function() { id: new U256(10), message }); - expect([...msg.rlpBytes()]).deep.equal([195, 4, 10, 192]); + expect(msg.rlpBytes().toString("hex")).deep.equal("c3040ac0"); }); it("ResponseBodyMessage RLP encoding test", function() { @@ -27,6 +27,6 @@ describe("Check BlockSyncMessage RLP encoding", function() { id: new U256(10), message }); - expect([...msg.rlpBytes()]).deep.equal([196, 5, 10, 193, 192]); + expect(msg.rlpBytes().toString("hex")).deep.equal("c8050ac5840204c1c0"); }); }); diff --git a/test/src/helper/mock/test/txSyncMessage.test.ts b/test/src/helper/mock/test/txSyncMessage.test.ts index 2b281be507..c90929b2d2 100644 --- a/test/src/helper/mock/test/txSyncMessage.test.ts +++ b/test/src/helper/mock/test/txSyncMessage.test.ts @@ -8,6 +8,6 @@ describe("Check TransactionSyncMessage RLP encoding", function() { type: "transactions", data: [] }); - expect([...msg.rlpBytes()]).deep.equal([192]); + expect(msg.rlpBytes().toString("hex")).deep.equal("830100c0"); }); }); From 32ce4f76de51719b5c20becf6a9c3d30d5158d8f Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Thu, 7 May 2020 18:10:42 +0900 Subject: [PATCH 46/55] Change mock's Header::default function to static function --- test/src/helper/mock/cHeader.ts | 37 +++++++++++++++++---------------- 1 file changed, 19 insertions(+), 18 deletions(-) diff --git a/test/src/helper/mock/cHeader.ts b/test/src/helper/mock/cHeader.ts index a8f73a771f..d3e72c5d3e 100644 --- a/test/src/helper/mock/cHeader.ts +++ b/test/src/helper/mock/cHeader.ts @@ -51,6 +51,25 @@ export class Header { return header; } + + public static default(): Header { + return new Header( + new H256( + "0000000000000000000000000000000000000000000000000000000000000000" + ), + new U256(0), + new U256(0), + new H160("0000000000000000000000000000000000000000"), + Buffer.alloc(0), + BLAKE_NULL_RLP, + BLAKE_NULL_RLP, + new U256( + "0000000000000000000000000000000000000000000000000000000000000000" + ), + [] + ); + } + private parentHash: H256; private timestamp: U256; private number: U256; @@ -137,24 +156,6 @@ export class Header { return this.score; } - public default(): Header { - return new Header( - new H256( - "0000000000000000000000000000000000000000000000000000000000000000" - ), - new U256(0), - new U256(0), - new H160("0000000000000000000000000000000000000000"), - Buffer.alloc(0), - BLAKE_NULL_RLP, - BLAKE_NULL_RLP, - new U256( - "0000000000000000000000000000000000000000000000000000000000000000" - ), - [] - ); - } - public toEncodeObject(): Array { return [ this.parentHash.toEncodeObject(), From 13fc568c1cb5efc931698d5ab480407a464fd0f2 Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Thu, 7 May 2020 18:12:07 +0900 Subject: [PATCH 47/55] Change seal serialize code in mock The seal is an array of any RLP data. Wrapping them with Buffer makes invalid RLP encoding. --- test/src/helper/mock/cHeader.ts | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/test/src/helper/mock/cHeader.ts b/test/src/helper/mock/cHeader.ts index d3e72c5d3e..9bf3ec94a0 100644 --- a/test/src/helper/mock/cHeader.ts +++ b/test/src/helper/mock/cHeader.ts @@ -78,7 +78,7 @@ export class Header { private transactionsRoot: H256; private stateRoot: H256; private score: U256; - private seal: number[][]; + private seal: any[]; private hash: null | H256; private bareHash: null | H256; @@ -91,7 +91,7 @@ export class Header { transactionsRoot: H256, stateRoot: H256, score: U256, - seal: number[][], + seal: any[], hash?: H256, bareHash?: H256 ) { @@ -140,7 +140,7 @@ export class Header { this.score = score; } - public setSeal(seal: number[][]) { + public setSeal(seal: any[]) { this.seal = seal; } @@ -166,7 +166,7 @@ export class Header { this.number.toEncodeObject(), this.timestamp.toEncodeObject(), this.extraData - ].concat(this.seal.map(seal => Buffer.of(...seal))); + ].concat(this.seal); } public rlpBytes(): Buffer { From 1512b81fd93a9ebe2172c966821e39d24355fb23 Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Thu, 7 May 2020 18:16:01 +0900 Subject: [PATCH 48/55] Add Header RLP encoding test in mock --- test/src/helper/mock/cHeader.ts | 4 ++ test/src/helper/mock/test/header.test.ts | 67 ++++++++++++++++++++++++ 2 files changed, 71 insertions(+) create mode 100644 test/src/helper/mock/test/header.test.ts diff --git a/test/src/helper/mock/cHeader.ts b/test/src/helper/mock/cHeader.ts index 9bf3ec94a0..277a56ace8 100644 --- a/test/src/helper/mock/cHeader.ts +++ b/test/src/helper/mock/cHeader.ts @@ -144,6 +144,10 @@ export class Header { this.seal = seal; } + public getParentHash(): H256 | null { + return this.parentHash; + } + public getHash(): H256 | null { return this.hash; } diff --git a/test/src/helper/mock/test/header.test.ts b/test/src/helper/mock/test/header.test.ts new file mode 100644 index 0000000000..968e5b00ef --- /dev/null +++ b/test/src/helper/mock/test/header.test.ts @@ -0,0 +1,67 @@ +import { Buffer } from "buffer"; +import { expect } from "chai"; +import "mocha"; +import * as RLP from "rlp"; +import { + getPublicFromPrivate, + H256, + U256, + H160, + blake256, + blake160, + signEcdsa, + signSchnorr, + getAccountIdFromPublic +} from "codechain-primitives"; +import { Header } from "../cHeader"; + +describe("Check Header RLP encoding", function() { + it("empty Header RLP encoding test", function() { + const header = Header.default(); + expect(header.rlpBytes().toString("hex")).deep.equal( + "f87ca00000000000000000000000000000000000000000000000000000000000000000940000000000000000000000000000000000000000a045b0cfc220ceec5b7c1c62c4d4193d38e4eba48e8815729ce75f9c0ab0e4c1c0a045b0cfc220ceec5b7c1c62c4d4193d38e4eba48e8815729ce75f9c0ab0e4c1c080808080" + ); + }); + + it("Header RLP encoding test", function() { + const privateKey = + "ede1d4ccb4ec9a8bbbae9a13db3f4a7b56ea04189be86ac3a6a439d9a0a1addd"; + const publicKey = getPublicFromPrivate(privateKey); + const header = Header.default(); + header.setNumber(new U256(4)); + header.setAuthor(new H160(getAccountIdFromPublic(publicKey))); + const bitset = Buffer.alloc(100, 0); + bitset[0] = 4; + const signature = createPrecommit({ + height: 3, + view: 0, + step: 2, + parentHash: header.getParentHash()!, + privateKey + }); + header.setSeal([0, 0, [Buffer.from(signature, "hex")], bitset]); + expect(header.rlpBytes().toString("hex")).deep.equal( + "f90128a00000000000000000000000000000000000000000000000000000000000000000946fe64ffa3a46c074226457c90ccb32dc06ccced1a045b0cfc220ceec5b7c1c62c4d4193d38e4eba48e8815729ce75f9c0ab0e4c1c0a045b0cfc220ceec5b7c1c62c4d4193d38e4eba48e8815729ce75f9c0ab0e4c1c0800480808080f842b8405aa028f952416218d440568ddf58b42a02515d53dbe40aec6d8fbc3a0b9de171bd1fa833c2bf9e7b950414ca4bbc261c662d50372340c0f7b41ab0a12d11a789b86404000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000" + ); + }); + + function createPrecommit({ + height, + view, + step, + parentHash, + privateKey + }: { + height: number; + view: number; + step: number; + parentHash: H256; + privateKey: string; + }): string { + const voteOn = [[height, view, step], [parentHash.toEncodeObject()]]; + const serializedVoteOn = RLP.encode(voteOn); + const message = blake256(serializedVoteOn); + const { r, s } = signSchnorr(message, privateKey); + return r + s; + } +}); From 56db6e9093f3315e44b034cb1593d12229305bf5 Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Thu, 7 May 2020 18:27:09 +0900 Subject: [PATCH 49/55] Remove PartialEq derive from Header and Block Since Header has a cache of its hash using RefCell, the existence of the cache changes the compare result. --- core/src/block.rs | 2 +- sync/src/block/message/mod.rs | 29 ++++++++++++++++++++++------- sync/src/block/message/response.rs | 17 +++++++++++------ sync/src/transaction/message.rs | 17 +++++++++++++---- types/src/header.rs | 2 +- 5 files changed, 48 insertions(+), 19 deletions(-) diff --git a/core/src/block.rs b/core/src/block.rs index 7154166f4a..421c840883 100644 --- a/core/src/block.rs +++ b/core/src/block.rs @@ -34,7 +34,7 @@ use rlp::{Decodable, DecoderError, Encodable, Rlp, RlpStream}; use std::collections::HashSet; /// A block, encoded as it is on the block chain. -#[derive(Debug, Clone, PartialEq)] +#[derive(Debug, Clone)] pub struct Block { /// The header of this block pub header: Header, diff --git a/sync/src/block/message/mod.rs b/sync/src/block/message/mod.rs index 3ecdf124cf..8ca850df56 100644 --- a/sync/src/block/message/mod.rs +++ b/sync/src/block/message/mod.rs @@ -62,7 +62,7 @@ impl Decodable for MessageID { } } -#[derive(Debug, PartialEq)] +#[derive(Debug)] pub enum Message { Status { total_score: U256, @@ -162,29 +162,44 @@ impl Decodable for Message { #[cfg(test)] mod tests { + use super::*; use primitives::H256; - use rlp::rlp_encode_and_decode_test; - use super::*; + /// For a type that does not have PartialEq, uses Debug instead. + fn assert_eq_by_debug(a: &T, b: &T) { + assert_eq!(format!("{:?}", a), format!("{:?}", b)); + } #[test] fn status_message_rlp() { - rlp_encode_and_decode_test!(Message::Status { + let status_message = Message::Status { total_score: U256::default(), best_hash: H256::default().into(), genesis_hash: H256::default().into(), - }); + }; + let encoded = rlp::encode(&status_message); + let decoded: Message = rlp::decode(&encoded).unwrap(); + + assert_eq_by_debug(&status_message, &decoded) } #[test] fn request_bodies_message_rlp() { let request_id = 10; - rlp_encode_and_decode_test!(Message::Request(request_id, RequestMessage::Bodies(vec![]))); + let message = Message::Request(request_id, RequestMessage::Bodies(vec![])); + let encoded = rlp::encode(&message); + let decoded: Message = rlp::decode(&encoded).unwrap(); + + assert_eq_by_debug(&message, &decoded) } #[test] fn request_state_head_rlp() { let request_id = 10; - rlp_encode_and_decode_test!(Message::Request(request_id, RequestMessage::StateHead(H256::random().into()))); + let message = Message::Request(request_id, RequestMessage::StateHead(H256::random().into())); + let encoded = rlp::encode(&message); + let decoded: Message = rlp::decode(&encoded).unwrap(); + + assert_eq_by_debug(&message, &decoded) } } diff --git a/sync/src/block/message/response.rs b/sync/src/block/message/response.rs index 76ec905467..8217fe1f67 100644 --- a/sync/src/block/message/response.rs +++ b/sync/src/block/message/response.rs @@ -20,7 +20,7 @@ use ctypes::Header; use rlp::{DecoderError, Encodable, Rlp, RlpStream}; use snap; -#[derive(Debug, PartialEq)] +#[derive(Debug)] pub enum ResponseMessage { Headers(Vec
), Bodies(Vec>), @@ -152,6 +152,11 @@ mod tests { ResponseMessage::decode(id, &rlp).unwrap() } + /// For a type that does not have PartialEq, uses Debug instead. + fn assert_eq_by_debug(a: &T, b: &T) { + assert_eq!(format!("{:?}", a), format!("{:?}", b)); + } + #[test] fn headers_message_rlp() { let headers = vec![Header::default()]; @@ -160,13 +165,13 @@ mod tests { }); let message = ResponseMessage::Headers(headers); - assert_eq!(message, decode_bytes(message.message_id(), message.rlp_bytes().as_ref())); + assert_eq_by_debug(&message, &decode_bytes(message.message_id(), message.rlp_bytes().as_ref())) } #[test] fn bodies_message_rlp() { let message = ResponseMessage::Bodies(vec![vec![]]); - assert_eq!(message, decode_bytes(message.message_id(), message.rlp_bytes().as_ref())); + assert_eq_by_debug(&message, &decode_bytes(message.message_id(), message.rlp_bytes().as_ref())); let tx = UnverifiedTransaction::new( Transaction { @@ -181,18 +186,18 @@ mod tests { ); let message = ResponseMessage::Bodies(vec![vec![tx]]); - assert_eq!(message, decode_bytes(message.message_id(), message.rlp_bytes().as_ref())); + assert_eq_by_debug(&message, &decode_bytes(message.message_id(), message.rlp_bytes().as_ref())); } #[test] fn state_head_message_rlp() { let message = ResponseMessage::StateHead(vec![]); - assert_eq!(message, decode_bytes(message.message_id(), message.rlp_bytes().as_ref())); + assert_eq_by_debug(&message, &decode_bytes(message.message_id(), message.rlp_bytes().as_ref())); } #[test] fn state_chunk_message_rlp() { let message = ResponseMessage::StateChunk(vec![]); - assert_eq!(message, decode_bytes(message.message_id(), message.rlp_bytes().as_ref())); + assert_eq_by_debug(&message, &decode_bytes(message.message_id(), message.rlp_bytes().as_ref())); } } diff --git a/sync/src/transaction/message.rs b/sync/src/transaction/message.rs index c16a1b614f..5cf45da61e 100644 --- a/sync/src/transaction/message.rs +++ b/sync/src/transaction/message.rs @@ -63,17 +63,23 @@ impl Decodable for Message { #[cfg(test)] mod tests { - use rlp::rlp_encode_and_decode_test; - use ccore::UnverifiedTransaction; use ckey::{Address, Signature}; use ctypes::transaction::{Action, Transaction}; use super::Message; + /// For a type that does not have PartialEq, uses Debug instead. + fn assert_eq_by_debug(a: &T, b: &T) { + assert_eq!(format!("{:?}", a), format!("{:?}", b)); + } + #[test] fn transactions_message_rlp() { - rlp_encode_and_decode_test!(Message::Transactions(Vec::new())); + let message = Message::Transactions(Vec::new()); + let encoded = rlp::encode(&message); + let decoded: Message = rlp::decode(&encoded).unwrap(); + assert_eq_by_debug(&message, &decoded); } #[test] @@ -90,6 +96,9 @@ mod tests { Signature::default(), ); - rlp_encode_and_decode_test!(Message::Transactions(vec![tx])); + let message = Message::Transactions(vec![tx]); + let encoded = rlp::encode(&message); + let decoded: Message = rlp::decode(&encoded).unwrap(); + assert_eq_by_debug(&message, &decoded); } } diff --git a/types/src/header.rs b/types/src/header.rs index c9027e8e2f..9cae05f388 100644 --- a/types/src/header.rs +++ b/types/src/header.rs @@ -32,7 +32,7 @@ pub enum Seal { } /// A block header. -#[derive(Debug, Clone, PartialEq)] +#[derive(Debug, Clone)] pub struct Header { /// Parent hash. parent_hash: BlockHash, From d1caafd876cc4e8533816173784e4d154cc474a0 Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Thu, 7 May 2020 18:35:34 +0900 Subject: [PATCH 50/55] Add a hint comment that helps programmer to manage tests --- core/src/consensus/tendermint/mod.rs | 44 +++++++++++++++++++++++- test/src/helper/mock/test/header.test.ts | 2 ++ types/src/header.rs | 13 +++++++ 3 files changed, 58 insertions(+), 1 deletion(-) diff --git a/core/src/consensus/tendermint/mod.rs b/core/src/consensus/tendermint/mod.rs index c50b6f8d31..4523840ef6 100644 --- a/core/src/consensus/tendermint/mod.rs +++ b/core/src/consensus/tendermint/mod.rs @@ -124,9 +124,10 @@ const SEAL_FIELDS: usize = 4; #[cfg(test)] mod tests { use ccrypto::blake256; - use ckey::Address; + use ckey::{public_to_address, sign_schnorr, Address, KeyPair, Private}; use ctypes::{CommonParams, Header}; use primitives::Bytes; + use std::str::FromStr; use super::super::BitSet; use super::message::VoteStep; @@ -176,6 +177,47 @@ mod tests { addr } + #[test] + fn serialize_deserialize_test() { + let key_pair = { + let serialized_priv_key = "ede1d4ccb4ec9a8bbbae9a13db3f4a7b56ea04189be86ac3a6a439d9a0a1addd"; + let private_key = Private::from_str(&serialized_priv_key).unwrap(); + KeyPair::from_private(private_key).unwrap() + }; + + let mut header = Header::default(); + header.set_number(4); + header.set_author(public_to_address(key_pair.public())); + + let precommit_bitset = { + let mut bitset = BitSet::new(); + bitset.set(2); + bitset + }; + let signature = { + let height = 3; + let view = 0; + let step = Step::Precommit; + let vote_on = VoteOn { + step: VoteStep::new(height, view, step), + block_hash: Some(*header.parent_hash()), + }; + sign_schnorr(key_pair.private(), &vote_on.hash()).unwrap() + }; + let seal = Seal::Tendermint { + prev_view: 0, + cur_view: 0, + precommits: vec![signature], + precommit_bitset, + }; + header.set_seal(seal.seal_fields().unwrap()); + + let encoded = rlp::encode(&header); + let decoded: Header = rlp::decode(&encoded).unwrap(); + + assert_eq!(header.hash(), decoded.hash()); + } + #[test] #[ignore] // FIXME fn verification_fails_on_short_seal() { diff --git a/test/src/helper/mock/test/header.test.ts b/test/src/helper/mock/test/header.test.ts index 968e5b00ef..3de02e23d1 100644 --- a/test/src/helper/mock/test/header.test.ts +++ b/test/src/helper/mock/test/header.test.ts @@ -18,6 +18,7 @@ import { Header } from "../cHeader"; describe("Check Header RLP encoding", function() { it("empty Header RLP encoding test", function() { const header = Header.default(); + // Find the empty header's rlp encoded data in the unit test in header.rs file expect(header.rlpBytes().toString("hex")).deep.equal( "f87ca00000000000000000000000000000000000000000000000000000000000000000940000000000000000000000000000000000000000a045b0cfc220ceec5b7c1c62c4d4193d38e4eba48e8815729ce75f9c0ab0e4c1c0a045b0cfc220ceec5b7c1c62c4d4193d38e4eba48e8815729ce75f9c0ab0e4c1c080808080" ); @@ -40,6 +41,7 @@ describe("Check Header RLP encoding", function() { privateKey }); header.setSeal([0, 0, [Buffer.from(signature, "hex")], bitset]); + // Find the header's rlp encoded data in the unit test in the tendermint/mod.rs file expect(header.rlpBytes().toString("hex")).deep.equal( "f90128a00000000000000000000000000000000000000000000000000000000000000000946fe64ffa3a46c074226457c90ccb32dc06ccced1a045b0cfc220ceec5b7c1c62c4d4193d38e4eba48e8815729ce75f9c0ab0e4c1c0a045b0cfc220ceec5b7c1c62c4d4193d38e4eba48e8815729ce75f9c0ab0e4c1c0800480808080f842b8405aa028f952416218d440568ddf58b42a02515d53dbe40aec6d8fbc3a0b9de171bd1fa833c2bf9e7b950414ca4bbc261c662d50372340c0f7b41ab0a12d11a789b86404000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000" ); diff --git a/types/src/header.rs b/types/src/header.rs index 9cae05f388..e88bb60f61 100644 --- a/types/src/header.rs +++ b/types/src/header.rs @@ -305,3 +305,16 @@ impl Encodable for Header { self.stream_rlp(s, &Seal::With); } } + +#[cfg(test)] +mod tests { + use super::*; + + #[test] + fn serialize_deserialize_test() { + let empty = Header::default(); + let encoded = rlp::encode(&empty); + let decoded: Header = rlp::decode(&encoded).unwrap(); + assert_eq!(empty.hash(), decoded.hash()); + } +} From 6d7d6826497f26c8831efeb64a0ee192650ad3c7 Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Wed, 20 May 2020 11:28:59 +0900 Subject: [PATCH 51/55] Make typescript check type errors in test files --- test/package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/package.json b/test/package.json index 2120b91b30..2d43bd56da 100644 --- a/test/package.json +++ b/test/package.json @@ -22,7 +22,7 @@ "test-mock": "mocha -r ts-node/register --timeout 5000 \"src/helper/mock/**/*.test.ts\"", "tendermint-test-local": "cargo build --release && NODE_ENV=production ts-node src/tendermint.test/local.ts", "tendermint-test-remote": "NODE_ENV=production ts-node src/tendermint.test/remote.ts", - "lint": "tslint -p . && prettier 'src/**/*.{ts, json}' -l", + "lint": "tsc -p . --noEmit && tslint -p . && prettier 'src/**/*.{ts, json}' -l", "fmt": "tslint -p . --fix && prettier 'src/**/*.{ts, json}' --write" }, "devDependencies": { From 9e2b373c2be1a20bf800dcaccb6634353182b304 Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Wed, 20 May 2020 12:03:17 +0900 Subject: [PATCH 52/55] Make CodeChain makes blocks slowly if RUN_ON_TEST is set This will make CodeChain in tests not to increase view to high. Before this commit, some tests (for example dv.nomination.test.ts) sometimes creates a block with a very high view like 9. It was because blocks were created so fast and the timestamp of a block is too future for CodeChain. --- core/src/miner/miner.rs | 10 +++++++++- test/src/helper/spawn.ts | 1 + 2 files changed, 10 insertions(+), 1 deletion(-) diff --git a/core/src/miner/miner.rs b/core/src/miner/miner.rs index 63903de306..51a5ff5e70 100644 --- a/core/src/miner/miner.rs +++ b/core/src/miner/miner.rs @@ -46,7 +46,7 @@ use std::iter::once; use std::ops::Range; use std::sync::atomic::{AtomicBool, Ordering}; use std::sync::Arc; -use std::time::{Duration, Instant}; +use std::time::{Duration, Instant, SystemTime, UNIX_EPOCH}; /// Configures the behaviour of the miner. #[derive(Debug, PartialEq)] @@ -991,6 +991,14 @@ impl MinerService for Miner { } }; + if std::env::var("RUN_ON_TEST").is_ok() { + let now = SystemTime::now().duration_since(UNIX_EPOCH).expect("There is no time machine.").as_secs(); + if block.header().timestamp() > now { + let delta = block.header().timestamp() - now; + std::thread::sleep(std::time::Duration::from_secs(delta)); + } + } + match self.engine.seals_internally() { Some(true) => { ctrace!(MINER, "update_sealing: engine indicates internal sealing"); diff --git a/test/src/helper/spawn.ts b/test/src/helper/spawn.ts index b8c7c63a8f..0c7bc87a7b 100644 --- a/test/src/helper/spawn.ts +++ b/test/src/helper/spawn.ts @@ -255,6 +255,7 @@ export default class CodeChain { { cwd: projectRoot, env: { + RUN_ON_TEST: "1", ...process.env, ...this.env } From 164321dd3b7e3f64e8e453a20327306303a19940 Mon Sep 17 00:00:00 2001 From: Seulgi Kim Date: Sun, 31 May 2020 19:08:23 +0900 Subject: [PATCH 53/55] Make the client hold the miner directly Currently, the client access the miner through the importer. It's better to give a method to access the miner directly. --- codechain/test_lock.rs | 0 core/src/client/client.rs | 54 ++++++++++++++++++------------------- core/src/client/importer.rs | 2 +- 3 files changed, 27 insertions(+), 29 deletions(-) delete mode 100644 codechain/test_lock.rs diff --git a/codechain/test_lock.rs b/codechain/test_lock.rs deleted file mode 100644 index e69de29bb2..0000000000 diff --git a/core/src/client/client.rs b/core/src/client/client.rs index d52f0cc77a..4a6965184b 100644 --- a/core/src/client/client.rs +++ b/core/src/client/client.rs @@ -75,6 +75,9 @@ pub struct Client { importer: Importer, + /// Handles block sealing + miner: Arc, + /// Timer for reseal_min_period/reseal_max_period on miner client reseal_timer: TimerApi, } @@ -106,7 +109,7 @@ impl Client { let engine = scheme.engine.clone(); - let importer = Importer::try_new(config, engine.clone(), message_channel.clone(), miner)?; + let importer = Importer::try_new(config, engine.clone(), message_channel.clone(), Arc::clone(&miner))?; let genesis_accounts = scheme.genesis_accounts(); let client = Arc::new(Client { @@ -119,6 +122,7 @@ impl Client { queue_transactions: AtomicUsize::new(0), genesis_accounts, importer, + miner, reseal_timer, }); @@ -199,7 +203,7 @@ impl Client { /// This is triggered by a message coming from a engine when a new block should be created pub fn update_sealing(&self, parent_block: BlockId, allow_empty_block: bool) { - self.importer.miner.update_sealing(self, parent_block, allow_empty_block); + self.miner.update_sealing(self, parent_block, allow_empty_block); } fn block_hash(chain: &BlockChain, id: &BlockId) -> Option { @@ -234,7 +238,7 @@ impl Client { self.queue_transactions.fetch_sub(transactions.len(), AtomicOrdering::SeqCst); let transactions: Vec = transactions.iter().filter_map(|bytes| Rlp::new(bytes).as_val().ok()).collect(); - let results = self.importer.miner.import_external_transactions(self, transactions); + let results = self.miner.import_external_transactions(self, transactions); results.len() } @@ -264,7 +268,7 @@ impl Client { } let (enacted, retracted) = self.importer.calculate_enacted_retracted(&[route]); - self.importer.miner.chain_new_blocks(self, &[], &[], &enacted, &retracted); + self.miner.chain_new_blocks(self, &[], &[], &enacted, &retracted); self.new_blocks(&[], &[], &enacted, &retracted, &[]); } @@ -315,7 +319,7 @@ impl TimeoutHandler for Client { match token { RESEAL_MAX_TIMER_TOKEN => { // Working in PoW only - if self.engine().seals_internally().is_none() && !self.importer.miner.prepare_work_sealing(self) { + if self.engine().seals_internally().is_none() && !self.miner.prepare_work_sealing(self) { self.update_sealing(BlockId::Latest, true); } } @@ -547,7 +551,7 @@ impl EngineClient for Client { /// Submit a seal for a block in the mining queue. fn submit_seal(&self, block_hash: BlockHash, seal: Vec) { - if self.importer.miner.submit_seal(self, block_hash, seal).is_err() { + if self.miner.submit_seal(self, block_hash, seal).is_err() { cwarn!(CLIENT, "Wrong internal seal submission!") } } @@ -660,7 +664,7 @@ impl ImportBlock for Client { route }; let (enacted, retracted) = self.importer.calculate_enacted_retracted(&[route]); - self.importer.miner.chain_new_blocks(self, &[h], &[], &enacted, &retracted); + self.miner.chain_new_blocks(self, &[h], &[], &enacted, &retracted); self.new_blocks(&[h], &[], &enacted, &retracted, &[h]); self.db().flush().expect("DB flush failed."); Ok(h) @@ -668,10 +672,7 @@ impl ImportBlock for Client { fn set_min_timer(&self) { self.reseal_timer.cancel(RESEAL_MIN_TIMER_TOKEN).expect("Reseal min timer clear succeeds"); - match self - .reseal_timer - .schedule_once(self.importer.miner.get_options().reseal_min_period, RESEAL_MIN_TIMER_TOKEN) - { + match self.reseal_timer.schedule_once(self.miner.get_options().reseal_min_period, RESEAL_MIN_TIMER_TOKEN) { Ok(_) => {} Err(TimerScheduleError::TokenAlreadyScheduled) => { // Since set_min_timer could be called in multi thread, ignore the TokenAlreadyScheduled error @@ -682,10 +683,7 @@ impl ImportBlock for Client { fn set_max_timer(&self) { self.reseal_timer.cancel(RESEAL_MAX_TIMER_TOKEN).expect("Reseal max timer clear succeeds"); - match self - .reseal_timer - .schedule_once(self.importer.miner.get_options().reseal_max_period, RESEAL_MAX_TIMER_TOKEN) - { + match self.reseal_timer.schedule_once(self.miner.get_options().reseal_max_period, RESEAL_MAX_TIMER_TOKEN) { Ok(_) => {} Err(TimerScheduleError::TokenAlreadyScheduled) => { // Since set_max_timer could be called in multi thread, ignore the TokenAlreadyScheduled error @@ -703,7 +701,7 @@ impl BlockChainClient for Client { /// Import own transaction fn queue_own_transaction(&self, transaction: SignedTransaction) -> Result<(), Error> { - self.importer.miner.import_own_transaction(self, transaction)?; + self.miner.import_own_transaction(self, transaction)?; Ok(()) } @@ -726,26 +724,26 @@ impl BlockChainClient for Client { } fn delete_all_pending_transactions(&self) { - self.importer.miner.delete_all_pending_transactions(); + self.miner.delete_all_pending_transactions(); } fn ready_transactions(&self, range: Range) -> PendingSignedTransactions { - self.importer.miner.ready_transactions(range) + self.miner.ready_transactions(range) } fn count_pending_transactions(&self, range: Range) -> usize { - self.importer.miner.count_pending_transactions(range) + self.miner.count_pending_transactions(range) } fn future_included_count_pending_transactions(&self, range: Range) -> usize { - self.importer.miner.future_included_count_pending_transactions(range) + self.miner.future_included_count_pending_transactions(range) } fn future_ready_transactions(&self, range: Range) -> PendingSignedTransactions { - self.importer.miner.future_ready_transactions(range) + self.miner.future_ready_transactions(range) } fn is_pending_queue_empty(&self) -> bool { - self.importer.miner.status().transactions_in_pending_queue == 0 + self.miner.status().transactions_in_pending_queue == 0 } fn block_number(&self, id: &BlockId) -> Option { @@ -895,27 +893,27 @@ impl BlockProducer for Client { impl MiningBlockChainClient for Client { fn get_malicious_users(&self) -> Vec
{ - self.importer.miner.get_malicious_users() + self.miner.get_malicious_users() } fn release_malicious_users(&self, prisoner_vec: Vec
) { - self.importer.miner.release_malicious_users(prisoner_vec) + self.miner.release_malicious_users(prisoner_vec) } fn imprison_malicious_users(&self, prisoner_vec: Vec
) { - self.importer.miner.imprison_malicious_users(prisoner_vec) + self.miner.imprison_malicious_users(prisoner_vec) } fn get_immune_users(&self) -> Vec
{ - self.importer.miner.get_immune_users() + self.miner.get_immune_users() } fn register_immune_users(&self, immune_user_vec: Vec
) { - self.importer.miner.register_immune_users(immune_user_vec) + self.miner.register_immune_users(immune_user_vec) } fn mem_pool_min_fees(&self) -> MemPoolMinFees { - self.importer.miner.get_options().mem_pool_min_fees + self.miner.get_options().mem_pool_min_fees } } diff --git a/core/src/client/importer.rs b/core/src/client/importer.rs index c98f429281..da46a1734a 100644 --- a/core/src/client/importer.rs +++ b/core/src/client/importer.rs @@ -50,7 +50,7 @@ pub struct Importer { pub header_queue: HeaderQueue, /// Handles block sealing - pub miner: Arc, + miner: Arc, /// CodeChain engine to be used during import pub engine: Arc, From 6aea3b85eb381ebeda267982552d60fc4027e386 Mon Sep 17 00:00:00 2001 From: Junha Yang0 Date: Thu, 9 Jul 2020 11:58:20 +0900 Subject: [PATCH 54/55] Upgrade parking_lot to 0.11.0 --- Cargo.lock | 164 +++++++++++++++++++++++++++-------------- Cargo.toml | 2 +- core/Cargo.toml | 2 +- discovery/Cargo.toml | 2 +- key/Cargo.toml | 2 +- keystore/Cargo.toml | 2 +- network/Cargo.toml | 2 +- rpc/Cargo.toml | 2 +- state/Cargo.toml | 2 +- stratum/Cargo.toml | 2 +- util/io/Cargo.toml | 2 +- util/logger/Cargo.toml | 2 +- util/timer/Cargo.toml | 2 +- 13 files changed, 122 insertions(+), 66 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 8e460ce469..ea7e508d3e 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -62,7 +62,7 @@ version = "0.11.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ee49baf6cb617b853aa8d93bf420db2383fab46d314482ca2803b40d5fde979b" dependencies = [ - "winapi 0.3.6", + "winapi 0.3.9", ] [[package]] @@ -94,7 +94,7 @@ checksum = "2fc4a1aa4c24c0718a250f0681885c1af91419d242f29eb8f2ab28502d80dbd1" dependencies = [ "libc", "termion", - "winapi 0.3.6", + "winapi 0.3.9", ] [[package]] @@ -113,7 +113,7 @@ dependencies = [ "cfg-if", "libc", "rustc-demangle", - "winapi 0.3.6", + "winapi 0.3.9", ] [[package]] @@ -144,9 +144,9 @@ checksum = "1955ebdd52d5c5f1fb4f94e97aa241c2ce5729d200b3c34fc71ac6ff7a7cc556" [[package]] name = "bitflags" -version = "1.0.3" +version = "1.2.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d0c54bb8f454c567f21197eefcdbf5679d0bd99f2ddbe52e84c77061952e6789" +checksum = "cf1de2fe8c75bc145a2f577add951f8134889b4795d47466a54a5c846d691693" [[package]] name = "bitstring" @@ -302,6 +302,15 @@ dependencies = [ "bitflags", ] +[[package]] +name = "cloudabi" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4344512281c643ae7638bbabc3af17a11307803ec8f0fcad9fae512a8bf36467" +dependencies = [ + "bitflags", +] + [[package]] name = "cmake" version = "0.1.35" @@ -342,7 +351,7 @@ dependencies = [ "log 0.4.6", "never-type", "panic_hook", - "parking_lot 0.6.4", + "parking_lot 0.11.0", "primitives", "rlp", "rpassword", @@ -383,7 +392,7 @@ dependencies = [ "lru-cache", "merkle-trie", "num-rational", - "parking_lot 0.6.4", + "parking_lot 0.11.0", "primitives", "rand 0.6.1", "rand_xorshift", @@ -439,7 +448,7 @@ dependencies = [ "lazy_static 1.2.0", "log 0.4.6", "never-type", - "parking_lot 0.6.4", + "parking_lot 0.11.0", "primitives", "rand 0.6.1", "rlp", @@ -454,7 +463,7 @@ dependencies = [ "crossbeam", "log 0.4.6", "mio", - "parking_lot 0.6.4", + "parking_lot 0.11.0", ] [[package]] @@ -477,7 +486,7 @@ dependencies = [ "codechain-crypto", "lazy_static 1.2.0", "never-type", - "parking_lot 0.6.4", + "parking_lot 0.11.0", "primitives", "rand 0.6.1", "rand_xorshift", @@ -501,7 +510,7 @@ dependencies = [ "libc", "log 0.4.6", "matches", - "parking_lot 0.6.4", + "parking_lot 0.11.0", "primitives", "rand 0.6.1", "rustc-hex 1.0.0", @@ -522,7 +531,7 @@ dependencies = [ "env_logger 0.6.0", "lazy_static 1.2.0", "log 0.4.6", - "parking_lot 0.6.4", + "parking_lot 0.11.0", "sendgrid", "serde", "serde_derive", @@ -547,7 +556,7 @@ dependencies = [ "log 0.4.6", "mio", "never-type", - "parking_lot 0.6.4", + "parking_lot 0.11.0", "primitives", "rand 0.6.1", "rlp", @@ -582,7 +591,7 @@ dependencies = [ "kvdb-rocksdb", "lazy_static 1.2.0", "log 0.4.6", - "parking_lot 0.6.4", + "parking_lot 0.11.0", "primitives", "rand 0.6.1", "rlp", @@ -610,7 +619,7 @@ dependencies = [ "log 0.4.6", "lru-cache", "merkle-trie", - "parking_lot 0.6.4", + "parking_lot 0.11.0", "primitives", "rlp", "rlp_derive", @@ -629,7 +638,7 @@ dependencies = [ "jsonrpc-derive", "jsonrpc-tcp-server", "log 0.4.6", - "parking_lot 0.6.4", + "parking_lot 0.11.0", "primitives", "tokio-core", "tokio-io", @@ -668,7 +677,7 @@ version = "0.1.0" dependencies = [ "codechain-logger", "log 0.4.6", - "parking_lot 0.6.4", + "parking_lot 0.11.0", ] [[package]] @@ -881,7 +890,7 @@ dependencies = [ "openssl-sys", "pkg-config", "vcpkg", - "winapi 0.3.6", + "winapi 0.3.9", ] [[package]] @@ -1079,7 +1088,7 @@ dependencies = [ "lazy_static 1.2.0", "libc", "libloading", - "winapi 0.3.6", + "winapi 0.3.9", ] [[package]] @@ -1216,7 +1225,7 @@ version = "0.4.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "1679e6ea370dee694f91f1dc469bf94cf8f52051d147aec3e1f9497c6fc22461" dependencies = [ - "winapi 0.3.6", + "winapi 0.3.9", ] [[package]] @@ -1357,6 +1366,12 @@ version = "1.0.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7e81a7c05f79578dbc15793d8b619db9ba32b4577003ef3af1a91c416798c58d" +[[package]] +name = "instant" +version = "0.1.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5b141fdc7836c525d4d594027d318c84161ca17aaf8113ab1f81ab93ae897485" + [[package]] name = "interleaved-ordered" version = "0.1.1" @@ -1548,9 +1563,9 @@ checksum = "ddba4c30a78328befecec92fc94970e53b3ae385827d28620f0f5bb2493081e0" [[package]] name = "libc" -version = "0.2.62" +version = "0.2.74" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "34fcd2c08d2f832f376f4173a231990fa5aef4e99fb569867318a227ef4c06ba" +checksum = "a2f02823cf78b754822df5f7f268fb59822e7296276d3e069d8e8cb26a14bd10" [[package]] name = "libflate" @@ -1570,7 +1585,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f2b111a074963af1d37a139918ac6d49ad1d0d5e47f72fd55388619691a7d753" dependencies = [ "cc", - "winapi 0.3.6", + "winapi 0.3.9", ] [[package]] @@ -1627,7 +1642,16 @@ version = "0.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f8912e782533a93a167888781b836336a6ca5da6175c05944c86cf28c31104dc" dependencies = [ - "scopeguard 1.0.0", + "scopeguard 1.1.0", +] + +[[package]] +name = "lock_api" +version = "0.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "28247cc5a5be2f05fbcd76dd0cf2c7d3b5400cb978a28042abcd4fa0b3f8261c" +dependencies = [ + "scopeguard 1.1.0", ] [[package]] @@ -1760,7 +1784,7 @@ dependencies = [ "log 0.4.6", "mio", "miow 0.3.3", - "winapi 0.3.6", + "winapi 0.3.9", ] [[package]] @@ -1793,7 +1817,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "396aa0f2003d7df8395cb93e09871561ccc3e785f0acb369170e8cc74ddf9226" dependencies = [ "socket2", - "winapi 0.3.6", + "winapi 0.3.9", ] [[package]] @@ -1831,7 +1855,7 @@ checksum = "9044faf1413a1057267be51b5afba8eb1090bd2231c693664aa1db716fe1eae0" dependencies = [ "cfg-if", "libc", - "winapi 0.3.6", + "winapi 0.3.9", ] [[package]] @@ -2014,7 +2038,7 @@ dependencies = [ "tokio", "tokio-named-pipes", "tokio-uds", - "winapi 0.3.6", + "winapi 0.3.9", ] [[package]] @@ -2038,6 +2062,17 @@ dependencies = [ "rustc_version", ] +[[package]] +name = "parking_lot" +version = "0.11.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a4893845fa2ca272e647da5d0e46660a314ead9c2fdd9a883aabc32e481a8733" +dependencies = [ + "instant", + "lock_api 0.4.1", + "parking_lot_core 0.8.0", +] + [[package]] name = "parking_lot_core" version = "0.3.1" @@ -2048,7 +2083,7 @@ dependencies = [ "rand 0.5.5", "rustc_version", "smallvec 0.6.4", - "winapi 0.3.6", + "winapi 0.3.9", ] [[package]] @@ -2058,12 +2093,27 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "b876b1b9e7ac6e1a74a6da34d25c42e17e8862aa409cbbbdcfc8d86c6f3bc62b" dependencies = [ "cfg-if", - "cloudabi", + "cloudabi 0.0.3", "libc", "redox_syscall", "rustc_version", "smallvec 0.6.4", - "winapi 0.3.6", + "winapi 0.3.9", +] + +[[package]] +name = "parking_lot_core" +version = "0.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c361aa727dd08437f2f1447be8b59a33b0edd15e0fcee698f935613d9efbca9b" +dependencies = [ + "cfg-if", + "cloudabi 0.1.0", + "instant", + "libc", + "redox_syscall", + "smallvec 1.4.1", + "winapi 0.3.9", ] [[package]] @@ -2253,7 +2303,7 @@ checksum = "8356f47b32624fef5b3301c1be97e5944ecdd595409cc5da11d05f211db6cfbd" dependencies = [ "fuchsia-zircon", "libc", - "winapi 0.3.6", + "winapi 0.3.9", ] [[package]] @@ -2262,11 +2312,11 @@ version = "0.5.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e464cd887e869cddcae8792a4ee31d23c7edd516700695608f5b98c67ee0131c" dependencies = [ - "cloudabi", + "cloudabi 0.0.3", "fuchsia-zircon", "libc", "rand_core 0.2.2", - "winapi 0.3.6", + "winapi 0.3.9", ] [[package]] @@ -2275,7 +2325,7 @@ version = "0.6.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ae9d223d52ae411a33cf7e54ec6034ec165df296ccd23533d671a28252b6f66a" dependencies = [ - "cloudabi", + "cloudabi 0.0.3", "fuchsia-zircon", "libc", "rand_chacha 0.1.0", @@ -2285,7 +2335,7 @@ dependencies = [ "rand_pcg", "rand_xorshift", "rustc_version", - "winapi 0.3.6", + "winapi 0.3.9", ] [[package]] @@ -2307,7 +2357,7 @@ version = "0.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "771b009e3a508cb67e8823dda454aaa5368c7bc1c16829fb77d3e980440dd34a" dependencies = [ - "rand_core 0.2.2", + "rand_core 0.3.0", "rustc_version", ] @@ -2351,7 +2401,7 @@ version = "0.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7b40677c7be09ae76218dc623efbf7b18e34bced3f38883af07bb75630a21bc4" dependencies = [ - "rand_core 0.2.2", + "rand_core 0.3.0", ] [[package]] @@ -2388,14 +2438,14 @@ version = "0.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "effa3fcaa47e18db002bdde6060944b6d2f9cfd8db471c30e873448ad9187be3" dependencies = [ - "rand_core 0.2.2", + "rand_core 0.3.0", ] [[package]] name = "redox_syscall" -version = "0.1.40" +version = "0.1.57" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c214e91d3ecf43e9a4e41e578973adeb14b474f2bee858742d127af75a0112b1" +checksum = "41cc0f7e4d5d4544e8861606a285bb08d3e70712ccc7d2b84d7c0ccfaf4b05ce" [[package]] name = "redox_termios" @@ -2430,7 +2480,7 @@ version = "0.5.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3488ba1b9a2084d38645c4c08276a1752dcbf2c7130d74f1569681ad5d2799c5" dependencies = [ - "winapi 0.3.6", + "winapi 0.3.9", ] [[package]] @@ -2471,7 +2521,7 @@ dependencies = [ "libc", "spin", "untrusted", - "winapi 0.3.6", + "winapi 0.3.9", ] [[package]] @@ -2595,7 +2645,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f2f6abf258d99c3c1c5c2131d99d064e94b7b3dd5f416483057f308fea253339" dependencies = [ "lazy_static 1.2.0", - "winapi 0.3.6", + "winapi 0.3.9", ] [[package]] @@ -2612,9 +2662,9 @@ checksum = "94258f53601af11e6a49f722422f6e3425c52b06245a5cf9bc09908b174f5e27" [[package]] name = "scopeguard" -version = "1.0.0" +version = "1.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b42e15e59b18a828bbf5c58ea01debb36b9b096346de35d941dcb89009f24a0d" +checksum = "d29ab0c6d3fc0ee92fe66e2d99f700eab17a8d57d1c1d3b748380fb20baa78cd" [[package]] name = "scrypt" @@ -2822,6 +2872,12 @@ dependencies = [ "unreachable", ] +[[package]] +name = "smallvec" +version = "1.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3757cb9d89161a2f24e1cf78efa0c1fcff485d18e3f55e0aa3480824ddaa0f3f" + [[package]] name = "snap" version = "0.2.4" @@ -2841,7 +2897,7 @@ dependencies = [ "cfg-if", "libc", "redox_syscall", - "winapi 0.3.6", + "winapi 0.3.9", ] [[package]] @@ -2959,7 +3015,7 @@ dependencies = [ "rand 0.7.2", "redox_syscall", "remove_dir_all", - "winapi 0.3.6", + "winapi 0.3.9", ] [[package]] @@ -3017,7 +3073,7 @@ checksum = "d825be0eb33fda1a7e68012d51e9c7f451dc1a69391e7fdc197060bb8c56667b" dependencies = [ "libc", "redox_syscall", - "winapi 0.3.6", + "winapi 0.3.9", ] [[package]] @@ -3484,9 +3540,9 @@ checksum = "167dc9d6949a9b857f3451275e911c3f44255842c1f7a76f33c55103a909087a" [[package]] name = "winapi" -version = "0.3.6" +version = "0.3.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "92c1eb33641e276cfa214a0522acad57be5c56b10cb348b3c5117db75f3ac4b0" +checksum = "5c839a674fcd7a98952e593242ea400abe93992746761e38641405d28b00f419" dependencies = [ "winapi-i686-pc-windows-gnu", "winapi-x86_64-pc-windows-gnu", @@ -3510,7 +3566,7 @@ version = "0.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "afc5508759c5bf4285e61feb862b6083c8480aec864fa17a81fdec6f69b461ab" dependencies = [ - "winapi 0.3.6", + "winapi 0.3.9", ] [[package]] @@ -3525,7 +3581,7 @@ version = "0.1.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "eeb06499a3a4d44302791052df005d5232b927ed1a9658146d842165c4de7767" dependencies = [ - "winapi 0.3.6", + "winapi 0.3.9", ] [[package]] @@ -3534,7 +3590,7 @@ version = "1.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "561ed901ae465d6185fa7864d63fbd5720d0ef718366c9a4dc83cf6170d7e9ba" dependencies = [ - "winapi 0.3.6", + "winapi 0.3.9", "winapi-util", ] diff --git a/Cargo.toml b/Cargo.toml index ab5ab8f2fb..a7adf1d636 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -41,7 +41,7 @@ log = "0.4.6" env_logger = "0.5.3" never-type = "0.1.0" panic_hook = { path = "util/panic_hook" } -parking_lot = "0.6.0" +parking_lot = "0.11.0" primitives = { git = "https://github.com/CodeChain-io/rust-codechain-primitives.git", version = "0.4" } rlp = { git = "https://github.com/CodeChain-io/rlp.git", version = "0.4" } rpassword = "2.0.0" diff --git a/core/Cargo.toml b/core/Cargo.toml index df178c9c35..cf78db5961 100644 --- a/core/Cargo.toml +++ b/core/Cargo.toml @@ -29,7 +29,7 @@ log = "0.4.6" lru-cache = "0.1.2" merkle-trie = { git = "https://github.com/CodeChain-io/rust-merkle-trie.git", version = "0.4" } num-rational = "0.2.1" -parking_lot = "0.6.0" +parking_lot = "0.11.0" primitives = { git = "https://github.com/CodeChain-io/rust-codechain-primitives.git", version = "0.4" } rand = "0.6.1" rlp = { git = "https://github.com/CodeChain-io/rlp.git", version = "0.4" } diff --git a/discovery/Cargo.toml b/discovery/Cargo.toml index d330626fa7..d5f30532f2 100644 --- a/discovery/Cargo.toml +++ b/discovery/Cargo.toml @@ -12,7 +12,7 @@ codechain-network = { path = "../network" } codechain-timer = { path = "../util/timer" } log = "0.4.6" never-type = "0.1.0" -parking_lot = "0.6.0" +parking_lot = "0.11.0" primitives = { git = "https://github.com/CodeChain-io/rust-codechain-primitives.git", version = "0.4" } rand = "0.6.1" rlp = { git = "https://github.com/CodeChain-io/rlp.git", version = "0.4" } diff --git a/key/Cargo.toml b/key/Cargo.toml index 1e65fbb30b..5c59bc36c1 100644 --- a/key/Cargo.toml +++ b/key/Cargo.toml @@ -12,7 +12,7 @@ lazy_static = "1.2" bech32 = "0.2.2" codechain-crypto = { git = "https://github.com/CodeChain-io/rust-codechain-crypto.git", version = "0.2" } never-type = "0.1.0" -parking_lot = "0.6.0" +parking_lot = "0.11.0" primitives = { git = "https://github.com/CodeChain-io/rust-codechain-primitives.git", version = "0.4" } rand_xorshift = "0.1.0" rlp = { git = "https://github.com/CodeChain-io/rlp.git", version = "0.4" } diff --git a/keystore/Cargo.toml b/keystore/Cargo.toml index 48212e89f7..aeb8e45751 100644 --- a/keystore/Cargo.toml +++ b/keystore/Cargo.toml @@ -16,7 +16,7 @@ serde_json = "1.0" serde_derive = "1.0" rustc-hex = "1.0" time = "0.1.34" -parking_lot = "0.6.0" +parking_lot = "0.11.0" codechain-crypto = { git = "https://github.com/CodeChain-io/rust-codechain-crypto.git", version = "0.2" } smallvec = "0.4" tempdir = "0.3" diff --git a/network/Cargo.toml b/network/Cargo.toml index 3916a0f519..a11a8d966a 100644 --- a/network/Cargo.toml +++ b/network/Cargo.toml @@ -18,7 +18,7 @@ log = "0.4.6" kvdb = "0.1" mio = "0.6.16" never-type = "0.1.0" -parking_lot = "0.6.0" +parking_lot = "0.11.0" rand = "0.6.1" rlp = { git = "https://github.com/CodeChain-io/rlp.git", version = "0.4" } rlp_derive = { git = "https://github.com/CodeChain-io/rlp.git", version = "0.2" } diff --git a/rpc/Cargo.toml b/rpc/Cargo.toml index f71ebdd4f9..5b97f9465d 100644 --- a/rpc/Cargo.toml +++ b/rpc/Cargo.toml @@ -23,7 +23,7 @@ kvdb = "0.1" kvdb-rocksdb = "0.1" lazy_static = "1.2" log = "0.4.6" -parking_lot = "0.6.0" +parking_lot = "0.11.0" primitives = { git = "https://github.com/CodeChain-io/rust-codechain-primitives.git", version = "0.4" } rlp = { git = "https://github.com/CodeChain-io/rlp.git", version = "0.4" } serde = "1.0" diff --git a/state/Cargo.toml b/state/Cargo.toml index 0ab2a58d2c..b1e6d7c23b 100644 --- a/state/Cargo.toml +++ b/state/Cargo.toml @@ -16,7 +16,7 @@ kvdb-memorydb = "0.1" log = "0.4.6" lru-cache = "0.1.1" merkle-trie = { git = "https://github.com/CodeChain-io/rust-merkle-trie.git", version = "0.4" } -parking_lot = "0.6.0" +parking_lot = "0.11.0" primitives = { git = "https://github.com/CodeChain-io/rust-codechain-primitives.git", version = "0.4" } rlp = { git = "https://github.com/CodeChain-io/rlp.git", version = "0.4" } rlp_derive = { git = "https://github.com/CodeChain-io/rlp.git", version = "0.2" } diff --git a/stratum/Cargo.toml b/stratum/Cargo.toml index 8c162d6018..d0da998314 100644 --- a/stratum/Cargo.toml +++ b/stratum/Cargo.toml @@ -14,7 +14,7 @@ jsonrpc-core = { git = "https://github.com/paritytech/jsonrpc.git", tag = "v14.0 jsonrpc-derive = { git = "https://github.com/paritytech/jsonrpc.git", tag = "v14.0.3" } jsonrpc-tcp-server = { git = "https://github.com/paritytech/jsonrpc.git", tag = "v14.0.3" } log = "0.4.6" -parking_lot = "0.6.0" +parking_lot = "0.11.0" primitives = { git = "https://github.com/CodeChain-io/rust-codechain-primitives.git", version = "0.4" } [dev-dependencies] diff --git a/util/io/Cargo.toml b/util/io/Cargo.toml index f0849917d0..32a3140c45 100644 --- a/util/io/Cargo.toml +++ b/util/io/Cargo.toml @@ -11,5 +11,5 @@ edition = "2018" codechain-logger = { path = "../logger" } mio = "0.6.16" crossbeam = "0.5.0" -parking_lot = "0.6.0" +parking_lot = "0.11.0" log = "0.4.6" diff --git a/util/logger/Cargo.toml b/util/logger/Cargo.toml index 5808f502fe..489bdc6dcc 100644 --- a/util/logger/Cargo.toml +++ b/util/logger/Cargo.toml @@ -10,7 +10,7 @@ colored = "1.6" env_logger = "0.6.0" lazy_static = "1.2" log = "0.4.6" -parking_lot = "0.6.0" +parking_lot = "0.11.0" sendgrid = "0.8.1" serde = "1.0" serde_derive = "1.0" diff --git a/util/timer/Cargo.toml b/util/timer/Cargo.toml index 322427a4ce..f7e977363d 100644 --- a/util/timer/Cargo.toml +++ b/util/timer/Cargo.toml @@ -7,6 +7,6 @@ edition = "2018" [lib] [dependencies] -parking_lot = "0.6.0" +parking_lot = "0.11.0" log = "0.4.6" codechain-logger = { path = "../logger" } From 62cded4383fc929bd3be75d32cc1f1a6398760a2 Mon Sep 17 00:00:00 2001 From: DoHyung Kim Date: Wed, 27 May 2020 19:54:24 +0900 Subject: [PATCH 55/55] Upgrade vergen 3 --- Cargo.lock | 26 ++------------------------ Cargo.toml | 2 +- build.rs | 16 ++-------------- 3 files changed, 5 insertions(+), 39 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index ea7e508d3e..8e640e8f69 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -958,15 +958,6 @@ dependencies = [ "termcolor 1.0.4", ] -[[package]] -name = "error-chain" -version = "0.12.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "07e791d3be96241c77c43846b665ef1384606da2cd2a48730abe606a12906e02" -dependencies = [ - "backtrace", -] - [[package]] name = "ethbloom" version = "0.5.0" @@ -1177,17 +1168,6 @@ dependencies = [ "wasi", ] -[[package]] -name = "getset" -version = "0.0.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "54c7f36a235738bb25904d6a2b3dbb28f6f5736cd3918c4bf80d6bb236200782" -dependencies = [ - "proc-macro2 0.3.8", - "quote 0.5.2", - "syn 0.13.11", -] - [[package]] name = "globset" version = "0.4.1" @@ -3493,14 +3473,12 @@ dependencies = [ [[package]] name = "vergen" -version = "2.0.0" +version = "3.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9a16834fc61e1492c07dae49b6c14b55f8b1d43a5f5f9e9a2ecc063f47b9f93c" +checksum = "4ce50d8996df1f85af15f2cd8d33daae6e479575123ef4314a51a70a230739cb" dependencies = [ "bitflags", "chrono", - "error-chain", - "getset", ] [[package]] diff --git a/Cargo.toml b/Cargo.toml index a7adf1d636..36f1b480af 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -54,7 +54,7 @@ toml = "0.4" cidr = "0.0.4" [build-dependencies] -vergen = "2" +vergen = "3" [[bin]] path = "codechain/main.rs" diff --git a/build.rs b/build.rs index deadea443d..7848e973d0 100644 --- a/build.rs +++ b/build.rs @@ -14,20 +14,8 @@ // You should have received a copy of the GNU Affero General Public License // along with this program. If not, see . -extern crate vergen; - -use vergen::{ConstantsFlags, Result, Vergen}; +use vergen::{generate_cargo_keys, ConstantsFlags}; fn main() { - gen_constants().expect("Unable to generate vergen constants!"); -} - -fn gen_constants() -> Result<()> { - let vergen = Vergen::new(ConstantsFlags::all())?; - - for (k, v) in vergen.build_info() { - println!("cargo:rustc-env={}={}", k.name(), v); - } - - Ok(()) + generate_cargo_keys(ConstantsFlags::all()).expect("Unable to generate vergen constants!"); }