perf(engine): check hashmap instead of clone (#23071)

Signed-off-by: Delweng <delweng@gmail.com>
This commit is contained in:
Delweng
2026-03-17 22:00:45 +08:00
committed by GitHub
parent a0b0d8854c
commit 55ed7d5bb5
2 changed files with 19 additions and 3 deletions

View File

@@ -2057,6 +2057,17 @@ where
))
}
/// Returns `true` if a block with the given hash is known, either in memory or in the
/// database. This is a lightweight existence check that avoids constructing a full
/// [`SealedHeader`].
fn has_block_by_hash(&self, hash: B256) -> ProviderResult<bool> {
if self.state.tree_state.contains_hash(&hash) {
Ok(true)
} else {
self.provider.is_known(hash)
}
}
/// Return sealed block header from in-memory state or database by hash.
fn sealed_header_by_hash(
&self,
@@ -2101,7 +2112,7 @@ where
parent_hash: B256,
) -> ProviderResult<Option<B256>> {
// Check if parent exists in side chain or in canonical chain.
if self.sealed_header_by_hash(parent_hash)?.is_some() {
if self.has_block_by_hash(parent_hash)? {
return Ok(Some(parent_hash))
}
@@ -2115,7 +2126,7 @@ where
// If current_header is None, then the current_hash does not have an invalid
// ancestor in the cache, check its presence in blockchain tree
if current_block.is_none() && self.sealed_header_by_hash(current_hash)?.is_some() {
if current_block.is_none() && self.has_block_by_hash(current_hash)? {
return Ok(Some(current_hash))
}
}
@@ -2782,7 +2793,7 @@ where
debug!(target: "engine::tree", block=?block_num_hash, parent = ?block_id.parent, "Inserting new block into tree");
// Check if block already exists - first in memory, then DB only if it could be persisted
if self.state.tree_state.sealed_header_by_hash(&block_num_hash.hash).is_some() {
if self.state.tree_state.contains_hash(&block_num_hash.hash) {
convert_to_block(self, input)?;
return Ok(InsertPayloadOk::AlreadySeen(BlockStatus::Valid));
}

View File

@@ -74,6 +74,11 @@ impl<N: NodePrimitives> TreeState<N> {
self.blocks_by_hash.get(&hash)
}
/// Returns `true` if a block with the given hash exists in memory.
pub fn contains_hash(&self, hash: &B256) -> bool {
self.blocks_by_hash.contains_key(hash)
}
/// Returns the sealed block header by hash.
pub fn sealed_header_by_hash(&self, hash: &B256) -> Option<SealedHeader<N::BlockHeader>> {
self.blocks_by_hash.get(hash).map(|b| b.sealed_block().sealed_header().clone())