Hi,
Testnet4
was rolled out a year ago to address the shortcomings of testnet3. One
of those shortcomings was the difficulty reset creating havoc. [0] In
spite of this a similar rule was adopted for testnet4. [1] As a result,
testnet4 is similarly creating havoc. [2]
The goal of testnet is
to mimic the Bitcoin mainnet. This is why it is useful to have in
addition to a more control testing environment such as Signet.
The
given rationale for a difficulty reset was to let developers
occasionally mine blocks on their laptop. But you cannot have your cake
and eat it too: either the network is permissionless (PoW) or you assign
identities and privileges to some (Signet). By trying to do both at the
same time testnet4 created a loophole for abuse. As a result it failed
on both count: it neither mimics mainnet nor allows developers to mine
active blocks on their laptop.
I propose to fix this by removing
the difficulty reset rule from testnet4 through a flag day hard fork on
2026-01-01. I picked a date well in the future to minimize disruption.
This leaves enough time for a patch to be reviewed, merged, included in
the next major Bitcoin Core release, backported to previous releases and
adopted by the infrastructure running on testnet4. That should be
enough for a test network.
Let me know what you think,
Antoine
Coming back to this thread because there is a small, targeted fix within testnet4 itself, and I think the mechanism is worth stating plainly.
Testnet4 has two interacting time windows:
a) the difficulty exception, relative to the parent: a min-difficulty block is allowed once its timestamp is more than 20 minutes past the parent's (pow.cpp, nPowTargetSpacing * 2);
b) the future limit, relative to the clock: a header is rejected if its timestamp is more than 2 hours ahead of the node's time (chain.h, MAX_FUTURE_BLOCK_TIME, global to every chain).
(a) was added for testnet. (b) was inherited from mainnet, where there is no (a). The second allows the first to be chained: a miner stamps the parent plus 20 minutes, then that plus 20 minutes, and so on until the clock limit stops them. With the parent near wall time, two hours over twenty minutes is why the spoofed blocks Sjors described arrive in bursts of five or six and then stop until real time catches up.
So the minimal fix is to reduce the wall-clock allowance to one exception interval. There are two obvious ways to align the scales:
* Raise the exception to 2 hours: one min-difficulty block per two hours of silence. That is close to no exception at all, and throws away the one thing the exception is for.
* Lower the future limit to 20 minutes on testnet4: when the parent is near wall time, a min-difficulty block can be at most one window ahead of the clock, and the current five-or-six-block bursts collapse to one block ahead.
The second is the one to pick. Its exact scope: the room for a burst is
(now + future_limit - parent_time) / 20 min
so after a long period without blocks a burst is still possible, because the exception is parent-relative rather than clock-relative. What the change removes is the steady-state case, several blocks ahead from a parent near wall time, which is the behaviour this thread is about. It does not prevent competing one-block forks at minimum difficulty, and a miner can still produce a min-difficulty block every 20 minutes of real time. It keeps CPU-mineable blocks.
Mechanically it means making MAX_FUTURE_BLOCK_TIME a chain parameter and setting it to 20 minutes for testnet4; mainnet and signet keep two hours. It tightens acceptance in the soft-fork direction: at any given node time, an upgraded node accepts a subset of the headers an old node accepts. Unlike an ordinary consensus soft fork the rule is wall-clock-dependent: a header rejected as too far in the future becomes acceptable as time catches up.
The failure mode is an un-upgraded miner stamping more than 20 minutes ahead and producing headers upgraded nodes do not yet accept. Such a branch carries negligible chainwork and should be reorganised away once hash rate on the compatible branch passes it, but pools should upgrade together. A 20-minute clock tolerance is ample for a testnet; the two-hour figure dates from early Bitcoin and mainnet has no reason to touch it.
In one line: testnet4's 20-minute parent-relative exception can currently be chained through a two-hour wall-clock allowance. Reducing that allowance to one interval removes the five-or-six-block steady-state bursts while preserving the exception itself.
Melvin
--
You received this message because you are subscribed to the Google Groups "Bitcoin Development Mailing List" group.
To unsubscribe from this group and stop receiving emails from it, send an email to bitcoindev+unsubscribe@googlegroups.com.
To view this discussion visit https://groups.google.com/d/msgid/bitcoindev/hU75DurC5XToqizyA-vOKmVtmzd3uZGDKOyXuE_ogE6eQ8tPCrvX__S08fG_nrW5CjH6IUx7EPrq8KwM5KFy9ltbFBJZQCHR2ThoimRbMqU%3D%40protonmail.com.