Skip to content

BIP321: note that example addresses are not for real payments - #2228

Closed
fametrano wants to merge 1 commit into
bitcoin:masterfrom
fametrano:intentionally-invalid
Closed

BIP321: note that example addresses are not for real payments#2228
fametrano wants to merge 1 commit into
bitcoin:masterfrom
fametrano:intentionally-invalid

Conversation

@fametrano

@fametrano fametrano commented Jul 31, 2026

Copy link
Copy Markdown
Contributor

BIP 321 started as a verbatim copy of BIP 21 (7e6a583) and has diverged since, but it never picked up the note about example addresses that was added to BIP 21 in #1861. This adds it.

One of three mutually exclusive options for the same problem — see the table at the bottom. My preference is #2229, not this PR.

Background

#119 (2015) proposed replacing the base58 example address 175tWpb8K1S7NmH4Zx6rewF9WQrcZv245W, whose checksum is intentionally invalid, with a valid one. It was closed for lack of author consensus, but the thread documents the cost of leaving the intent undocumented: users repeatedly filed URI-parsing bugs against wallets after copying URIs straight out of the document (@schildbach), and it tripped up someone using the examples as test vectors (@evoskuil), who asked for exactly this kind of warning. #1861 later resolved it for BIP 21 by documenting the intent instead of changing the address. This PR extends the same treatment to BIP 321.

One difference from BIP 21

BIP 321's examples also include bech32/bech32m addresses, added after the fork from BIP 21, and unlike the base58 one their checksums are valid:

Address Status
175tWpb8K1S7NmH4Zx6rewF9WQrcZv245W invalid checksum (intentional)
bc1qufgy354j3kmvuch987xe4s40836x3h0lg8f5n2 valid bech32, witness v0, mainnet
bc1p5swkugezn97763tl0yty6556856uug0q6jflljvep9m4p7339x5qzyrh4g valid bech32m, witness v1, mainnet
tb1qghfhmd4zh7ncpmxl3qzhmq566jk8ckq4gafnmg valid bech32, witness v0, testnet

So BIP 21's exact wording ("the addresses used in these examples are intentionally invalid") would be inaccurate here, and misleading in the direction that matters: it would tell readers that two spendable mainnet addresses are safe. The wording used here states the illustration-only intent for all the examples and attributes the invalid checksum specifically to the base58 address:

Note: The addresses used in these examples are for illustration only and must not be used to send funds; the base58 address has an intentionally invalid checksum to prevent accidental transactions.

The three options

PR Approach Diff
#2228 keep the addresses, word the note to match reality +2 this PR
#2229 invalidate every address, add BIP 21's note verbatim +7 / -5 my preference
#2230 make every address valid, warn against paying them +18 / -16

Only one should be merged; I'll close the other two.

My preference is #2229. It is the only one of the three that leaves no spendable address anywhere in the document, it makes BIP 21's existing wording literally true here so the two documents stay in sync, and the whole cost is four characters. This PR is the minimal-diff fallback if maintainers would rather not touch strings that downstream implementations may already be using as test vectors. #2230 is on the table because #119 was closed for lack of author consensus rather than on the merits, so the option deserves to be stated explicitly rather than assumed dead — but it is the one I would close first.

BIP 321 was copied from BIP 21 before the note added in bitcoin#1861, so the
warning was missing here.

The wording differs from BIP 21 on purpose: BIP 321's examples also
include bech32/bech32m addresses, and unlike the base58 one their
checksums are valid. BIP 21's blanket "intentionally invalid" claim
would therefore be inaccurate here, and would imply that a spendable
mainnet address is safe.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>

@jonatack jonatack left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Agree with you; I prefer #2229. Suggest closing here.

fametrano added a commit to fametrano/bips that referenced this pull request Jul 31, 2026
Revives bitcoin#119, closed in 2015 for lack of author consensus.

175tWpb8K1S7NmH4Zx6rewF9WQrcZv245W has a deliberately broken checksum
-- the address from the Wikipedia Bitcoin page of the time with its
final character replaced -- while every other address in the document,
the bech32 and bech32m examples added after the fork from BIP 21, has a
valid checksum. That inconsistency has a documented cost: users have
filed URI-parsing bugs against wallets after copying URIs straight out
of the document (schildbach in bitcoin#119), and the examples cannot be used
as test vectors as they stand (evoskuil in bitcoin#119, who opened it for
exactly this reason).

Use 1NS17iag9jJgTHD1VXjvLCEnZuQ3rJED9L, the replacement bitcoin#119 proposed.
It is BIP 20's example address, where it is already paired with the
same label=Luke-Jr used here, so the labels in the examples stay
coherent -- luke-jr's objection in bitcoin#119.

Every address in the document is now valid and parseable, so the
examples work as test vectors, and a note states that they are
illustrative and must not be paid. That addresses laanwj's objection in
bitcoin#119 -- that valid example addresses are spendable ones -- by warning
the reader rather than by breaking the encoding.

Alternatives: bitcoin#2228 and bitcoin#2229, which keep the addresses unspendable
instead.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
@jonatack jonatack added the Fixups Minor fixups not worth bothering the BIP author(s) for label Jul 31, 2026
@jonatack jonatack closed this Jul 31, 2026
jonatack pushed a commit that referenced this pull request Aug 3, 2026
The base58 example address has an intentionally invalid checksum, but
the bech32 and bech32m examples added later have valid checksums, so
they are spendable addresses that a reader may pay by accident -- the
very hazard that motivated the invalid base58 address in #119. Two of
them are mainnet:

  bc1qufgy354j3kmvuch987xe4s40836x3h0lg8f5n2  (bech32, witness v0)
  bc1p5swkugezn...vep9m4p7339x5qzyrh4g        (bech32m, witness v1)
  tb1qghfhmd4zh7ncpmxl3qzhmq566jk8ckq4gafnmg  (bech32, testnet)

Alter the final checksum character of each, and document the intent
with the note BIP 21 received in #1861. Bech32 detects any
single-character substitution, so the modified strings cannot be valid
addresses. The human-readable part, charset and length are unchanged,
so the examples remain structurally representative of P2WPKH and P2TR.

The uppercase QR-code variants are updated to match, and the changed
testnet address in the "Invalid URIs" section still demonstrates the
same point (a `tb` address in the `bc` parameter).

Alternative to #2228, which leaves the addresses untouched and instead
words the note to match them.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Fixups Minor fixups not worth bothering the BIP author(s) for

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants