Make sure to not mark block header hash as invalid if only the body is wrong. (#11356)
* Patch invalid transaction root. * Add raw hash to bad and include fix for uncles too. * Fix submodules.
This commit is contained in:
parent
29ebddc64f
commit
54c2d6167f
@ -27,9 +27,12 @@ pub use self::headers::Headers;
|
|||||||
|
|
||||||
/// Something which can produce a hash and a parent hash.
|
/// Something which can produce a hash and a parent hash.
|
||||||
pub trait BlockLike {
|
pub trait BlockLike {
|
||||||
/// Get the hash of this item.
|
/// Get the hash of this item - i.e. the header hash.
|
||||||
fn hash(&self) -> H256;
|
fn hash(&self) -> H256;
|
||||||
|
|
||||||
|
/// Get a raw hash of this item - i.e. the hash of the RLP representation.
|
||||||
|
fn raw_hash(&self) -> H256;
|
||||||
|
|
||||||
/// Get the hash of this item's parent.
|
/// Get the hash of this item's parent.
|
||||||
fn parent_hash(&self) -> H256;
|
fn parent_hash(&self) -> H256;
|
||||||
|
|
||||||
@ -160,6 +163,10 @@ pub mod blocks {
|
|||||||
self.header.hash()
|
self.header.hash()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn raw_hash(&self) -> H256 {
|
||||||
|
hash::keccak(&self.bytes)
|
||||||
|
}
|
||||||
|
|
||||||
fn parent_hash(&self) -> H256 {
|
fn parent_hash(&self) -> H256 {
|
||||||
self.header.parent_hash().clone()
|
self.header.parent_hash().clone()
|
||||||
}
|
}
|
||||||
@ -174,6 +181,10 @@ pub mod blocks {
|
|||||||
self.header.hash()
|
self.header.hash()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn raw_hash(&self) -> H256 {
|
||||||
|
hash::keccak(&self.bytes)
|
||||||
|
}
|
||||||
|
|
||||||
fn parent_hash(&self) -> H256 {
|
fn parent_hash(&self) -> H256 {
|
||||||
self.header.parent_hash().clone()
|
self.header.parent_hash().clone()
|
||||||
}
|
}
|
||||||
@ -197,6 +208,7 @@ pub mod headers {
|
|||||||
|
|
||||||
impl BlockLike for Header {
|
impl BlockLike for Header {
|
||||||
fn hash(&self) -> H256 { self.hash() }
|
fn hash(&self) -> H256 { self.hash() }
|
||||||
|
fn raw_hash(&self) -> H256 { self.hash() }
|
||||||
fn parent_hash(&self) -> H256 { self.parent_hash().clone() }
|
fn parent_hash(&self) -> H256 { self.parent_hash().clone() }
|
||||||
fn difficulty(&self) -> U256 { self.difficulty().clone() }
|
fn difficulty(&self) -> U256 { self.difficulty().clone() }
|
||||||
}
|
}
|
||||||
|
@ -472,13 +472,14 @@ impl<K: Kind> VerificationQueue<K> {
|
|||||||
/// Add a block to the queue.
|
/// Add a block to the queue.
|
||||||
pub fn import(&self, input: K::Input) -> Result<H256, (K::Input, Error)> {
|
pub fn import(&self, input: K::Input) -> Result<H256, (K::Input, Error)> {
|
||||||
let hash = input.hash();
|
let hash = input.hash();
|
||||||
|
let raw_hash = input.raw_hash();
|
||||||
{
|
{
|
||||||
if self.processing.read().contains_key(&hash) {
|
if self.processing.read().contains_key(&hash) {
|
||||||
bail!((input, ErrorKind::Import(ImportErrorKind::AlreadyQueued).into()));
|
bail!((input, ErrorKind::Import(ImportErrorKind::AlreadyQueued).into()));
|
||||||
}
|
}
|
||||||
|
|
||||||
let mut bad = self.verification.bad.lock();
|
let mut bad = self.verification.bad.lock();
|
||||||
if bad.contains(&hash) {
|
if bad.contains(&hash) || bad.contains(&raw_hash) {
|
||||||
bail!((input, ErrorKind::Import(ImportErrorKind::KnownBad).into()));
|
bail!((input, ErrorKind::Import(ImportErrorKind::KnownBad).into()));
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -505,6 +506,16 @@ impl<K: Kind> VerificationQueue<K> {
|
|||||||
match err {
|
match err {
|
||||||
// Don't mark future blocks as bad.
|
// Don't mark future blocks as bad.
|
||||||
Error(ErrorKind::Block(BlockError::TemporarilyInvalid(_)), _) => {},
|
Error(ErrorKind::Block(BlockError::TemporarilyInvalid(_)), _) => {},
|
||||||
|
// If the transaction root or uncles hash is invalid, it doesn't necessarily mean
|
||||||
|
// that the header is invalid. We might have just received a malformed block body,
|
||||||
|
// so we shouldn't put the header hash to `bad`.
|
||||||
|
//
|
||||||
|
// We still put the entire `Item` hash to bad, so that we can early reject
|
||||||
|
// the items that are malformed.
|
||||||
|
Error(ErrorKind::Block(BlockError::InvalidTransactionsRoot(_)), _) |
|
||||||
|
Error(ErrorKind::Block(BlockError::InvalidUnclesHash(_)), _) => {
|
||||||
|
self.verification.bad.lock().insert(raw_hash);
|
||||||
|
},
|
||||||
_ => {
|
_ => {
|
||||||
self.verification.bad.lock().insert(hash);
|
self.verification.bad.lock().insert(hash);
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user