Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Resolves #3554.
When we transition from "header sync" to "body sync" we identify missing blocks based on the delta between the chain of headers and the current chain of full blocks. i.e. We sync headers and then we go request the full blocks for each of those headers.
There is some additional complexity where we support a fork between the header chain and the full block chain as one is not always a subset of the other. And to do this we identify the "fork point" which is the last common header between header chain and full block chain before they begin to diverge.
Fork example -
Headers:
A -> B -> C' -> D -> E
Full blocks:
A -> B -> C
Header sync gave us a chain of headers building on
C'
while our local node was previously aware ofC
.We need to "rewind" to the fork point
B
immediately prior toC
andC'
and request missing blocks[C', D, E]
.The existing implementation rewinds back from the head of the header chain to identify both the fork point and a set of missing block hashes. This is fine if the delta between header chain and full block chain is small but is not suitable if the header chain must be rewound a significant number of blocks.
It fails badly in the "full archval node sync" scenario where we must rewind from height ~1,500,00 back to 1.
The PR introduces a more efficient approach -
get_header_by_height()
This places an upper bound on the iteration required as we can lookup headers directly based on height.
This greatly reduces the amount of iteration required when identifying missing blocks to sync.
As part of this rework
check_txhashset_needed()
was refactored, splitting outget_fork_point()
andcheck_txhashset_needed()
into separate fns.This allowed the implementation to be simplified significantly.