Remove the BitcoinHash trait
Replaced by a `block_hash` method on both `Block` and `BlockHeader`.
This commit is contained in:
parent
2cba81935d
commit
8e52b8ce4d
|
@ -22,7 +22,7 @@
|
||||||
|
|
||||||
use util;
|
use util;
|
||||||
use util::Error::{BlockBadTarget, BlockBadProofOfWork};
|
use util::Error::{BlockBadTarget, BlockBadProofOfWork};
|
||||||
use util::hash::{BitcoinHash, bitcoin_merkle_root};
|
use util::hash::bitcoin_merkle_root;
|
||||||
use hashes::{Hash, HashEngine};
|
use hashes::{Hash, HashEngine};
|
||||||
use hash_types::{Wtxid, BlockHash, TxMerkleNode, WitnessMerkleNode, WitnessCommitment};
|
use hash_types::{Wtxid, BlockHash, TxMerkleNode, WitnessMerkleNode, WitnessCommitment};
|
||||||
use util::uint::Uint256;
|
use util::uint::Uint256;
|
||||||
|
@ -61,6 +61,11 @@ pub struct Block {
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Block {
|
impl Block {
|
||||||
|
/// Return the block hash.
|
||||||
|
pub fn block_hash(&self) -> BlockHash {
|
||||||
|
self.header.block_hash()
|
||||||
|
}
|
||||||
|
|
||||||
/// check if merkle root of header matches merkle root of the transaction list
|
/// check if merkle root of header matches merkle root of the transaction list
|
||||||
pub fn check_merkle_root (&self) -> bool {
|
pub fn check_merkle_root (&self) -> bool {
|
||||||
self.header.merkle_root == self.merkle_root()
|
self.header.merkle_root == self.merkle_root()
|
||||||
|
@ -122,6 +127,13 @@ impl Block {
|
||||||
}
|
}
|
||||||
|
|
||||||
impl BlockHeader {
|
impl BlockHeader {
|
||||||
|
/// Return the block hash.
|
||||||
|
pub fn block_hash(&self) -> BlockHash {
|
||||||
|
let mut engine = BlockHash::engine();
|
||||||
|
self.consensus_encode(&mut engine).expect("engines don't error");
|
||||||
|
BlockHash::from_engine(engine)
|
||||||
|
}
|
||||||
|
|
||||||
/// Computes the target [0, T] that a blockhash must land in to be valid
|
/// Computes the target [0, T] that a blockhash must land in to be valid
|
||||||
pub fn target(&self) -> Uint256 {
|
pub fn target(&self) -> Uint256 {
|
||||||
// This is a floating-point "compact" encoding originally used by
|
// This is a floating-point "compact" encoding originally used by
|
||||||
|
@ -174,7 +186,7 @@ impl BlockHeader {
|
||||||
if target != required_target {
|
if target != required_target {
|
||||||
return Err(BlockBadTarget);
|
return Err(BlockBadTarget);
|
||||||
}
|
}
|
||||||
let data: [u8; 32] = self.bitcoin_hash().into_inner();
|
let data: [u8; 32] = self.block_hash().into_inner();
|
||||||
let mut ret = [0u64; 4];
|
let mut ret = [0u64; 4];
|
||||||
util::endian::bytes_to_u64_slice_le(&data, &mut ret);
|
util::endian::bytes_to_u64_slice_le(&data, &mut ret);
|
||||||
let hash = &Uint256(ret);
|
let hash = &Uint256(ret);
|
||||||
|
@ -193,19 +205,6 @@ impl BlockHeader {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl BitcoinHash<BlockHash> for BlockHeader {
|
|
||||||
fn bitcoin_hash(&self) -> BlockHash {
|
|
||||||
use consensus::encode::serialize;
|
|
||||||
BlockHash::hash(&serialize(self))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl BitcoinHash<BlockHash> for Block {
|
|
||||||
fn bitcoin_hash(&self) -> BlockHash {
|
|
||||||
self.header.bitcoin_hash()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl_consensus_encoding!(BlockHeader, version, prev_blockhash, merkle_root, time, bits, nonce);
|
impl_consensus_encoding!(BlockHeader, version, prev_blockhash, merkle_root, time, bits, nonce);
|
||||||
impl_consensus_encoding!(Block, header, txdata);
|
impl_consensus_encoding!(Block, header, txdata);
|
||||||
serde_struct_impl!(BlockHeader, version, prev_blockhash, merkle_root, time, bits, nonce);
|
serde_struct_impl!(BlockHeader, version, prev_blockhash, merkle_root, time, bits, nonce);
|
||||||
|
|
|
@ -151,7 +151,6 @@ mod test {
|
||||||
use consensus::encode::serialize;
|
use consensus::encode::serialize;
|
||||||
use blockdata::constants::{genesis_block, bitcoin_genesis_tx};
|
use blockdata::constants::{genesis_block, bitcoin_genesis_tx};
|
||||||
use blockdata::constants::{MAX_SEQUENCE, COIN_VALUE};
|
use blockdata::constants::{MAX_SEQUENCE, COIN_VALUE};
|
||||||
use util::hash::BitcoinHash;
|
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn bitcoin_genesis_first_transaction() {
|
fn bitcoin_genesis_first_transaction() {
|
||||||
|
@ -186,7 +185,7 @@ mod test {
|
||||||
assert_eq!(gen.header.time, 1231006505);
|
assert_eq!(gen.header.time, 1231006505);
|
||||||
assert_eq!(gen.header.bits, 0x1d00ffff);
|
assert_eq!(gen.header.bits, 0x1d00ffff);
|
||||||
assert_eq!(gen.header.nonce, 2083236893);
|
assert_eq!(gen.header.nonce, 2083236893);
|
||||||
assert_eq!(format!("{:x}", gen.header.bitcoin_hash()),
|
assert_eq!(format!("{:x}", gen.header.block_hash()),
|
||||||
"000000000019d6689c085ae165831e934ff763ae46a2a6c172b3f1b60a8ce26f".to_string());
|
"000000000019d6689c085ae165831e934ff763ae46a2a6c172b3f1b60a8ce26f".to_string());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -200,7 +199,7 @@ mod test {
|
||||||
assert_eq!(gen.header.time, 1296688602);
|
assert_eq!(gen.header.time, 1296688602);
|
||||||
assert_eq!(gen.header.bits, 0x1d00ffff);
|
assert_eq!(gen.header.bits, 0x1d00ffff);
|
||||||
assert_eq!(gen.header.nonce, 414098458);
|
assert_eq!(gen.header.nonce, 414098458);
|
||||||
assert_eq!(format!("{:x}", gen.header.bitcoin_hash()),
|
assert_eq!(format!("{:x}", gen.header.block_hash()),
|
||||||
"000000000933ea01ad0ee984209779baaec3ced90fa3f408719526f8d77f4943".to_string());
|
"000000000933ea01ad0ee984209779baaec3ced90fa3f408719526f8d77f4943".to_string());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -97,7 +97,6 @@ pub use util::address::Address;
|
||||||
pub use util::address::AddressType;
|
pub use util::address::AddressType;
|
||||||
pub use util::amount::Amount;
|
pub use util::amount::Amount;
|
||||||
pub use util::amount::SignedAmount;
|
pub use util::amount::SignedAmount;
|
||||||
pub use util::hash::BitcoinHash;
|
|
||||||
pub use util::key::PrivateKey;
|
pub use util::key::PrivateKey;
|
||||||
pub use util::key::PublicKey;
|
pub use util::key::PublicKey;
|
||||||
pub use util::merkleblock::MerkleBlock;
|
pub use util::merkleblock::MerkleBlock;
|
||||||
|
|
|
@ -59,7 +59,6 @@ use blockdata::transaction::OutPoint;
|
||||||
use consensus::{Decodable, Encodable};
|
use consensus::{Decodable, Encodable};
|
||||||
use consensus::encode::VarInt;
|
use consensus::encode::VarInt;
|
||||||
use util::endian;
|
use util::endian;
|
||||||
use util::hash::BitcoinHash;
|
|
||||||
|
|
||||||
/// Golomb encoding parameter as in BIP-158, see also https://gist.github.com/sipa/576d5f09c3b86c3b1b75598d799fc845
|
/// Golomb encoding parameter as in BIP-158, see also https://gist.github.com/sipa/576d5f09c3b86c3b1b75598d799fc845
|
||||||
const P: u8 = 19;
|
const P: u8 = 19;
|
||||||
|
@ -155,7 +154,7 @@ pub struct BlockFilterWriter<'a> {
|
||||||
impl<'a> BlockFilterWriter<'a> {
|
impl<'a> BlockFilterWriter<'a> {
|
||||||
/// Create a block filter writer
|
/// Create a block filter writer
|
||||||
pub fn new(writer: &'a mut io::Write, block: &'a Block) -> BlockFilterWriter<'a> {
|
pub fn new(writer: &'a mut io::Write, block: &'a Block) -> BlockFilterWriter<'a> {
|
||||||
let block_hash_as_int = block.bitcoin_hash().into_inner();
|
let block_hash_as_int = block.block_hash().into_inner();
|
||||||
let k0 = endian::slice_to_u64_le(&block_hash_as_int[0..8]);
|
let k0 = endian::slice_to_u64_le(&block_hash_as_int[0..8]);
|
||||||
let k1 = endian::slice_to_u64_le(&block_hash_as_int[8..16]);
|
let k1 = endian::slice_to_u64_le(&block_hash_as_int[8..16]);
|
||||||
let writer = GCSFilterWriter::new(writer, k0, k1, M, P);
|
let writer = GCSFilterWriter::new(writer, k0, k1, M, P);
|
||||||
|
@ -559,7 +558,7 @@ mod test {
|
||||||
for t in testdata.iter().skip(1) {
|
for t in testdata.iter().skip(1) {
|
||||||
let block_hash = BlockHash::from_hex(&t.get(1).unwrap().as_str().unwrap()).unwrap();
|
let block_hash = BlockHash::from_hex(&t.get(1).unwrap().as_str().unwrap()).unwrap();
|
||||||
let block: Block = deserialize(hex::decode(&t.get(2).unwrap().as_str().unwrap().as_bytes()).unwrap().as_slice()).unwrap();
|
let block: Block = deserialize(hex::decode(&t.get(2).unwrap().as_str().unwrap().as_bytes()).unwrap().as_slice()).unwrap();
|
||||||
assert_eq!(block.bitcoin_hash(), block_hash);
|
assert_eq!(block.block_hash(), block_hash);
|
||||||
let scripts = t.get(3).unwrap().as_array().unwrap();
|
let scripts = t.get(3).unwrap().as_array().unwrap();
|
||||||
let previous_filter_id = FilterHash::from_hex(&t.get(4).unwrap().as_str().unwrap()).unwrap();
|
let previous_filter_id = FilterHash::from_hex(&t.get(4).unwrap().as_str().unwrap()).unwrap();
|
||||||
let filter_content = hex::decode(&t.get(5).unwrap().as_str().unwrap().as_bytes()).unwrap();
|
let filter_content = hex::decode(&t.get(5).unwrap().as_str().unwrap().as_bytes()).unwrap();
|
||||||
|
@ -584,7 +583,7 @@ mod test {
|
||||||
|
|
||||||
assert_eq!(test_filter.content, filter.content);
|
assert_eq!(test_filter.content, filter.content);
|
||||||
|
|
||||||
let block_hash = &block.header.bitcoin_hash();
|
let block_hash = &block.block_hash();
|
||||||
assert!(filter.match_all(block_hash, &mut txmap.iter()
|
assert!(filter.match_all(block_hash, &mut txmap.iter()
|
||||||
.filter_map(|(_, s)| if !s.is_empty() { Some(s.as_bytes()) } else { None })).unwrap());
|
.filter_map(|(_, s)| if !s.is_empty() { Some(s.as_bytes()) } else { None })).unwrap());
|
||||||
|
|
||||||
|
|
|
@ -75,9 +75,3 @@ pub fn bitcoin_merkle_root<T, I>(mut iter: I) -> T
|
||||||
}
|
}
|
||||||
bitcoin_merkle_root_inline(&mut alloc)
|
bitcoin_merkle_root_inline(&mut alloc)
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Objects which are referred to by hash
|
|
||||||
pub trait BitcoinHash<T: Hash> {
|
|
||||||
/// Produces a Sha256dHash which can be used to refer to the object
|
|
||||||
fn bitcoin_hash(&self) -> T;
|
|
||||||
}
|
|
||||||
|
|
|
@ -502,7 +502,7 @@ mod tests {
|
||||||
use secp256k1::rand::prelude::*;
|
use secp256k1::rand::prelude::*;
|
||||||
|
|
||||||
use consensus::encode::{deserialize, serialize};
|
use consensus::encode::{deserialize, serialize};
|
||||||
use util::hash::{bitcoin_merkle_root, BitcoinHash};
|
use util::hash::bitcoin_merkle_root;
|
||||||
use util::merkleblock::{MerkleBlock, PartialMerkleTree};
|
use util::merkleblock::{MerkleBlock, PartialMerkleTree};
|
||||||
use {hex, Block};
|
use {hex, Block};
|
||||||
|
|
||||||
|
@ -616,7 +616,7 @@ mod tests {
|
||||||
af156d6fc30b55fad4112df2b95531e68114e9ad10011e72f7b7cfdb025700";
|
af156d6fc30b55fad4112df2b95531e68114e9ad10011e72f7b7cfdb025700";
|
||||||
|
|
||||||
let mb: MerkleBlock = deserialize(&hex::decode(mb_hex).unwrap()).unwrap();
|
let mb: MerkleBlock = deserialize(&hex::decode(mb_hex).unwrap()).unwrap();
|
||||||
assert_eq!(get_block_13b8a().bitcoin_hash(), mb.header.bitcoin_hash());
|
assert_eq!(get_block_13b8a().block_hash(), mb.header.block_hash());
|
||||||
assert_eq!(
|
assert_eq!(
|
||||||
mb.header.merkle_root,
|
mb.header.merkle_root,
|
||||||
mb.txn.extract_matches(&mut vec![], &mut vec![]).unwrap()
|
mb.txn.extract_matches(&mut vec![], &mut vec![]).unwrap()
|
||||||
|
@ -645,7 +645,7 @@ mod tests {
|
||||||
|
|
||||||
let merkle_block = MerkleBlock::from_block(&block, &txids);
|
let merkle_block = MerkleBlock::from_block(&block, &txids);
|
||||||
|
|
||||||
assert_eq!(merkle_block.header.bitcoin_hash(), block.bitcoin_hash());
|
assert_eq!(merkle_block.header.block_hash(), block.block_hash());
|
||||||
|
|
||||||
let mut matches: Vec<Txid> = vec![];
|
let mut matches: Vec<Txid> = vec![];
|
||||||
let mut index: Vec<u32> = vec![];
|
let mut index: Vec<u32> = vec![];
|
||||||
|
@ -678,7 +678,7 @@ mod tests {
|
||||||
|
|
||||||
let merkle_block = MerkleBlock::from_block(&block, &txids);
|
let merkle_block = MerkleBlock::from_block(&block, &txids);
|
||||||
|
|
||||||
assert_eq!(merkle_block.header.bitcoin_hash(), block.bitcoin_hash());
|
assert_eq!(merkle_block.header.block_hash(), block.block_hash());
|
||||||
|
|
||||||
let mut matches: Vec<Txid> = vec![];
|
let mut matches: Vec<Txid> = vec![];
|
||||||
let mut index: Vec<u32> = vec![];
|
let mut index: Vec<u32> = vec![];
|
||||||
|
|
Loading…
Reference in New Issue