Browse Source

Pulled AcceptBlock out of CBlock.

miguelfreitas
Eric Lombrozo 12 years ago
parent
commit
2a4d3464fd
  1. 32
      src/main.cpp
  2. 9
      src/main.h

32
src/main.cpp

@ -2246,10 +2246,10 @@ bool CheckBlock(const CBlock& block, CValidationState& state, bool fCheckPOW, bo
return true; return true;
} }
bool CBlock::AcceptBlock(CValidationState &state, CDiskBlockPos *dbp) bool AcceptBlock(CBlock& block, CValidationState& state, CDiskBlockPos* dbp)
{ {
// Check for duplicate // Check for duplicate
uint256 hash = GetHash(); uint256 hash = block.GetHash();
if (mapBlockIndex.count(hash)) if (mapBlockIndex.count(hash))
return state.Invalid(error("AcceptBlock() : block already in mapBlockIndex")); return state.Invalid(error("AcceptBlock() : block already in mapBlockIndex"));
@ -2257,23 +2257,23 @@ bool CBlock::AcceptBlock(CValidationState &state, CDiskBlockPos *dbp)
CBlockIndex* pindexPrev = NULL; CBlockIndex* pindexPrev = NULL;
int nHeight = 0; int nHeight = 0;
if (hash != Params().HashGenesisBlock()) { if (hash != Params().HashGenesisBlock()) {
map<uint256, CBlockIndex*>::iterator mi = mapBlockIndex.find(hashPrevBlock); map<uint256, CBlockIndex*>::iterator mi = mapBlockIndex.find(block.hashPrevBlock);
if (mi == mapBlockIndex.end()) if (mi == mapBlockIndex.end())
return state.DoS(10, error("AcceptBlock() : prev block not found")); return state.DoS(10, error("AcceptBlock() : prev block not found"));
pindexPrev = (*mi).second; pindexPrev = (*mi).second;
nHeight = pindexPrev->nHeight+1; nHeight = pindexPrev->nHeight+1;
// Check proof of work // Check proof of work
if (nBits != GetNextWorkRequired(pindexPrev, this)) if (block.nBits != GetNextWorkRequired(pindexPrev, &block))
return state.DoS(100, error("AcceptBlock() : incorrect proof of work")); return state.DoS(100, error("AcceptBlock() : incorrect proof of work"));
// Check timestamp against prev // Check timestamp against prev
if (GetBlockTime() <= pindexPrev->GetMedianTimePast()) if (block.GetBlockTime() <= pindexPrev->GetMedianTimePast())
return state.Invalid(error("AcceptBlock() : block's timestamp is too early")); return state.Invalid(error("AcceptBlock() : block's timestamp is too early"));
// Check that all transactions are finalized // Check that all transactions are finalized
BOOST_FOREACH(const CTransaction& tx, vtx) BOOST_FOREACH(const CTransaction& tx, block.vtx)
if (!IsFinalTx(tx, nHeight, GetBlockTime())) if (!IsFinalTx(tx, nHeight, block.GetBlockTime()))
return state.DoS(10, error("AcceptBlock() : contains a non-final transaction")); return state.DoS(10, error("AcceptBlock() : contains a non-final transaction"));
// Check that the block chain matches the known block chain up to a checkpoint // Check that the block chain matches the known block chain up to a checkpoint
@ -2281,7 +2281,7 @@ bool CBlock::AcceptBlock(CValidationState &state, CDiskBlockPos *dbp)
return state.DoS(100, error("AcceptBlock() : rejected by checkpoint lock-in at %d", nHeight)); return state.DoS(100, error("AcceptBlock() : rejected by checkpoint lock-in at %d", nHeight));
// Reject block.nVersion=1 blocks when 95% (75% on testnet) of the network has upgraded: // Reject block.nVersion=1 blocks when 95% (75% on testnet) of the network has upgraded:
if (nVersion < 2) if (block.nVersion < 2)
{ {
if ((!TestNet() && CBlockIndex::IsSuperMajority(2, pindexPrev, 950, 1000)) || if ((!TestNet() && CBlockIndex::IsSuperMajority(2, pindexPrev, 950, 1000)) ||
(TestNet() && CBlockIndex::IsSuperMajority(2, pindexPrev, 75, 100))) (TestNet() && CBlockIndex::IsSuperMajority(2, pindexPrev, 75, 100)))
@ -2290,14 +2290,14 @@ bool CBlock::AcceptBlock(CValidationState &state, CDiskBlockPos *dbp)
} }
} }
// Enforce block.nVersion=2 rule that the coinbase starts with serialized block height // Enforce block.nVersion=2 rule that the coinbase starts with serialized block height
if (nVersion >= 2) if (block.nVersion >= 2)
{ {
// if 750 of the last 1,000 blocks are version 2 or greater (51/100 if testnet): // if 750 of the last 1,000 blocks are version 2 or greater (51/100 if testnet):
if ((!TestNet() && CBlockIndex::IsSuperMajority(2, pindexPrev, 750, 1000)) || if ((!TestNet() && CBlockIndex::IsSuperMajority(2, pindexPrev, 750, 1000)) ||
(TestNet() && CBlockIndex::IsSuperMajority(2, pindexPrev, 51, 100))) (TestNet() && CBlockIndex::IsSuperMajority(2, pindexPrev, 51, 100)))
{ {
CScript expect = CScript() << nHeight; CScript expect = CScript() << nHeight;
if (!std::equal(expect.begin(), expect.end(), vtx[0].vin[0].scriptSig.begin())) if (!std::equal(expect.begin(), expect.end(), block.vtx[0].vin[0].scriptSig.begin()))
return state.DoS(100, error("AcceptBlock() : block height mismatch in coinbase")); return state.DoS(100, error("AcceptBlock() : block height mismatch in coinbase"));
} }
} }
@ -2305,16 +2305,16 @@ bool CBlock::AcceptBlock(CValidationState &state, CDiskBlockPos *dbp)
// Write block to history file // Write block to history file
try { try {
unsigned int nBlockSize = ::GetSerializeSize(*this, SER_DISK, CLIENT_VERSION); unsigned int nBlockSize = ::GetSerializeSize(block, SER_DISK, CLIENT_VERSION);
CDiskBlockPos blockPos; CDiskBlockPos blockPos;
if (dbp != NULL) if (dbp != NULL)
blockPos = *dbp; blockPos = *dbp;
if (!FindBlockPos(state, blockPos, nBlockSize+8, nHeight, nTime, dbp != NULL)) if (!FindBlockPos(state, blockPos, nBlockSize+8, nHeight, block.nTime, dbp != NULL))
return error("AcceptBlock() : FindBlockPos failed"); return error("AcceptBlock() : FindBlockPos failed");
if (dbp == NULL) if (dbp == NULL)
if (!WriteBlockToDisk(*this, blockPos)) if (!WriteBlockToDisk(block, blockPos))
return state.Abort(_("Failed to write block")); return state.Abort(_("Failed to write block"));
if (!AddToBlockIndex(*this, state, blockPos)) if (!AddToBlockIndex(block, state, blockPos))
return error("AcceptBlock() : AddToBlockIndex failed"); return error("AcceptBlock() : AddToBlockIndex failed");
} catch(std::runtime_error &e) { } catch(std::runtime_error &e) {
return state.Abort(_("System error: ") + e.what()); return state.Abort(_("System error: ") + e.what());
@ -2407,7 +2407,7 @@ bool ProcessBlock(CValidationState &state, CNode* pfrom, CBlock* pblock, CDiskBl
} }
// Store to disk // Store to disk
if (!pblock->AcceptBlock(state, dbp)) if (!AcceptBlock(*pblock, state, dbp))
return error("ProcessBlock() : AcceptBlock FAILED"); return error("ProcessBlock() : AcceptBlock FAILED");
// Recursively process any orphan blocks that depended on this one // Recursively process any orphan blocks that depended on this one
@ -2423,7 +2423,7 @@ bool ProcessBlock(CValidationState &state, CNode* pfrom, CBlock* pblock, CDiskBl
CBlock* pblockOrphan = (*mi).second; CBlock* pblockOrphan = (*mi).second;
// Use a dummy CValidationState so someone can't setup nodes to counter-DoS based on orphan resolution (that is, feeding people an invalid block based on LegitBlockX in order to get anyone relaying LegitBlockX banned) // Use a dummy CValidationState so someone can't setup nodes to counter-DoS based on orphan resolution (that is, feeding people an invalid block based on LegitBlockX in order to get anyone relaying LegitBlockX banned)
CValidationState stateDummy; CValidationState stateDummy;
if (pblockOrphan->AcceptBlock(stateDummy)) if (AcceptBlock(*pblockOrphan, stateDummy))
vWorkQueue.push_back(pblockOrphan->GetHash()); vWorkQueue.push_back(pblockOrphan->GetHash());
mapOrphanBlocks.erase(pblockOrphan->GetHash()); mapOrphanBlocks.erase(pblockOrphan->GetHash());
delete pblockOrphan; delete pblockOrphan;

9
src/main.h

@ -701,11 +701,6 @@ public:
printf("%s ", vMerkleTree[i].ToString().c_str()); printf("%s ", vMerkleTree[i].ToString().c_str());
printf("\n"); printf("\n");
} }
// Store block on disk
// if dbp is provided, the file is known to already reside on disk
bool AcceptBlock(CValidationState &state, CDiskBlockPos *dbp = NULL);
}; };
@ -732,6 +727,10 @@ bool AddToBlockIndex(CBlock& block, CValidationState& state, const CDiskBlockPos
// Context-independent validity checks // Context-independent validity checks
bool CheckBlock(const CBlock& block, CValidationState& state, bool fCheckPOW = true, bool fCheckMerkleRoot = true); bool CheckBlock(const CBlock& block, CValidationState& state, bool fCheckPOW = true, bool fCheckMerkleRoot = true);
// Store block on disk
// if dbp is provided, the file is known to already reside on disk
bool AcceptBlock(CBlock& block, CValidationState& state, CDiskBlockPos* dbp = NULL);
class CBlockFileInfo class CBlockFileInfo

Loading…
Cancel
Save