ReducedData Temporary Softfork (BIP-110/RDTS) #34930

pull dathonohm wants to merge 29 commits into bitcoin:master from dathonohm:bip110-core-pr2 changing 61 files +4043 −222
  1. dathonohm commented at 6:59 pm on March 26, 2026: none

    This PR implements consensus changes and deployment parameters for BIP-110 (ReducedData Temporary Softfork). It is built on top of #34929, which implements the versionbits extensions needed for BIP-110’s activation. I will rebase this PR on master once #34929 is merged.

    Background

    Following BIP-110’s initial proposal in October 2025, and shortly before its acceptance into the BIPs repo, the first version of the official activation client for BIP-110 was released at the end of January as a fork of Bitcoin Knots. This client has proven immensely popular, and now comprises over 8 percent of listening nodes and over 10 percent of all nodes on the network, after just 2 months. While a few bugs were found early on, they were all swiftly resolved and the code has now been stable for several weeks.

    For those new to BIP-110, it is a proposal to temporarily limit the size of data fields at the consensus level, in order to reject the standardization of data storage as a supported use case at the consensus level. It achieves this by temporarily limiting all officially supported methods of data storage (and methods of data storage that could be or become perceived as officially supported) to 256 bytes or less, while preserving all known monetary use cases.

    This has several desirable effects, including but not limited to:

    • Reducing demand for arbitrary data storage by frustrating attempts to monetize and gamify arbitrary data.
    • Bringing consensus and policy back into closer alignment, by restoring policy limits from a few years ago in consensus.
    • Protecting the decentralization of the node network by eliminating unnecessary costs and (in some cases, extreme) risks introduced by making arbitrary data storage an officially supported function of Bitcoin.
    • Making Bitcoin better money by preventing Bitcoin payments from having to compete at an unfair disadvantage against gamified data spam.

    Motivation

    Due to BIP-110’s rising popularity, it seems prudent to augment Core with the ability to enforce the new rules, so that once BIP-110 is activated, Core users will remain secure because their nodes will follow the valid chain. While BIP-110’s mandatory signaling period is not until August, it allows for early activation if the threshold of 55% of hashpower signaling is reached before the deadline, so BIP-110’s activation could be imminent (as soon as a few weeks from now). Given this, I humbly suggest that we prepare sooner rather than later. My sincere hope is that BIP-110’s activation will heal the divide in our community and allow us all to get back to building Bitcoin into history’s greatest money.

    Deployment

    BIP-110 uses the versionbits extensions from #34929:

    • Bit: 4
    • Start: December 1, 2025 (epoch 1764547200)
    • max_activation_height: 965664 (~September 1, 2026) - mandatory activation deadline
    • active_duration: 52416 blocks (~1 year) - temporary deployment, transitions to EXPIRED after the active period
    • threshold: 1109 / 2016 (55%)

    The deployment is temporary: after active_duration blocks, the rules expire and the EXPIRED state is terminal.

    Features

    Consensus rules (when DEPLOYMENT_REDUCED_DATA is active)

    • Output scripts limited to 34 bytes (OP_RETURN limited to 83 bytes)
    • Data push size limit reduced to 256 bytes, except BIP16 redeemScript
    • DISCOURAGE_UPGRADABLE_WITNESS_PROGRAM, DISCOURAGE_UPGRADABLE_TAPROOT_VERSION, DISCOURAGE_OP_SUCCESS enforced at consensus level
    • Taproot annex forbidden
    • Taproot control block limited to 257 bytes (tree depth 7)
    • OP_IF/OP_NOTIF forbidden in Tapscript
    • Empty witness required for P2A spends
    • UTXO-height exemption: inputs spending UTXOs created before activation are exempt from script rules

    Policy

    • The above rules are enforced unconditionally in policy

    Tests

    • Unit/fuzz tests: script verification tests for each new rule, CheckTxInputsRules::OutputSizeLimit enforcement, fuzz test updates for REDUCED_DATA flag
    • feature_rdts.py: tests each consensus rule individually, policy enforcement before activation, consensus enforcement after activation
    • feature_reduced_data_utxo_height.py: pre-activation UTXO exemption, post-activation enforcement, cache-poisoning prevention
    • feature_reduced_data_temporary_deployment.py: full deployment lifecycle (DEFINED -> STARTED -> LOCKED_IN -> ACTIVE -> EXPIRED), consensus rules enforced during active period, rules stop after expiry, chain split/reorg behavior

    Commit structure (29 commits across 2 PRs)

    The first 7 commits (PR 1, #34929) are versionbits extensions: max_activation_height, active_duration/EXPIRED state, mandatory signaling enforcement, -vbparams support, and tests. These are included here temporarily so CI passes; they will be dropped if and when PR 1 merges.

    The remaining 22 commits (this PR) introduce the script validation rules first (initially unused), then wire up DEPLOYMENT_REDUCED_DATA activation, then add the remaining consensus features (coinbase output size limits, mandatory DISCOURAGE flag enforcement, and UTXO height exemption), and finally the functional tests. Every commit builds and passes all tests. One commit (a628bef9bf) is intentionally large because it breaks many tests, so test adaptations that must land atomically are bundled.

    Size

    ~200 lines non-test C++/H (excluding activation infrastructure in #34929). For comparison against activated soft forks:

    Non-test C++/H Soft fork PRs
    3209 SegWit (BIP 141/143/144) 9
    2903 Taproot (BIP 340/341/342) 11
    1005 CSV (BIP 68/112/113) 8
    ~375 BIP-110 (both PRs) 2
    143 CLTV (BIP 65) 2

    The closest apples-to-apples comparison is CSV, which similarly included new reusable activation infrastructure (BIP 9).

    CSV (BIP 68/112/113) BIP-110
    Consensus rules 120 ~47
    Activation infrastructure 605 ~175
    Other (RPC, policy, etc.) 280 ~100
    Total non-test C++/H 1005 ~375
    PRs 8 2

    BIP-110 is roughly a third of the size of CSV across both PRs.

  2. versionbits: add expiry support to versionbit deployments 731adbdad4
  3. versionbits: add max_activation_height for mandatory BIP9 activation 3444808035
  4. chainparams: support regtest vbparams for max_activation_height and active_duration 7227d5ef12
  5. test: add versionbits unit tests for max_activation_height and active_duration 402f257559
  6. chainparams: support regtest vbparams for per-deployment threshold e46a82ae82
  7. versionbits: add mandatory signaling enforcement for max_activation_height and set vbrequired during mandatory signaling d8d9d53f87
  8. test: add functional tests for modified BIP9 deployment features 28650257b6
  9. script: use TAPROOT_CONTROL_MAX_NODE_COUNT_REDUCED for non-consensus Taproot logic; adapt tests
    Co-Authored-By: Dathon Ohm <dathonohm@proton.me>
    72fe8e4361
  10. policy: enforce SCRIPT_VERIFY_REDUCED_DATA as a policy rule
    Co-Authored-By: Dathon Ohm <dathonohm@proton.me>
    d649958dbb
  11. script: Define SCRIPT_VERIFY_REDUCED_DATA verification flag (unused) to reduce data push size limit to 256 bytes (except for P2SH redeemScript push); adapt tests
    Co-Authored-By: Dathon Ohm <dathonohm@proton.me>
    Co-Authored-By: Léo Haf <leo@haf.ovh>
    e1ace4f3f2
  12. script: forbid Taproot annex with SCRIPT_VERIFY_REDUCED_DATA 70c2ba9835
  13. script: Forbid OP_IF in Tapscript with SCRIPT_VERIFY_REDUCED_DATA (still unused)
    Co-Authored-By: Dathon Ohm <dathonohm@proton.me>
    Co-Authored-By: Léo Haf <leo@haf.ovh>
    0519a33021
  14. script: Limit Taproot control block to 257 bytes for SCRIPT_VERIFY_REDUCED_DATA (still unused) 7da36fb3ba
  15. script: require empty witness for P2A spends 7275914ff1
  16. consensus: Add no-op flags to CheckTxInputs function 7e9cedae7c
  17. consensus: Define CheckTxInputsRules::OutputSizeLimit flag (unused) to cap output scripts at 83 bytes 5f60f812b6
  18. consensus: When CheckTxInputsRules::OutputSizeLimit is enforced (still never), limit non-OP_RETURN scripts to 34 bytes and OP_RETURN outputs to 83 bytes
    MAX_OUTPUT_DATA_SIZE constant definition moved here from its original commit (4a8d8d0490) due to commit reordering.
    
    Co-Authored-By: Dathon Ohm <dathonohm@proton.me>
    15ab3acbd7
  19. chainparams: add DEPLOYMENT_REDUCED_DATA temporary BIP9 deployment 98776859d1
  20. consensus: Enforce SCRIPT_VERIFY_REDUCED_DATA if DEPLOYMENT_REDUCED_DATA is active 353882e378
  21. consensus: Enforce CheckTxInputsRules::OutputSizeLimit when DEPLOYMENT_REDUCED_DATA is active; adapt tests
    Wire OutputSizeLimit to deployment with unconditional mempool enforcement. Adapt test framework and functional tests for 34-byte output script limit and 83-byte OP_RETURN limit.
    
    Test fixes from: 8257367348, c609a453a0, 9194f6f05f, b141420e59, e011d53b4d, fc62079ba1, a065a596b1, 4f371cfa2c, 5ee8102c82, ebe821e7c0 (partial)
    
    Co-Authored-By: Dathon Ohm <dathonohm@proton.me>
    Co-Authored-By: 3c853b6299 <3c853b6299@pm.me>
    Co-Authored-By: moneybadger1 <moneybadger1@proton.me>
    Co-Authored-By: Léo Haf <leohaf@orangepill.ovh>
    a628bef9bf
  22. consensus: apply output size limit to generation transactions d853544e03
  23. consensus: Enforce SCRIPT_VERIFY_DISCOURAGE_{UPGRADABLE_WITNESS_PROGRAM,UPGRADABLE_TAPROOT_VERSION,OP_SUCCESS} on blocks when DEPLOYMENT_REDUCED_DATA is active
    Co-Authored-By: Léo Haf <leo@haf.ovh>
    Co-Authored-By: Dathon Ohm <dathonohm@proton.me>
    71e6241ad2
  24. Refactor: Include all reduced_data verify flags in REDUCED_DATA_MANDATORY_VERIFY_FLAGS 15d8cbd983
  25. validation: Extend CheckInputScripts to allow overriding script validation flags on a per-input basis 4e7fb124ff
  26. validation: Exempt inputs spending UTXOs prior to reduced_data_start_height from reduced_data script validation rules
    Bugfix: validation: Do not cache the result of CheckInputScripts if flags_per_input is used (and avoid using it when unnecessary)
    
    Co-Authored-By: Dathon Ohm <dathonohm@proton.me>
    Co-Authored-By: Lőrinc <pap.lorinc@gmail.com>
    4b32998ed2
  27. test: implement functional tests for ReducedData Spec
    Co-Authored-By: Dathon Ohm <dathonohm@proton.me>
    Co-Authored-By: Léo Haf <leohaf@orangepill.ovh>
    0faef7bbd1
  28. test: Add UTXO height-based REDUCED_DATA enforcement test
    Co-Authored-By: Léo Haf <leohaf@orangepill.ovh>
    Co-Authored-By: Lőrinc <pap.lorinc@gmail.com>
    aa8c4807a5
  29. test: add functional tests for modified BIP9 temporary deployment
    Co-Authored-By: Léo Haf <leohaf@orangepill.ovh>
    cd32f0421f
  30. doc: add BIP-110 to bips.md 661aa5dc63
  31. DrahtBot commented at 6:59 pm on March 26, 2026: contributor

    ♻️ Automatically closing for now based on heuristics. Please leave a comment, if this was erroneous. Generally, please focus on creating high-quality, original content that demonstrates a clear understanding of the project’s requirements and goals.

    📝 Moderators: If this is spam, please replace the title with ., so that the thread does not appear in search results.

  32. DrahtBot closed this on Mar 26, 2026

  33. dathonohm commented at 6:59 pm on March 26, 2026: none
    This is not spam.
  34. DrahtBot commented at 7:00 pm on March 26, 2026: contributor

    The following sections might be updated with supplementary metadata relevant to reviewers and maintainers.

    Reviews

    See the guideline for information on the review process. A summary of reviews will appear here.

    LLM Linter (✨ experimental)

    Possible typos and grammar issues:

    • doc/bips.md+* [BIP 110](...): ReducedData Temporary Softfork (RDTS) consensus rules are implemented as of **FIXME: update version** ... -> FIXME: update version is left as a placeholder, which makes the “as of” information incomprehensible until replaced with an actual version.

    • test/functional/feature_rdts.py+5. Taproot control blocks larger than 257 bytes are invalid (max 7 merkle nodes = 128 leaves) -> merkle should be Merkle (spelling error).

    Possible places where comparison-specific test macros should replace generic comparisons:

    • [src/test/versionbits_tests.cpp] BOOST_CHECK_THROW(CreateChainParams(args, ChainType::REGTEST), std::runtime_error); -> Prefer BOOST_CHECK_EXCEPTION(..., std::runtime_error, HasReason("...exact expected message...")) if the precise failure reason is known/meaningful for the test.

    • [test/functional/feature_rdts.py] assert len(witness_script) > MAX_SCRIPT_ELEMENT_SIZE_REDUCED, \ ... -> Use assert_greater_than(len(witness_script), MAX_SCRIPT_ELEMENT_SIZE_REDUCED).

    • [test/functional/feature_rdts.py] assert len(large_tapscript) > MAX_SCRIPT_ELEMENT_SIZE_REDUCED, \ ... -> Use assert_greater_than(len(large_tapscript), MAX_SCRIPT_ELEMENT_SIZE_REDUCED).

    • [test/functional/feature_reduced_data_utxo_height.py] assert p2wsh_vout is not None, "P2WSH output not found" -> Use assert_not_equal(p2wsh_vout, None) (optionally keep the message via the surrounding test harness/logging if desired).

    • [test/functional/feature_reduced_data_utxo_height.py] assert self.nodes[0].getbestblockhash() == block.hash_hex -> Use assert_equal(self.nodes[0].getbestblockhash(), block.hash_hex).

    No other added Python bare assert comparisons in test/functional/ were found that clearly warrant switching to one of the provided comparison-specific helpers.

    2026-03-26 19:00:47

  35. stickies-v commented at 7:53 pm on March 26, 2026: contributor

    Good bot.

    For good measure, NACK, and I don’t think this should be reopened. There is nowhere near broad support for BIP-110, as you of course know.

  36. dathonohm commented at 8:01 pm on March 26, 2026: none
    @stickies-v On the contrary. As I noted in the top comment, over 8% of listening nodes and over 10% of all nodes are running this activation client now.
  37. stickies-v commented at 8:16 pm on March 26, 2026: contributor
    I’m not saying there’s no support. There’s very clearly no broad support. I know you know all of this, so I’m no longer going to waste my time on this thread.
  38. TheBlueMatt commented at 8:19 pm on March 26, 2026: contributor
    This should probably be locked before X discovers it and it gets brigaded to death. Obviously 8% of IPs doesn’t constitute overwhelming broad support nor lack of sustained disagreement.
  39. dathonohm commented at 8:20 pm on March 26, 2026: none
    How much more popular does BIP-110 need to become before you consider support to be “broad”, and by what metric? The activation client is rapidly growing in popularity.
  40. dathonohm commented at 8:22 pm on March 26, 2026: none
    @TheBlueMatt I think locking this PR would be a mistake. It should be reopened. It was closed by mistake.
  41. TheBlueMatt commented at 8:23 pm on March 26, 2026: contributor
    First of all, its not measured in IP addresses, second of all, if I open X/nostr and half the posts are people talking about how its a terrible idea and would destroy Bitcoin, its probably not “broadly supported”, even if the other half think it saves Bitcoin.
  42. dathonohm commented at 8:24 pm on March 26, 2026: none
    @TheBlueMatt Whether this PR is open or closed has no bearing on whether BIP-110 activates. This PR only affects whether Core users remain secure through the activation.
  43. bitcoin locked this on Mar 26, 2026

github-metadata-mirror

This is a metadata mirror of the GitHub repository bitcoin/bitcoin. This site is not affiliated with GitHub. Content is generated from a GitHub metadata backup.
generated: 2026-03-31 12:13 UTC

This site is hosted by @0xB10C
More mirrored repositories can be found on mirror.b10c.me