This week’s newsletter summarizes an idea for preventing the pinning of coinjoin transactions and describes a proposal for speculatively using hoped-for consensus changes. Also included is another entry in our limited weekly series about mempool policy, plus our regular sections describing popular questions and answers on the Bitcoin Stack Exchange, new releases and release candidates, and changes to popular Bitcoin infrastructure software.
● Preventing coinjoin pinning with v3 transaction relay: Greg Sanders posted to the Bitcoin-Dev mailing list a description for how the proposed v3 transaction relay rules could allow creating a coinjoin-style multiparty transaction that wouldn’t be vulnerable to transaction pinning. The specific concern with pinning is that one of the participants in a coinjoin can use their input to the transaction to create a conflicting transaction that prevents the coinjoin transaction from confirming.
Sanders proposes that coinjoin-style transactions can avoid this problem by having each participant initially spend their bitcoins to a script that can only be spent by either a signature from all participants in the coinjoin or by just the participant after a timelock expires. Alternatively, for a coordinated coinjoin, the coordinator and the participant must sign together (or the participant alone after the timelock expiration).
Up until the timelock expires, the participant must now get either the other parties or the coordinator to co-sign any conflicting transactions, which they are unlikely to do unless signing would be in the best interests of all the participants (e.g. a fee bump).
● Speculatively using hoped-for consensus changes: Robin Linus posted to the Bitcoin-Dev mailing list an idea for spending money to a script fragment that can’t be executed for a long time (such as 20 years). If that script fragment is interpreted under current consensus rules, it will allow miners in 20 years to claim all the funds paid to it. However, the fragment is designed so that an upgrade to the consensus rules will give the fragment a different meaning. Linus gives the example of an
OP_ZKP_VERIFYopcode that, if added to Bitcoin, will allow anyone providing a Zero-Knowledge Proof (ZKP) for a program with a particular hash to claim the funds.
This could allow people to spend BTC today to one of these scripts and use the proof of that spend to receive an equivalent amount of BTC on a sidechain or alternative chain, called a one-way peg. The BTC on the other chain could be spent repeatedly for 20 years, until the script timelock expired. Then the current owner of the BTC on the other chain could generate a ZKP proof that they owned it and use that proof to withdraw the locked deposit on the Bitcoin mainnet, creating a two-way peg. With a good design for the verification program, the withdrawal would be simple and flexible, which would allow for fungible withdrawals.
The authors note that anyone who would benefit from this construction (e.g. who receives BTC on another chain) is basically making a bet that Bitcoin’s consensus rules will be changed (e.g.
OP_ZKP_VERIFYwill be added). This gives them an incentive to advocate for the change, but heavily incentivizing some users to change the system may result in other users feeling like they’re being coerced. The idea had not received any discussion on the mailing list as of this writing.
Waiting for confirmation #7: Network Resources
A limited weekly series about transaction relay, mempool inclusion, and mining transaction selection—including why Bitcoin Core has a more restrictive policy than allowed by consensus and how wallets can use that policy most effectively.
A previous post discussed protecting node resources, which may be unique to each node and thus sometimes configurable. We also made our case for why it is best to converge on one policy, but what should be part of that policy? This post will discuss the concept of network-wide resources, critical to things like scalability, upgradeability and accessibility of bootstrapping and maintaining a full node.
As discussed in previous posts, many of the Bitcoin network’s ideological goals are embodied in its distributed structure. Bitcoin’s peer-to-peer nature allows the rules of the network to emerge from rough consensus of the individual node operators’ choices and curbs attempts to acquire undue influence in the network. Those rules are then enforced by each node individually validating every transaction. A diverse and healthy node population requires that the cost of operating a node is kept low. It is hard to scale any project with a global audience, but doing so without sacrificing decentralization is akin to fighting with one hand tied to your back. The Bitcoin project attempts this balancing act by being fiercely protective of its shared network resources: the UTXO set, the data footprint of the blockchain and the computational effort required to process it, and upgrade hooks to evolve the Bitcoin protocol.
There is no need to reiterate the entire blocksize war to realize that a limit
on blockchain growth is necessary to keep it affordable to run your own node.
However, blockchain growth is also dissuaded at the policy level by the
minRelayTxFee of 1 sat/vbyte, ensuring a minimum cost to express some of the
“unbounded demand for highly-replicated perpetual storage”.
Originally, the network state was tracked by keeping all transactions that still had unspent outputs. This much bigger portion of the blockchain got reduced significantly with the introduction of the UTXO set as the means of keeping track of funds. Since then, the UTXO set has been a central data structure. Especially during IBD, but also generally, UTXO lookups represent a major portion of all memory accesses of a node. Bitcoin Core already uses a manually optimized data structure for the UTXO cache, but the size of the UTXO set determines how much of it cannot fit in a node’s cache. A larger UTXO set means more cache misses which slows down block validation, IBD, and transaction validation speed. The dust limit is an example of a policy that restricts the creation of UTXOs, specifically curbing UTXOs that might never get spent because their amount falls short of the cost for spending them. Even so, “dust storms” with thousands of transactions occurred as recently as 2020.
When it became popular to use bare multisig outputs to publish data onto the
blockchain, the definition of standard transactions was amended to permit a
single OP_RETURN output as an alternative. People realized that it would be
impossible to prevent users from publishing data on the blockchain, but at
least such data would not need to live in the UTXO set forever when published
in outputs that could never be spent. Bitcoin Core 0.13.0 introduced a start-up
-permitbaremultisig that users may toggle to reject unconfirmed
transactions with bare multisig outputs.
While the consensus rules allow output scripts to be freeform, only a few well-understood patterns are relayed by Bitcoin Core nodes. This makes it easier to reason about many concerns in the network, including validation costs and protocol upgrade mechanisms. For example, an input script that contains op-codes, a P2SH input with more than 15 signatures, or a P2WSH input whose witness stack has more than 100 items each would make a transaction non-standard. (Check out this policy overview for more examples of policies and their motivations.)
Finally, the Bitcoin protocol is a living software project that will need to keep evolving to address future challenges and user needs. To that end, there are a number of upgrade hooks deliberately left consensus valid but unused, such as the annex, taproot leaf versions, witness versions, OP_SUCCESS, and a number of no-op opcodes. However, just like attacks are hindered by the lack of central points of failure, network-wide software upgrades involve a coordinated effort between tens of thousands of independent node operators. Nodes will not relay transactions that make use of any reserved upgrade hooks until their meaning has been defined. This discouragement is meant to dissuade applications from independently creating conflicting standards, which would make it impossible to adopt one application’s standard into consensus without invalidating another’s. Also, when a consensus change does happen, nodes that do not upgrade immediately—and thus do not know the new consensus rules—cannot be “tricked” into accepting a now-invalid transaction into their mempools. The proactive discouragement helps nodes be forward-compatible and enables the network to safely upgrade consensus rules without requiring a completely synchronized software update.
We can see that using policy to protect shared network resources aids in protecting the network’s characteristics, and keeps paths for future protocol development open. Meanwhile, we are seeing how the friction of growing the network against a strictly limited blockweight has been driving adoption of best practices, good technical design, and innovation: next week’s post will explore mempool policy as an interface for second-layer protocols and smart contract systems.
Selected Q&A from Bitcoin Stack Exchange
Bitcoin Stack Exchange is one of the first places Optech contributors look for answers to their questions—or when we have a few spare moments to help curious or confused users. In this monthly feature, we highlight some of the top-voted questions and answers posted since our last update.
● Why do Bitcoin nodes accept blocks that have so many excluded transactions? User commstark wonders why a node accepts a block from miners that exclude transactions that were anticipated for that block according to that node’s block template. There are various tools that show expected compared to actual blocks. Pieter Wuille points out that due to inherent variance in different nodes’ mempools related to transaction propagation, a consensus rule enforcing block contents is not possible.
● Why does everyone say that soft forks restrict the existing ruleset? Pieter Wuille uses the rules added during the taproot and segwit soft fork activations as examples of tightening the consensus rules:
● Why is the default LN channel limit set to 16777215 sats? Vojtěch Strnad explains the 2^24 satoshi limit history and motivation for large (wumbo) channels and also links to Optech’s large channel topic for more information.
● Why does Bitcoin Core use ancestor score instead of just ancestor fee rate to select transactions? Sdaftuar explains that performance optimization is the reason that the mining block template transaction selection algorithm uses both the ancestor feerate and ancestor score. (See Waiting for confirmation #2: Incentives).
● How does Lightning multipart payments (MPP) protocol define the amounts per part? Rene Pickhardt points out that multipath payments do not have a protocol-specified part size or algorithm for choosing part size and points out some relevant payment-splitting research.
Releases and release candidates
New releases and release candidates for popular Bitcoin infrastructure projects. Please consider upgrading to new releases or helping to test release candidates.
- ● BTCPay Server 1.10.3 is the latest release for this self-hosted payment processing software. See their blog post for a tour of the headline features in the 1.10 branch.
Notable code and documentation changes
Notable changes this week in Bitcoin Core, Core Lightning, Eclair, LDK, LND, libsecp256k1, Hardware Wallet Interface (HWI), Rust Bitcoin, BTCPay Server, BDK, Bitcoin Improvement Proposals (BIPs), Lightning BOLTs, and Bitcoin Inquisition.
● Eclair #2701 begins recording both when an offered HTLC is received and when it is settled. This allows tracking how long the HTLC was pending from the node’s perspective. If many HTLCs, or a few high-value HTLCs, are pending for long periods of time, this may indicate a channel jamming attack is in progress. Tracking HTLC duration helps detect such attacks and may contribute to mitigating them.
● Eclair #2696 changes how Eclair allows users to configure what feerates to use. Previously, users could specify what feerate to use with a block target, e.g. a setting of “6” meant Eclair would try to get a transaction confirmed within six blocks. Now Eclair accepts “slow”, “medium”, and “fast”, which it translates into specific feerates using constants or block targets.
● LND #7710 adds the ability for plugins (or the daemon itself) to retrieve data received earlier in an HTLC. This is necessary for route blinding and may be used by various channel jamming countermeasures, among other ideas for future features.
● LDK #2368 allows accepting new channels created by a peer that use anchor outputs but requires the controlling program deliberately choose to accept each new channel. This is done because properly settling an anchor channel may require the user to have access to one or more UTXOs with sufficient value. LDK, as a library that is unaware of what non-LN UTXOs the user’s wallet controls, uses this prompt to give the controlling program a chance to verify that it has the necessary UTXOs.
● LDK #2319 allows a peer to create an HTLC that commits to paying less than the amount the original spender said should be paid, allowing the peer to keep the difference for itself as an extra fee. This is useful for the creation of JIT channels where a peer receives an HTLC for a receiver that doesn’t have a channel yet. The peer creates an onchain transaction that funds the channel and commits to the HTLC within that channel—but it incurs additional transaction fees in creating that onchain transaction. By taking an extra fee, it is compensated for its costs if the receiver accepts the new channel and settles the HTLC on time.
● Libsecp256k1 #1129 implements the ElligatorSwift technique to introduce a 64-byte public key encoding that is computationally indistinguishable from random data. The
ellswiftmodule provides functions for encoding and decoding public keys in the new format as well as convenience functions to generate new uniformly-random keys and perform an Elliptic Curve Diffie-Hellman key exchange (ECDH) on ellswift-encoded keys. The ellswift-based ECDH is to be used in establishing connections for the version 2 P2P encrypted transport protocol (BIP324).