It seems you are right. However, this rule is based on block timestamps, which gives me another idea: what about simply invalidating a block, if the block time difference is bigger than 20 minutes? Because that's what ASIC miners would want to do anyway, to reorg a long chain of CPU-mined blocks: if the difficulty is 12345678, and you can see hundreds of blocks with difficulty 1, then a single block with difficulty 12345678 will reorg all of these CPU-mined blocks in a single shot.
By the way: if we are entering a hard-fork territory, and if testnet4 coins are traded, then what about switching to testnet5 with new rules instead?
And also, in case of any forks, there is a question, how many miners will actually support new changes. Because in case of new timewarp rules, we saw hundreds of blocks being reorged, because some ASIC miners didn't upgrade their code: https://github.com/bitcoin/bitcoin/issues/30786
And even when mempool.space upgraded their code, a few weeks after that, I could still see some ASIC nodes in the wild, which were mining on the wrong branch, and with just a CPU, it was possible to fork them once every 2016 blocks, for a few hundred blocks.
> Op 19 mrt 2025, om 08:01 heeft Garlo Nicon <garlo...@gmail.com> het volgende geschreven:
>
> > I propose to fix this by removing the difficulty reset rule from testnet4 through a flag day hard fork on 2026-01-01.
>
> You can do that in a soft-fork way. Just rejecting blocks with difficulty=1, and requiring always a block with the true network difficulty, is a valid soft-fork.
Unfortunately it's a hard-fork.
> So, I assume if you change "fPowAllowMinDifficultyBlocks" from "true" to "false", when block time will be greater than unix time "1767225600", then you will get a valid soft-fork.
The fPowAllowMinDifficultyBlocks rule says that after 20 minutes the new block MUST have difficulty 1. A block with the real difficulty will be rejected.
This is because in general the block nBits value, which announces how much work the block has, must have an exact value. It can't be higher.
In validation.cpp we have this:
if (block.nBits != GetNextWorkRequired(pindexPrev, &block, consensusParams))
return state.Invalid(BlockValidationResult::BLOCK_INVALID_HEADER, "bad-diffbits", "incorrect proof of work");
Inside GetNextWorkRequired there is the testnet exception rule, which Antoine proposes to drop:
if (params.fPowAllowMinDifficultyBlocks) {
// Special difficulty rule for testnet:
// If the new block's timestamp is more than 2* 10 minutes
// then allow mining of a min-difficulty block.
if (pblock->GetBlockTime() > pindexLast->GetBlockTime() + params.nPowTargetSpacing*2)
return nProofOfWorkLimit;
else
... (same difficulty as last block, unless it's a retarget)
The code comment is misleading, "allow" should be "require".
- Sjors