From 62cbf0432721c3041aed3e168b4962ac926f09ed Mon Sep 17 00:00:00 2001 From: Ross Nicoll Date: Sun, 24 Sep 2017 15:56:19 +0100 Subject: [PATCH 1/3] Sync changes from Dogecoin 1.10 --- src/dogecoin.cpp | 21 +++++++++++++++++++-- src/dogecoin.h | 1 + src/pow.cpp | 15 ++++++++++++++- src/test/auxpow_tests.cpp | 4 +++- 4 files changed, 37 insertions(+), 4 deletions(-) diff --git a/src/dogecoin.cpp b/src/dogecoin.cpp index 8ac2782ba..76db22f94 100644 --- a/src/dogecoin.cpp +++ b/src/dogecoin.cpp @@ -16,6 +16,24 @@ int static generateMTRandom(unsigned int s, int range) return dist(gen); } +// Dogecoin: Normally minimum difficulty blocks can only occur in between +// retarget blocks. However, once we introduce Digishield every block is +// a retarget, so we need to handle minimum difficulty on all blocks. +bool AllowDigishieldMinDifficultyForBlock(const CBlockIndex* pindexLast, const CBlockHeader *pblock, const Consensus::Params& params) +{ + // check if the chain allows minimum difficulty blocks + if (!params.fPowAllowMinDifficultyBlocks) + return false; + + // check if the chain allows minimum difficulty blocks on recalc blocks + if (pindexLast->nHeight < 157500) + // if (!params.fPowAllowDigishieldMinDifficultyBlocks) + return false; + + // Allow for a minimum block time if the elapsed time > 2*nTargetSpacing + return (pblock->GetBlockTime() > pindexLast->GetBlockTime() + params.nPowTargetSpacing*2); +} + unsigned int CalculateDogecoinNextWorkRequired(const CBlockIndex* pindexLast, int64_t nFirstBlockTime, const Consensus::Params& params) { int nHeight = pindexLast->nHeight + 1; @@ -88,8 +106,7 @@ bool CheckAuxPowProofOfWork(const CBlockHeader& block, const Consensus::Params& params.nAuxpowChainId, block.nVersion); /* If there is no auxpow, just check the block hash. */ - if (!block.auxpow) - { + if (!block.auxpow) { if (block.IsAuxpow()) return error("%s : no auxpow on block with auxpow version", __func__); diff --git a/src/dogecoin.h b/src/dogecoin.h index edc07b5f5..e466d1e98 100644 --- a/src/dogecoin.h +++ b/src/dogecoin.h @@ -6,6 +6,7 @@ #include "chain.h" #include "chainparams.h" +bool AllowDigishieldMinDifficultyForBlock(const CBlockIndex* pindexLast, const CBlockHeader *pblock, const Consensus::Params& params); CAmount GetDogecoinBlockSubsidy(int nHeight, const Consensus::Params& consensusParams, uint256 prevHash); unsigned int CalculateDogecoinNextWorkRequired(const CBlockIndex* pindexLast, int64_t nLastRetargetTime, const Consensus::Params& params); diff --git a/src/pow.cpp b/src/pow.cpp index a8d0efdab..8bbb66a70 100644 --- a/src/pow.cpp +++ b/src/pow.cpp @@ -21,8 +21,21 @@ unsigned int GetNextWorkRequired(const CBlockIndex* pindexLast, const CBlockHead if (pindexLast == NULL) return nProofOfWorkLimit; + // Dogecoin: Special rules for minimum difficulty blocks with Digishield + if (AllowDigishieldMinDifficultyForBlock(pindexLast, pblock, params)) + { + // Special difficulty rule for testnet: + // If the new block's timestamp is more than 2* nTargetSpacing minutes + // then allow mining of a min-difficulty block. + return nProofOfWorkLimit; + } + // Only change once per difficulty adjustment interval - if ((pindexLast->nHeight+1) % params.DifficultyAdjustmentInterval() != 0) + bool fNewDifficultyProtocol = (pindexLast->nHeight >= 145000); + const int64_t difficultyAdjustmentInterval = fNewDifficultyProtocol + ? 1 + : params.DifficultyAdjustmentInterval(); + if ((pindexLast->nHeight+1) % difficultyAdjustmentInterval != 0) { if (params.fPowAllowMinDifficultyBlocks) { diff --git a/src/test/auxpow_tests.cpp b/src/test/auxpow_tests.cpp index eaad49eef..5cb2e3269 100644 --- a/src/test/auxpow_tests.cpp +++ b/src/test/auxpow_tests.cpp @@ -362,7 +362,9 @@ BOOST_AUTO_TEST_CASE(auxpow_pow) mineBlock(block, true); BOOST_CHECK(CheckAuxPowProofOfWork(block, params)); - block.nVersion = 2; + // Dogecoin block version 2 can be both AuxPoW and regular, so test 3 + + block.nVersion = 3; mineBlock(block, true); BOOST_CHECK(!CheckAuxPowProofOfWork(block, params)); From 493709b829f3d3e97a0ae025cb83c7075e51bf98 Mon Sep 17 00:00:00 2001 From: Ross Nicoll Date: Sun, 19 Nov 2017 22:10:34 +0000 Subject: [PATCH 2/3] Correct PoW calculation logic to use locally calcualted difficulty --- src/pow.cpp | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/pow.cpp b/src/pow.cpp index 8bbb66a70..b569e709a 100644 --- a/src/pow.cpp +++ b/src/pow.cpp @@ -58,9 +58,9 @@ unsigned int GetNextWorkRequired(const CBlockIndex* pindexLast, const CBlockHead // Litecoin: This fixes an issue where a 51% attack can change difficulty at will. // Go back the full period unless it's the first retarget after genesis. Code courtesy of Art Forz - int blockstogoback = params.DifficultyAdjustmentInterval()-1; - if ((pindexLast->nHeight+1) != params.DifficultyAdjustmentInterval()) - blockstogoback = params.DifficultyAdjustmentInterval(); + int blockstogoback = difficultyAdjustmentInterval-1; + if ((pindexLast->nHeight+1) != difficultyAdjustmentInterval) + blockstogoback = difficultyAdjustmentInterval; // Go back by what we want to be 14 days worth of blocks int nHeightFirst = pindexLast->nHeight - blockstogoback; From f1e116f711b789806a48d06462f97f8cb9604068 Mon Sep 17 00:00:00 2001 From: Ross Nicoll Date: Sun, 19 Nov 2017 22:12:19 +0000 Subject: [PATCH 3/3] Handle legacy v2 block at #66064 --- src/primitives/pureheader.h | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/primitives/pureheader.h b/src/primitives/pureheader.h index 0443a530d..841743632 100644 --- a/src/primitives/pureheader.h +++ b/src/primitives/pureheader.h @@ -149,7 +149,9 @@ public: */ inline bool IsLegacy() const { - return nVersion == 1; + return nVersion == 1 + // Dogecoin: We have a random v2 block with no AuxPoW, treat as legacy + || (nVersion == 2 && GetChainId() == 0); } };