Skip to content

Commit 4ada742

Browse files
committed
Merge bitcoin/bitcoin#23974: Make blockstorage globals private members of BlockManager
fa68a6c scripted-diff: Rename touched member variables (MarcoFalke) facd3df Make blockstorage globals private members of BlockManager (MarcoFalke) faa8c2d doc: Clarify nPruneAfterHeight for signet (MarcoFalke) fad381b test: Load genesis block to allow flush (MarcoFalke) fab2621 Move blockstorage-related unload to BlockManager::Unload (MarcoFalke) fa467f3 move-only: Create WriteBlockIndexDB helper (MarcoFalke) fa88cfd Move functions to BlockManager (MarcoFalke) Pull request description: Globals aren't too nice because they hide dependencies, also they make testing harder. Fix that by removing some. ACKs for top commit: Sjors: ACK fa68a6c ryanofsky: Code review ACK fa68a6c. Nice changes! Tree-SHA512: 6abc5929a5e43a05e238276721d46a64a44f23dca18c2caa9775437a32351d6815d88b88757254686421531d0df13861bbd3a202e13a3192798d87a96abef65d
2 parents be72ae2 + fa68a6c commit 4ada742

File tree

6 files changed

+142
-135
lines changed

6 files changed

+142
-135
lines changed

src/node/blockstorage.cpp

+81-73
Original file line numberDiff line numberDiff line change
@@ -27,23 +27,6 @@ bool fHavePruned = false;
2727
bool fPruneMode = false;
2828
uint64_t nPruneTarget = 0;
2929

30-
// TODO make namespace {
31-
RecursiveMutex cs_LastBlockFile;
32-
std::vector<CBlockFileInfo> vinfoBlockFile;
33-
int nLastBlockFile = 0;
34-
/** Global flag to indicate we should check to see if there are
35-
* block/undo files that should be deleted. Set on startup
36-
* or if we allocate more file space when we're in prune mode
37-
*/
38-
bool fCheckForPruning = false;
39-
40-
/** Dirty block index entries. */
41-
std::set<CBlockIndex*> setDirtyBlockIndex;
42-
43-
/** Dirty block file entries. */
44-
std::set<int> setDirtyFileInfo;
45-
// } // namespace
46-
4730
static FILE* OpenUndoFile(const FlatFilePos& pos, bool fReadOnly = false);
4831
static FlatFileSeq BlockFileSeq();
4932
static FlatFileSeq UndoFileSeq();
@@ -86,7 +69,7 @@ CBlockIndex* BlockManager::AddToBlockIndex(const CBlockHeader& block)
8669
if (pindexBestHeader == nullptr || pindexBestHeader->nChainWork < pindexNew->nChainWork)
8770
pindexBestHeader = pindexNew;
8871

89-
setDirtyBlockIndex.insert(pindexNew);
72+
m_dirty_blockindex.insert(pindexNew);
9073

9174
return pindexNew;
9275
}
@@ -104,7 +87,7 @@ void BlockManager::PruneOneBlockFile(const int fileNumber)
10487
pindex->nFile = 0;
10588
pindex->nDataPos = 0;
10689
pindex->nUndoPos = 0;
107-
setDirtyBlockIndex.insert(pindex);
90+
m_dirty_blockindex.insert(pindex);
10891

10992
// Prune from m_blocks_unlinked -- any block we prune would have
11093
// to be downloaded again in order to consider its chain, at which
@@ -121,8 +104,8 @@ void BlockManager::PruneOneBlockFile(const int fileNumber)
121104
}
122105
}
123106

124-
vinfoBlockFile[fileNumber].SetNull();
125-
setDirtyFileInfo.insert(fileNumber);
107+
m_blockfile_info[fileNumber].SetNull();
108+
m_dirty_fileinfo.insert(fileNumber);
126109
}
127110

128111
void BlockManager::FindFilesToPruneManual(std::set<int>& setFilesToPrune, int nManualPruneHeight, int chain_tip_height)
@@ -137,8 +120,8 @@ void BlockManager::FindFilesToPruneManual(std::set<int>& setFilesToPrune, int nM
137120
// last block to prune is the lesser of (user-specified height, MIN_BLOCKS_TO_KEEP from the tip)
138121
unsigned int nLastBlockWeCanPrune = std::min((unsigned)nManualPruneHeight, chain_tip_height - MIN_BLOCKS_TO_KEEP);
139122
int count = 0;
140-
for (int fileNumber = 0; fileNumber < nLastBlockFile; fileNumber++) {
141-
if (vinfoBlockFile[fileNumber].nSize == 0 || vinfoBlockFile[fileNumber].nHeightLast > nLastBlockWeCanPrune) {
123+
for (int fileNumber = 0; fileNumber < m_last_blockfile; fileNumber++) {
124+
if (m_blockfile_info[fileNumber].nSize == 0 || m_blockfile_info[fileNumber].nHeightLast > nLastBlockWeCanPrune) {
142125
continue;
143126
}
144127
PruneOneBlockFile(fileNumber);
@@ -177,10 +160,10 @@ void BlockManager::FindFilesToPrune(std::set<int>& setFilesToPrune, uint64_t nPr
177160
nBuffer += nPruneTarget / 10;
178161
}
179162

180-
for (int fileNumber = 0; fileNumber < nLastBlockFile; fileNumber++) {
181-
nBytesToPrune = vinfoBlockFile[fileNumber].nSize + vinfoBlockFile[fileNumber].nUndoSize;
163+
for (int fileNumber = 0; fileNumber < m_last_blockfile; fileNumber++) {
164+
nBytesToPrune = m_blockfile_info[fileNumber].nSize + m_blockfile_info[fileNumber].nUndoSize;
182165

183-
if (vinfoBlockFile[fileNumber].nSize == 0) {
166+
if (m_blockfile_info[fileNumber].nSize == 0) {
184167
continue;
185168
}
186169

@@ -189,7 +172,7 @@ void BlockManager::FindFilesToPrune(std::set<int>& setFilesToPrune, uint64_t nPr
189172
}
190173

191174
// don't prune files that could have a block within MIN_BLOCKS_TO_KEEP of the main chain's tip but keep scanning
192-
if (vinfoBlockFile[fileNumber].nHeightLast > nLastBlockWeCanPrune) {
175+
if (m_blockfile_info[fileNumber].nHeightLast > nLastBlockWeCanPrune) {
193176
continue;
194177
}
195178

@@ -290,7 +273,7 @@ bool BlockManager::LoadBlockIndex(
290273
}
291274
if (!(pindex->nStatus & BLOCK_FAILED_MASK) && pindex->pprev && (pindex->pprev->nStatus & BLOCK_FAILED_MASK)) {
292275
pindex->nStatus |= BLOCK_FAILED_CHILD;
293-
setDirtyBlockIndex.insert(pindex);
276+
m_dirty_blockindex.insert(pindex);
294277
}
295278
if (pindex->IsAssumedValid() ||
296279
(pindex->IsValid(BLOCK_VALID_TRANSACTIONS) &&
@@ -348,6 +331,31 @@ void BlockManager::Unload()
348331
}
349332

350333
m_block_index.clear();
334+
335+
m_blockfile_info.clear();
336+
m_last_blockfile = 0;
337+
m_dirty_blockindex.clear();
338+
m_dirty_fileinfo.clear();
339+
}
340+
341+
bool BlockManager::WriteBlockIndexDB()
342+
{
343+
std::vector<std::pair<int, const CBlockFileInfo*>> vFiles;
344+
vFiles.reserve(m_dirty_fileinfo.size());
345+
for (std::set<int>::iterator it = m_dirty_fileinfo.begin(); it != m_dirty_fileinfo.end();) {
346+
vFiles.push_back(std::make_pair(*it, &m_blockfile_info[*it]));
347+
m_dirty_fileinfo.erase(it++);
348+
}
349+
std::vector<const CBlockIndex*> vBlocks;
350+
vBlocks.reserve(m_dirty_blockindex.size());
351+
for (std::set<CBlockIndex*>::iterator it = m_dirty_blockindex.begin(); it != m_dirty_blockindex.end();) {
352+
vBlocks.push_back(*it);
353+
m_dirty_blockindex.erase(it++);
354+
}
355+
if (!m_block_tree_db->WriteBatchSync(vFiles, m_last_blockfile, vBlocks)) {
356+
return false;
357+
}
358+
return true;
351359
}
352360

353361
bool BlockManager::LoadBlockIndexDB(ChainstateManager& chainman)
@@ -357,17 +365,17 @@ bool BlockManager::LoadBlockIndexDB(ChainstateManager& chainman)
357365
}
358366

359367
// Load block file info
360-
m_block_tree_db->ReadLastBlockFile(nLastBlockFile);
361-
vinfoBlockFile.resize(nLastBlockFile + 1);
362-
LogPrintf("%s: last block file = %i\n", __func__, nLastBlockFile);
363-
for (int nFile = 0; nFile <= nLastBlockFile; nFile++) {
364-
m_block_tree_db->ReadBlockFileInfo(nFile, vinfoBlockFile[nFile]);
365-
}
366-
LogPrintf("%s: last block file info: %s\n", __func__, vinfoBlockFile[nLastBlockFile].ToString());
367-
for (int nFile = nLastBlockFile + 1; true; nFile++) {
368+
m_block_tree_db->ReadLastBlockFile(m_last_blockfile);
369+
m_blockfile_info.resize(m_last_blockfile + 1);
370+
LogPrintf("%s: last block file = %i\n", __func__, m_last_blockfile);
371+
for (int nFile = 0; nFile <= m_last_blockfile; nFile++) {
372+
m_block_tree_db->ReadBlockFileInfo(nFile, m_blockfile_info[nFile]);
373+
}
374+
LogPrintf("%s: last block file info: %s\n", __func__, m_blockfile_info[m_last_blockfile].ToString());
375+
for (int nFile = m_last_blockfile + 1; true; nFile++) {
368376
CBlockFileInfo info;
369377
if (m_block_tree_db->ReadBlockFileInfo(nFile, info)) {
370-
vinfoBlockFile.push_back(info);
378+
m_blockfile_info.push_back(info);
371379
} else {
372380
break;
373381
}
@@ -425,7 +433,7 @@ bool IsBlockPruned(const CBlockIndex* pblockindex)
425433
// If we're using -prune with -reindex, then delete block files that will be ignored by the
426434
// reindex. Since reindexing works by starting at block file 0 and looping until a blockfile
427435
// is missing, do the same here to delete any later block files after a gap. Also delete all
428-
// rev files since they'll be rewritten by the reindex anyway. This ensures that vinfoBlockFile
436+
// rev files since they'll be rewritten by the reindex anyway. This ensures that m_blockfile_info
429437
// is in sync with what's actually on disk by the time we start downloading, so that pruning
430438
// works correctly.
431439
void CleanupBlockRevFiles()
@@ -470,11 +478,11 @@ std::string CBlockFileInfo::ToString() const
470478
return strprintf("CBlockFileInfo(blocks=%u, size=%u, heights=%u...%u, time=%s...%s)", nBlocks, nSize, nHeightFirst, nHeightLast, FormatISO8601Date(nTimeFirst), FormatISO8601Date(nTimeLast));
471479
}
472480

473-
CBlockFileInfo* GetBlockFileInfo(size_t n)
481+
CBlockFileInfo* BlockManager::GetBlockFileInfo(size_t n)
474482
{
475483
LOCK(cs_LastBlockFile);
476484

477-
return &vinfoBlockFile.at(n);
485+
return &m_blockfile_info.at(n);
478486
}
479487

480488
static bool UndoWriteToDisk(const CBlockUndo& blockundo, FlatFilePos& pos, const uint256& hashBlock, const CMessageHeader::MessageStartChars& messageStart)
@@ -538,32 +546,32 @@ bool UndoReadFromDisk(CBlockUndo& blockundo, const CBlockIndex* pindex)
538546
return true;
539547
}
540548

541-
static void FlushUndoFile(int block_file, bool finalize = false)
549+
void BlockManager::FlushUndoFile(int block_file, bool finalize)
542550
{
543-
FlatFilePos undo_pos_old(block_file, vinfoBlockFile[block_file].nUndoSize);
551+
FlatFilePos undo_pos_old(block_file, m_blockfile_info[block_file].nUndoSize);
544552
if (!UndoFileSeq().Flush(undo_pos_old, finalize)) {
545553
AbortNode("Flushing undo file to disk failed. This is likely the result of an I/O error.");
546554
}
547555
}
548556

549-
void FlushBlockFile(bool fFinalize = false, bool finalize_undo = false)
557+
void BlockManager::FlushBlockFile(bool fFinalize, bool finalize_undo)
550558
{
551559
LOCK(cs_LastBlockFile);
552-
FlatFilePos block_pos_old(nLastBlockFile, vinfoBlockFile[nLastBlockFile].nSize);
560+
FlatFilePos block_pos_old(m_last_blockfile, m_blockfile_info[m_last_blockfile].nSize);
553561
if (!BlockFileSeq().Flush(block_pos_old, fFinalize)) {
554562
AbortNode("Flushing block file to disk failed. This is likely the result of an I/O error.");
555563
}
556564
// we do not always flush the undo file, as the chain tip may be lagging behind the incoming blocks,
557565
// e.g. during IBD or a sync after a node going offline
558-
if (!fFinalize || finalize_undo) FlushUndoFile(nLastBlockFile, finalize_undo);
566+
if (!fFinalize || finalize_undo) FlushUndoFile(m_last_blockfile, finalize_undo);
559567
}
560568

561-
uint64_t CalculateCurrentUsage()
569+
uint64_t BlockManager::CalculateCurrentUsage()
562570
{
563571
LOCK(cs_LastBlockFile);
564572

565573
uint64_t retval = 0;
566-
for (const CBlockFileInfo& file : vinfoBlockFile) {
574+
for (const CBlockFileInfo& file : m_blockfile_info) {
567575
retval += file.nSize + file.nUndoSize;
568576
}
569577
return retval;
@@ -605,44 +613,44 @@ fs::path GetBlockPosFilename(const FlatFilePos& pos)
605613
return BlockFileSeq().FileName(pos);
606614
}
607615

608-
bool FindBlockPos(FlatFilePos& pos, unsigned int nAddSize, unsigned int nHeight, CChain& active_chain, uint64_t nTime, bool fKnown = false)
616+
bool BlockManager::FindBlockPos(FlatFilePos& pos, unsigned int nAddSize, unsigned int nHeight, CChain& active_chain, uint64_t nTime, bool fKnown)
609617
{
610618
LOCK(cs_LastBlockFile);
611619

612-
unsigned int nFile = fKnown ? pos.nFile : nLastBlockFile;
613-
if (vinfoBlockFile.size() <= nFile) {
614-
vinfoBlockFile.resize(nFile + 1);
620+
unsigned int nFile = fKnown ? pos.nFile : m_last_blockfile;
621+
if (m_blockfile_info.size() <= nFile) {
622+
m_blockfile_info.resize(nFile + 1);
615623
}
616624

617625
bool finalize_undo = false;
618626
if (!fKnown) {
619-
while (vinfoBlockFile[nFile].nSize + nAddSize >= (gArgs.GetBoolArg("-fastprune", false) ? 0x10000 /* 64kb */ : MAX_BLOCKFILE_SIZE)) {
627+
while (m_blockfile_info[nFile].nSize + nAddSize >= (gArgs.GetBoolArg("-fastprune", false) ? 0x10000 /* 64kb */ : MAX_BLOCKFILE_SIZE)) {
620628
// when the undo file is keeping up with the block file, we want to flush it explicitly
621629
// when it is lagging behind (more blocks arrive than are being connected), we let the
622630
// undo block write case handle it
623-
finalize_undo = (vinfoBlockFile[nFile].nHeightLast == (unsigned int)active_chain.Tip()->nHeight);
631+
finalize_undo = (m_blockfile_info[nFile].nHeightLast == (unsigned int)active_chain.Tip()->nHeight);
624632
nFile++;
625-
if (vinfoBlockFile.size() <= nFile) {
626-
vinfoBlockFile.resize(nFile + 1);
633+
if (m_blockfile_info.size() <= nFile) {
634+
m_blockfile_info.resize(nFile + 1);
627635
}
628636
}
629637
pos.nFile = nFile;
630-
pos.nPos = vinfoBlockFile[nFile].nSize;
638+
pos.nPos = m_blockfile_info[nFile].nSize;
631639
}
632640

633-
if ((int)nFile != nLastBlockFile) {
641+
if ((int)nFile != m_last_blockfile) {
634642
if (!fKnown) {
635-
LogPrint(BCLog::BLOCKSTORE, "Leaving block file %i: %s\n", nLastBlockFile, vinfoBlockFile[nLastBlockFile].ToString());
643+
LogPrint(BCLog::BLOCKSTORE, "Leaving block file %i: %s\n", m_last_blockfile, m_blockfile_info[m_last_blockfile].ToString());
636644
}
637645
FlushBlockFile(!fKnown, finalize_undo);
638-
nLastBlockFile = nFile;
646+
m_last_blockfile = nFile;
639647
}
640648

641-
vinfoBlockFile[nFile].AddBlock(nHeight, nTime);
649+
m_blockfile_info[nFile].AddBlock(nHeight, nTime);
642650
if (fKnown) {
643-
vinfoBlockFile[nFile].nSize = std::max(pos.nPos + nAddSize, vinfoBlockFile[nFile].nSize);
651+
m_blockfile_info[nFile].nSize = std::max(pos.nPos + nAddSize, m_blockfile_info[nFile].nSize);
644652
} else {
645-
vinfoBlockFile[nFile].nSize += nAddSize;
653+
m_blockfile_info[nFile].nSize += nAddSize;
646654
}
647655

648656
if (!fKnown) {
@@ -652,31 +660,31 @@ bool FindBlockPos(FlatFilePos& pos, unsigned int nAddSize, unsigned int nHeight,
652660
return AbortNode("Disk space is too low!", _("Disk space is too low!"));
653661
}
654662
if (bytes_allocated != 0 && fPruneMode) {
655-
fCheckForPruning = true;
663+
m_check_for_pruning = true;
656664
}
657665
}
658666

659-
setDirtyFileInfo.insert(nFile);
667+
m_dirty_fileinfo.insert(nFile);
660668
return true;
661669
}
662670

663-
static bool FindUndoPos(BlockValidationState& state, int nFile, FlatFilePos& pos, unsigned int nAddSize)
671+
bool BlockManager::FindUndoPos(BlockValidationState& state, int nFile, FlatFilePos& pos, unsigned int nAddSize)
664672
{
665673
pos.nFile = nFile;
666674

667675
LOCK(cs_LastBlockFile);
668676

669-
pos.nPos = vinfoBlockFile[nFile].nUndoSize;
670-
vinfoBlockFile[nFile].nUndoSize += nAddSize;
671-
setDirtyFileInfo.insert(nFile);
677+
pos.nPos = m_blockfile_info[nFile].nUndoSize;
678+
m_blockfile_info[nFile].nUndoSize += nAddSize;
679+
m_dirty_fileinfo.insert(nFile);
672680

673681
bool out_of_space;
674682
size_t bytes_allocated = UndoFileSeq().Allocate(pos, nAddSize, out_of_space);
675683
if (out_of_space) {
676684
return AbortNode(state, "Disk space is too low!", _("Disk space is too low!"));
677685
}
678686
if (bytes_allocated != 0 && fPruneMode) {
679-
fCheckForPruning = true;
687+
m_check_for_pruning = true;
680688
}
681689

682690
return true;
@@ -705,7 +713,7 @@ static bool WriteBlockToDisk(const CBlock& block, FlatFilePos& pos, const CMessa
705713
return true;
706714
}
707715

708-
bool WriteUndoDataForBlock(const CBlockUndo& blockundo, BlockValidationState& state, CBlockIndex* pindex, const CChainParams& chainparams)
716+
bool BlockManager::WriteUndoDataForBlock(const CBlockUndo& blockundo, BlockValidationState& state, CBlockIndex* pindex, const CChainParams& chainparams)
709717
{
710718
// Write undo information to disk
711719
if (pindex->GetUndoPos().IsNull()) {
@@ -721,14 +729,14 @@ bool WriteUndoDataForBlock(const CBlockUndo& blockundo, BlockValidationState& st
721729
// in the block file info as below; note that this does not catch the case where the undo writes are keeping up
722730
// with the block writes (usually when a synced up node is getting newly mined blocks) -- this case is caught in
723731
// the FindBlockPos function
724-
if (_pos.nFile < nLastBlockFile && static_cast<uint32_t>(pindex->nHeight) == vinfoBlockFile[_pos.nFile].nHeightLast) {
732+
if (_pos.nFile < m_last_blockfile && static_cast<uint32_t>(pindex->nHeight) == m_blockfile_info[_pos.nFile].nHeightLast) {
725733
FlushUndoFile(_pos.nFile, true);
726734
}
727735

728736
// update nUndoPos in block index
729737
pindex->nUndoPos = _pos.nPos;
730738
pindex->nStatus |= BLOCK_HAVE_UNDO;
731-
setDirtyBlockIndex.insert(pindex);
739+
m_dirty_blockindex.insert(pindex);
732740
}
733741

734742
return true;
@@ -825,7 +833,7 @@ bool ReadRawBlockFromDisk(std::vector<uint8_t>& block, const CBlockIndex* pindex
825833
}
826834

827835
/** Store block on disk. If dbp is non-nullptr, the file is known to already reside on disk */
828-
FlatFilePos SaveBlockToDisk(const CBlock& block, int nHeight, CChain& active_chain, const CChainParams& chainparams, const FlatFilePos* dbp)
836+
FlatFilePos BlockManager::SaveBlockToDisk(const CBlock& block, int nHeight, CChain& active_chain, const CChainParams& chainparams, const FlatFilePos* dbp)
829837
{
830838
unsigned int nBlockSize = ::GetSerializeSize(block, CLIENT_VERSION);
831839
FlatFilePos blockPos;

0 commit comments

Comments
 (0)