When the block index database is non-contiguous due to file corruption (i.e. it contains indexes of height x-1
and x+1
, but not x
), bitcoind can currently crash with an assert in BuildSkip()
/ GetAncestor()
during BlockManager::LoadBlockIndex()
:
0bitcoind: chain.cpp:112: const CBlockIndex* CBlockIndex::GetAncestor(int) const: Assertion `pindexWalk->pprev' failed.
This PR changes it such that we instead return an InitError
to the user.
I stumbled upon this because I noticed that the file perturbation in feature_init.py
wasn’t working as intended, which is fixed in the second commit:
- Opening the file twice in one
with
statement would lead totf_read
being empty, so the test wouldn’t perturb anything but replace the file with a new one. Fixed by first opening for read, then for write. - We need to restore the previous state after perturbations, so that only the current perturbation is active and not a mix of the current and previous ones.
- I also added
checkblocks=200
to the startup parameters so that corruption in earlier blocks ofblk00000.dat
is detected during init verification and not ignored.
After fixing feature_init.py
like that I’d run into the assert
mentioned above (so running the testfix from the second commit without the first one is a way to reproduce it).