diff --git a/src/miner.cpp b/src/miner.cpp index f82a0a1a05302..743478112745e 100644 --- a/src/miner.cpp +++ b/src/miner.cpp @@ -470,7 +470,7 @@ CBlockTemplate* CreateNewBlock(const CScript& scriptPubKeyIn, CWallet* pwallet, return pblocktemplate.release(); } -void IncrementExtraNonce(CBlock* pblock, CBlockIndex* pindexPrev, unsigned int& nExtraNonce) +void IncrementExtraNonce(std::shared_ptr& pblock, CBlockIndex* pindexPrev, unsigned int& nExtraNonce) { // Update nExtraNonce static uint256 hashPrevBlock; @@ -517,7 +517,7 @@ CBlockTemplate* CreateNewBlockWithKey(CReserveKey& reservekey, CWallet* pwallet) return CreateNewBlock(scriptPubKey, pwallet, false); } -bool ProcessBlockFound(CBlock* pblock, CWallet& wallet, Optional& reservekey) +bool ProcessBlockFound(const std::shared_ptr& pblock, CWallet& wallet, Optional& reservekey) { LogPrintf("%s\n", pblock->ToString()); LogPrintf("generated %s\n", FormatMoney(pblock->vtx[0]->vout[0].nValue)); @@ -628,7 +628,7 @@ void BitcoinMiner(CWallet* pwallet, bool fProofOfStake) CreateNewBlock(CScript(), pwallet, true, &availableCoins) : CreateNewBlockWithKey(*opReservekey, pwallet))); if (!pblocktemplate.get()) continue; - CBlock* pblock = &pblocktemplate->block; + std::shared_ptr pblock = std::make_shared(pblocktemplate->block); // POS - block found: process it if (fProofOfStake) { @@ -713,7 +713,7 @@ void BitcoinMiner(CWallet* pwallet, bool fProofOfStake) ) break; // Update nTime every few seconds - UpdateTime(pblock, pindexPrev); + UpdateTime(pblock.get(), pindexPrev); if (Params().GetConsensus().fPowAllowMinDifficultyBlocks) { // Changing pblock->nTime can change work required on testnet: hashTarget.SetCompact(pblock->nBits); diff --git a/src/miner.h b/src/miner.h index 8b9116a7ed7bf..9f77fd3e867b4 100644 --- a/src/miner.h +++ b/src/miner.h @@ -26,7 +26,7 @@ struct CBlockTemplate; /** Generate a new block, without valid proof-of-work */ CBlockTemplate* CreateNewBlock(const CScript& scriptPubKeyIn, CWallet* pwallet, bool fProofOfStake, std::vector* availableCoins = nullptr); /** Modify the extranonce in a block */ -void IncrementExtraNonce(CBlock* pblock, CBlockIndex* pindexPrev, unsigned int& nExtraNonce); +void IncrementExtraNonce(std::shared_ptr& pblock, CBlockIndex* pindexPrev, unsigned int& nExtraNonce); /** Check mined block */ void UpdateTime(CBlockHeader* block, const CBlockIndex* pindexPrev); diff --git a/src/net_processing.cpp b/src/net_processing.cpp index e0d337b5882ba..427f75a85266d 100644 --- a/src/net_processing.cpp +++ b/src/net_processing.cpp @@ -1581,18 +1581,18 @@ bool static ProcessMessage(CNode* pfrom, std::string strCommand, CDataStream& vR else if (strCommand == NetMsgType::BLOCK && !fImporting && !fReindex) // Ignore blocks received while importing { - CBlock block; - vRecv >> block; - const uint256& hashBlock = block.GetHash(); + std::shared_ptr pblock = std::make_shared(); + vRecv >> *pblock; + const uint256& hashBlock = pblock->GetHash(); CInv inv(MSG_BLOCK, hashBlock); LogPrint(BCLog::NET, "received block %s peer=%d\n", inv.hash.ToString(), pfrom->id); //sometimes we will be sent their most recent block and its not the one we want, in that case tell where we are - if (!mapBlockIndex.count(block.hashPrevBlock)) { + if (!mapBlockIndex.count(pblock->hashPrevBlock)) { if (find(pfrom->vBlockRequested.begin(), pfrom->vBlockRequested.end(), hashBlock) != pfrom->vBlockRequested.end()) { //we already asked for this block, so lets work backwards and ask for the previous block - connman.PushMessage(pfrom, msgMaker.Make(NetMsgType::GETBLOCKS, chainActive.GetLocator(), block.hashPrevBlock)); - pfrom->vBlockRequested.push_back(block.hashPrevBlock); + connman.PushMessage(pfrom, msgMaker.Make(NetMsgType::GETBLOCKS, chainActive.GetLocator(), pblock->hashPrevBlock)); + pfrom->vBlockRequested.push_back(pblock->hashPrevBlock); } else { //ask to sync to this block connman.PushMessage(pfrom, msgMaker.Make(NetMsgType::GETBLOCKS, chainActive.GetLocator(), hashBlock)); @@ -1604,7 +1604,7 @@ bool static ProcessMessage(CNode* pfrom, std::string strCommand, CDataStream& vR if (!mapBlockIndex.count(hashBlock)) { WITH_LOCK(cs_main, MarkBlockAsReceived(hashBlock); ); bool fAccepted = true; - ProcessNewBlock(state, pfrom, &block, nullptr, &fAccepted); + ProcessNewBlock(state, pfrom, pblock, nullptr, &fAccepted); if (!fAccepted) { CheckBlockSpam(state, pfrom, hashBlock); } @@ -1622,7 +1622,7 @@ bool static ProcessMessage(CNode* pfrom, std::string strCommand, CDataStream& vR //disconnect this node if its old protocol version pfrom->DisconnectOldProtocol(pfrom->nVersion, ActiveProtocol(), strCommand); } else { - LogPrint(BCLog::NET, "%s : Already processed block %s, skipping ProcessNewBlock()\n", __func__, block.GetHash().GetHex()); + LogPrint(BCLog::NET, "%s : Already processed block %s, skipping ProcessNewBlock()\n", __func__, pblock->GetHash().GetHex()); } } } diff --git a/src/rpc/mining.cpp b/src/rpc/mining.cpp index 8637e043fb270..6f364d2913091 100644 --- a/src/rpc/mining.cpp +++ b/src/rpc/mining.cpp @@ -169,7 +169,7 @@ UniValue generate(const JSONRPCRequest& request) CreateNewBlock(CScript(), pwalletMain, true, &availableCoins) : CreateNewBlockWithKey(reservekey, pwalletMain)); if (!pblocktemplate.get()) break; - CBlock *pblock = &pblocktemplate->block; + std::shared_ptr pblock = std::make_shared(pblocktemplate->block); if(!fPoS) { { @@ -679,7 +679,8 @@ UniValue submitblock(const JSONRPCRequest& request) "\nExamples:\n" + HelpExampleCli("submitblock", "\"mydata\"") + HelpExampleRpc("submitblock", "\"mydata\"")); - CBlock block; + std::shared_ptr blockptr = std::make_shared(); + CBlock& block = *blockptr; if (!DecodeHexBlk(block, request.params[0].get_str())) throw JSONRPCError(RPC_DESERIALIZATION_ERROR, "Block decode failed"); @@ -706,7 +707,7 @@ UniValue submitblock(const JSONRPCRequest& request) CValidationState state; submitblock_StateCatcher sc(block.GetHash()); RegisterValidationInterface(&sc); - bool fAccepted = ProcessNewBlock(state, nullptr, &block, nullptr); + bool fAccepted = ProcessNewBlock(state, nullptr, blockptr, nullptr); UnregisterValidationInterface(&sc); if (fBlockPresent) { if (fAccepted && !sc.found) diff --git a/src/validation.cpp b/src/validation.cpp index bfd243ba125e0..fcd3ee47560c6 100644 --- a/src/validation.cpp +++ b/src/validation.cpp @@ -3291,7 +3291,7 @@ void CBlockIndex::BuildSkip() pskip = pprev->GetAncestor(GetSkipHeight(nHeight)); } -bool ProcessNewBlock(CValidationState& state, CNode* pfrom, const CBlock* pblock, CDiskBlockPos* dbp, bool* fAccepted) +bool ProcessNewBlock(CValidationState& state, CNode* pfrom, const std::shared_ptr pblock, CDiskBlockPos* dbp, bool* fAccepted) { AssertLockNotHeld(cs_main); @@ -3335,12 +3335,7 @@ bool ProcessNewBlock(CValidationState& state, CNode* pfrom, const CBlock* pblock } } - //TODO: This copy is a major performance regression, but callers need updated to fix this - std::shared_ptr block_ptr; - if (pblock) - block_ptr.reset(new CBlock(*pblock)); - - if (!ActivateBestChain(state, block_ptr, checked)) + if (!ActivateBestChain(state, pblock, checked)) return error("%s : ActivateBestChain failed", __func__); if (!fLiteMode) { @@ -3801,7 +3796,8 @@ bool LoadExternalBlockFile(FILE* fileIn, CDiskBlockPos* dbp) // process in case the block isn't known yet if (mapBlockIndex.count(hash) == 0 || (mapBlockIndex[hash]->nStatus & BLOCK_HAVE_DATA) == 0) { CValidationState state; - if (ProcessNewBlock(state, nullptr, &block, dbp)) + std::shared_ptr block_ptr = std::make_shared(block); + if (ProcessNewBlock(state, nullptr, block_ptr, dbp)) nLoaded++; if (state.IsError()) break; @@ -3822,7 +3818,8 @@ bool LoadExternalBlockFile(FILE* fileIn, CDiskBlockPos* dbp) LogPrintf("%s: Processing out of order child %s of %s\n", __func__, block.GetHash().ToString(), head.ToString()); CValidationState dummy; - if (ProcessNewBlock(dummy, nullptr, &block, &it->second)) { + std::shared_ptr block_ptr = std::make_shared(block); + if (ProcessNewBlock(dummy, nullptr, block_ptr, &it->second)) { nLoaded++; queue.push_back(block.GetHash()); } diff --git a/src/validation.h b/src/validation.h index cefaa619ae5ce..2220ca181d3dc 100644 --- a/src/validation.h +++ b/src/validation.h @@ -172,7 +172,7 @@ static const uint64_t nMinDiskSpace = 52428800; * @param[out] fAccepted Whether the block is accepted or not * @return True if state.IsValid() */ -bool ProcessNewBlock(CValidationState& state, CNode* pfrom, const CBlock* pblock, CDiskBlockPos* dbp, bool* fAccepted = nullptr); +bool ProcessNewBlock(CValidationState& state, CNode* pfrom, const std::shared_ptr pblock, CDiskBlockPos* dbp, bool* fAccepted = nullptr); /** Check whether enough disk space is available for an incoming block */ bool CheckDiskSpace(uint64_t nAdditionalBytes = 0); /** Open a block file (blk?????.dat) */