From 4e0f31f9a0de3091be1d9e63d5656c27868f0db4 Mon Sep 17 00:00:00 2001 From: Ashley Holman Date: Mon, 26 Aug 2013 11:46:06 +0930 Subject: [PATCH] Don't store or send blocks forked before last checkpoint. --- src/main.cpp | 24 +++++++++++++++++++++++- 1 file changed, 23 insertions(+), 1 deletion(-) diff --git a/src/main.cpp b/src/main.cpp index 51703c2f2..8858fa732 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -2185,6 +2185,11 @@ bool CBlock::AcceptBlock(CValidationState &state, CDiskBlockPos *dbp) if (!Checkpoints::CheckBlock(nHeight, hash)) return state.DoS(100, error("AcceptBlock() : rejected by checkpoint lock-in at %d", nHeight)); + // Don't accept any forks from the main chain prior to last checkpoint + CBlockIndex* pcheckpoint = Checkpoints::GetLastCheckpoint(mapBlockIndex); + if (pcheckpoint && nHeight < pcheckpoint->nHeight) + return state.DoS(100, error("AcceptBlock() : forked chain older than last checkpoint (height %d)", nHeight)); + // Reject block.nVersion=1 blocks when 95% (75% on testnet) of the network has upgraded: if (nVersion < 2) { @@ -3087,11 +3092,28 @@ void static ProcessGetData(CNode* pfrom) if (inv.type == MSG_BLOCK || inv.type == MSG_FILTERED_BLOCK) { - // Send block from disk + bool send = true; map::iterator mi = mapBlockIndex.find(inv.hash); pfrom->nBlocksRequested++; if (mi != mapBlockIndex.end()) { + // If the requested block is at a height below our last + // checkpoint, only serve it if it's in the checkpointed chain + int nHeight = ((*mi).second)->nHeight; + CBlockIndex* pcheckpoint = Checkpoints::GetLastCheckpoint(mapBlockIndex); + if (pcheckpoint && nHeight < pcheckpoint->nHeight) { + if (!((*mi).second)->IsInMainChain()) + { + printf("ProcessGetData(): ignoring request for old block that isn't in the main chain\n"); + send = false; + } + } + } else { + send = false; + } + if (send) + { + // Send block from disk CBlock block; block.ReadFromDisk((*mi).second); if (inv.type == MSG_BLOCK)