diff --git a/src/blockchain.rs b/src/blockchain.rs index 4982afc4c..9e6d02089 100644 --- a/src/blockchain.rs +++ b/src/blockchain.rs @@ -1,5 +1,7 @@ use std::collections::HashMap; +use std::sync::{Arc, Mutex}; use util::hash::*; +use util::uint::*; use util::rlp::*; use util::hashdb::*; use util::overlaydb::*; @@ -10,12 +12,21 @@ use verifiedblock::*; use importroute::*; use account::*; use genesis::*; +use extras::*; pub struct BlockChain { + // TODO: consider wrapping `genesis_info` into Arc + // rlp list of 3 genesis_block: Vec, + // genesis block header genesis_header: Vec, genesis_hash: H256, - genesis_state: HashMap + genesis_state: HashMap, + + // extras + // TODO: is arc really needed here, since blockchain itself will be wrapped + // into `Arc`? + block_details: Arc>> } impl BlockChain { @@ -39,17 +50,29 @@ impl BlockChain { pub fn new(genesis: Genesis) -> BlockChain { let (genesis_block, genesis_state) = genesis.drain(); - let (genesis_header, genesis_hash) = { - let rlp = Rlp::new(&genesis_block).at(0); - (rlp.raw().to_vec(), BlockView::new_from_rlp(rlp).sha3()) + let genesis_header = Rlp::new(&genesis_block).at(0).raw().to_vec(); + let genesis_hash = BlockView::new(&genesis_header).sha3(); + + let genesis_details = BlockDetails { + number: U256::from(0u64), + total_difficulty: BlockView::new(&genesis_header).difficulty(), + parent: H256::new(), + children: vec![] }; - BlockChain { + // TODO: also insert into backing db + let mut block_details = HashMap::new(); + block_details.insert(genesis_hash.clone(), genesis_details); + + let bc = BlockChain { genesis_block: genesis_block, genesis_header: genesis_header, genesis_hash: genesis_hash, - genesis_state: genesis_state - } + genesis_state: genesis_state, + block_details: Arc::new(Mutex::new(block_details)) + }; + + bc } pub fn genesis_hash(&self) -> &H256 { @@ -94,7 +117,8 @@ impl BlockChain { /// Returns true if the given block is known /// (though not necessarily a part of the canon chain). pub fn is_known(&self, hash: &H256) -> bool { - unimplemented!() + return false; + //unimplemented!() // TODO: check is hash exist in hashes } } diff --git a/src/blockheader.rs b/src/blockheader.rs index 8d454c440..a11b83ca5 100644 --- a/src/blockheader.rs +++ b/src/blockheader.rs @@ -63,7 +63,7 @@ pub struct BlockHeader { } impl Decodable for BlockHeader { - fn decode(decoder: &D) -> Result where D: Decoder { + fn decode(decoder: &D) -> Result where D: Decoder { decoder.read_list(| d | { // return an error if d != 14 let blockheader = BlockHeader { diff --git a/src/extras.rs b/src/extras.rs new file mode 100644 index 000000000..d16c1e9c0 --- /dev/null +++ b/src/extras.rs @@ -0,0 +1,35 @@ +use util::uint::*; +use util::hash::*; +use util::rlp::*; + +pub struct BlockDetails { + pub number: U256, + pub total_difficulty: U256, + pub parent: H256, + pub children: Vec +} + +impl Decodable for BlockDetails { + fn decode(decoder: &D) -> Result where D: Decoder { + decoder.read_list(| d | { + let details = BlockDetails { + number: try!(Decodable::decode(&d[0])), + total_difficulty: try!(Decodable::decode(&d[1])), + parent: try!(Decodable::decode(&d[2])), + children: try!(Decodable::decode(&d[3])) + }; + Ok(details) + }) + } +} + +impl Encodable for BlockDetails { + fn encode(&self, encoder: &mut E) where E: Encoder { + encoder.emit_list(| e | { + self.number.encode(e); + self.total_difficulty.encode(e); + self.parent.encode(e); + self.children.encode(e); + }) + } +} diff --git a/src/lib.rs b/src/lib.rs index 43a55a4a6..d4096cfcf 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -83,6 +83,7 @@ pub mod block; pub mod blockchain; pub mod blockheader; pub mod transaction; +pub mod extras; pub mod genesis; pub mod verifiedblock; pub mod importroute;