Repository: bitcoin/bips Branch: master Commit: 2778442c21ce Files: 385 Total size: 14.9 MB Directory structure: gitextract_ant9xgmu/ ├── .gitattributes ├── .github/ │ └── workflows/ │ └── github-action-checks.yml ├── .gitignore ├── .typos.toml ├── CONTRIBUTING.md ├── README.mediawiki ├── bip-0001.mediawiki ├── bip-0002.mediawiki ├── bip-0003.md ├── bip-0008/ │ ├── assignments.mediawiki │ └── states.dot ├── bip-0008.mediawiki ├── bip-0009/ │ ├── assignments.mediawiki │ └── states.gv ├── bip-0009.mediawiki ├── bip-0010.mediawiki ├── bip-0011.mediawiki ├── bip-0012.mediawiki ├── bip-0013.mediawiki ├── bip-0014.mediawiki ├── bip-0015.mediawiki ├── bip-0016/ │ └── qa.mediawiki ├── bip-0016.mediawiki ├── bip-0017.mediawiki ├── bip-0018.mediawiki ├── bip-0019.mediawiki ├── bip-0020.mediawiki ├── bip-0021.mediawiki ├── bip-0022.mediawiki ├── bip-0023.mediawiki ├── bip-0030.mediawiki ├── bip-0031.mediawiki ├── bip-0032.mediawiki ├── bip-0033.mediawiki ├── bip-0034.mediawiki ├── bip-0035.mediawiki ├── bip-0036.mediawiki ├── bip-0037.mediawiki ├── bip-0038.mediawiki ├── bip-0039/ │ ├── bip-0039-wordlists.md │ ├── chinese_simplified.txt │ ├── chinese_traditional.txt │ ├── czech.txt │ ├── english.txt │ ├── french.txt │ ├── italian.txt │ ├── japanese.txt │ ├── korean.txt │ ├── portuguese.txt │ └── spanish.txt ├── bip-0039.mediawiki ├── bip-0042.mediawiki ├── bip-0043.mediawiki ├── bip-0044.mediawiki ├── bip-0045.mediawiki ├── bip-0046.mediawiki ├── bip-0047.mediawiki ├── bip-0048.mediawiki ├── bip-0049.mediawiki ├── bip-0050.mediawiki ├── bip-0052.mediawiki ├── bip-0053/ │ ├── 64byte-tx-mainnet.txt │ └── non-standard-hashlock-utxos.txt ├── bip-0053.mediawiki ├── bip-0054/ │ └── test_vectors/ │ ├── README.md │ ├── coinbases.json │ ├── sigops.json │ ├── timestamps.json │ └── txsize.json ├── bip-0054.md ├── bip-0060.mediawiki ├── bip-0061.mediawiki ├── bip-0062.mediawiki ├── bip-0064.mediawiki ├── bip-0065.mediawiki ├── bip-0066.mediawiki ├── bip-0067.mediawiki ├── bip-0068.mediawiki ├── bip-0069/ │ └── bip-0069_examples.py ├── bip-0069.mediawiki ├── bip-0070/ │ ├── extensions.mediawiki │ └── paymentrequest.proto ├── bip-0070.mediawiki ├── bip-0071.mediawiki ├── bip-0072.mediawiki ├── bip-0073.mediawiki ├── bip-0074.mediawiki ├── bip-0075/ │ └── paymentrequest.proto ├── bip-0075.mediawiki ├── bip-0077.md ├── bip-0078.mediawiki ├── bip-0079.mediawiki ├── bip-0080.mediawiki ├── bip-0081.mediawiki ├── bip-0083.mediawiki ├── bip-0084.mediawiki ├── bip-0085.mediawiki ├── bip-0086.mediawiki ├── bip-0087.mediawiki ├── bip-0088.mediawiki ├── bip-0089/ │ ├── bip32.py │ ├── descriptor.py │ ├── reference.py │ ├── secp256k1lab/ │ │ ├── COPYING │ │ ├── __init__.py │ │ ├── bip340.py │ │ ├── ecdh.py │ │ ├── keys.py │ │ ├── py.typed │ │ ├── secp256k1.py │ │ └── util.py │ └── vectors/ │ ├── blind_challenge_gen_vectors.json │ ├── blind_nonce_gen_vectors.json │ ├── blind_sign_and_verify_vectors.json │ ├── change_output_verification_vectors.json │ ├── compute_bip32_tweak_vectors.json │ ├── delegator_sign_vectors.json │ ├── input_verification_vectors.json │ └── unblind_signature_vectors.json ├── bip-0089.mediawiki ├── bip-0090.mediawiki ├── bip-0091.mediawiki ├── bip-0093.mediawiki ├── bip-0094.mediawiki ├── bip-0098/ │ ├── build.sh │ ├── node-variants.dot │ ├── skip-skip.dot │ ├── traversal-example.dot │ └── unbalanced-hash-tree.dot ├── bip-0098.mediawiki ├── bip-0099.mediawiki ├── bip-0100.mediawiki ├── bip-0101.mediawiki ├── bip-0102.mediawiki ├── bip-0103.mediawiki ├── bip-0104.mediawiki ├── bip-0105.mediawiki ├── bip-0106.mediawiki ├── bip-0107.mediawiki ├── bip-0109.mediawiki ├── bip-0110.mediawiki ├── bip-0111.mediawiki ├── bip-0112.mediawiki ├── bip-0113.mediawiki ├── bip-0114.mediawiki ├── bip-0115.mediawiki ├── bip-0116.mediawiki ├── bip-0117.mediawiki ├── bip-0118.mediawiki ├── bip-0119/ │ ├── simulation.py │ └── vectors/ │ ├── ctvhash.json │ ├── tx_invalid.json │ └── tx_valid.json ├── bip-0119.mediawiki ├── bip-0120.mediawiki ├── bip-0121.mediawiki ├── bip-0122.mediawiki ├── bip-0123.mediawiki ├── bip-0124.mediawiki ├── bip-0125.mediawiki ├── bip-0126.mediawiki ├── bip-0127.mediawiki ├── bip-0128.mediawiki ├── bip-0129.mediawiki ├── bip-0130.mediawiki ├── bip-0131.mediawiki ├── bip-0132.mediawiki ├── bip-0133.mediawiki ├── bip-0134.mediawiki ├── bip-0135.mediawiki ├── bip-0136.mediawiki ├── bip-0137.mediawiki ├── bip-0140.mediawiki ├── bip-0141.mediawiki ├── bip-0142.mediawiki ├── bip-0143.mediawiki ├── bip-0144.mediawiki ├── bip-0145.mediawiki ├── bip-0146.mediawiki ├── bip-0147.mediawiki ├── bip-0148.mediawiki ├── bip-0149.mediawiki ├── bip-0150.mediawiki ├── bip-0151.mediawiki ├── bip-0152.mediawiki ├── bip-0154.mediawiki ├── bip-0155.mediawiki ├── bip-0156/ │ └── bitcoin.conf ├── bip-0156.mediawiki ├── bip-0157.mediawiki ├── bip-0158/ │ ├── gentestvectors.go │ ├── go.mod │ ├── go.sum │ └── testnet-19.json ├── bip-0158.mediawiki ├── bip-0159.mediawiki ├── bip-0171.mediawiki ├── bip-0172.mediawiki ├── bip-0173.mediawiki ├── bip-0174/ │ ├── build.sh │ ├── coinjoin-workflow.tex │ └── multisig-workflow.tex ├── bip-0174.mediawiki ├── bip-0175.mediawiki ├── bip-0176.mediawiki ├── bip-0177.mediawiki ├── bip-0178.mediawiki ├── bip-0179.mediawiki ├── bip-0180.mediawiki ├── bip-0197.mediawiki ├── bip-0199.mediawiki ├── bip-0300/ │ └── images.txt ├── bip-0300.mediawiki ├── bip-0301.mediawiki ├── bip-0310.mediawiki ├── bip-0320.mediawiki ├── bip-0321.mediawiki ├── bip-0322.mediawiki ├── bip-0324/ │ ├── ellswift_decode_test_vectors.csv │ ├── gen_test_vectors.py │ ├── message_type_ids.md │ ├── packet_encoding_test_vectors.csv │ ├── reference.py │ ├── run_test_vectors.py │ ├── secp256k1_test_vectors.py │ ├── test_sage_decoding.py │ └── xswiftec_inv_test_vectors.csv ├── bip-0324.mediawiki ├── bip-0325.mediawiki ├── bip-0326.mediawiki ├── bip-0327/ │ ├── gen_vectors_helper.py │ ├── reference.py │ ├── tests.sh │ └── vectors/ │ ├── det_sign_vectors.json │ ├── key_agg_vectors.json │ ├── key_sort_vectors.json │ ├── nonce_agg_vectors.json │ ├── nonce_gen_vectors.json │ ├── sig_agg_vectors.json │ ├── sign_verify_vectors.json │ └── tweak_vectors.json ├── bip-0327.mediawiki ├── bip-0328/ │ ├── _base58.py │ ├── _common.py │ ├── _xpub.py │ ├── reference.py │ └── vectors.json ├── bip-0328.mediawiki ├── bip-0329.mediawiki ├── bip-0330/ │ └── minisketch.py ├── bip-0330.mediawiki ├── bip-0331.mediawiki ├── bip-0337.mediawiki ├── bip-0338.mediawiki ├── bip-0339.mediawiki ├── bip-0340/ │ ├── LICENSE │ ├── reference.py │ ├── test-vectors.csv │ └── test-vectors.py ├── bip-0340.mediawiki ├── bip-0341/ │ └── wallet-test-vectors.json ├── bip-0341.mediawiki ├── bip-0342.mediawiki ├── bip-0343.mediawiki ├── bip-0345/ │ └── vaults.drawio ├── bip-0345.mediawiki ├── bip-0346/ │ └── ref-impl/ │ ├── Cargo.toml │ ├── src/ │ │ └── main.rs │ └── txhash_vectors.json ├── bip-0346.md ├── bip-0347.mediawiki ├── bip-0348.md ├── bip-0349.md ├── bip-0350.mediawiki ├── bip-0351.mediawiki ├── bip-0352/ │ ├── bech32m.py │ ├── bitcoin_utils.py │ ├── reference.py │ ├── ripemd160.py │ ├── secp256k1lab/ │ │ ├── .github/ │ │ │ └── workflows/ │ │ │ └── main.yml │ │ ├── .python-version │ │ ├── CHANGELOG.md │ │ ├── COPYING │ │ ├── README.md │ │ ├── pyproject.toml │ │ └── src/ │ │ └── secp256k1lab/ │ │ ├── __init__.py │ │ ├── bip340.py │ │ ├── ecdh.py │ │ ├── keys.py │ │ ├── py.typed │ │ ├── secp256k1.py │ │ └── util.py │ └── send_and_receive_test_vectors.json ├── bip-0352.mediawiki ├── bip-0353.mediawiki ├── bip-0360/ │ └── ref-impl/ │ ├── .gitignore │ ├── common/ │ │ ├── tests/ │ │ │ └── data/ │ │ │ ├── p2mr_construction.json │ │ │ └── p2mr_pqc_construction.json │ │ └── utils/ │ │ ├── signet_miner_loop.sh │ │ └── workshop/ │ │ ├── Dockerfile.bcli │ │ ├── Dockerfile.full │ │ └── bip360-workshop.drawio │ ├── js/ │ │ ├── .gitignore │ │ ├── README.adoc │ │ ├── package.json │ │ ├── src/ │ │ │ ├── p2mr-example.ts │ │ │ └── test-npm-pqc-package.js │ │ └── tsconfig.json │ ├── python/ │ │ └── .gitignore │ └── rust/ │ ├── .cargo/ │ │ └── config.toml │ ├── Cargo.toml │ ├── README.md │ ├── docs/ │ │ ├── development_notes.adoc │ │ ├── p2mr-end-to-end.adoc │ │ ├── p2mr-signet-workshop.adoc │ │ ├── p2tr-end-to-end.adoc │ │ ├── quantum_root_tap_tree.txt │ │ └── stack_element_size_performance_tests.adoc │ ├── examples/ │ │ ├── p2mr-end-to-end.sh │ │ ├── p2mr_construction.rs │ │ ├── p2mr_spend.rs │ │ ├── p2tr_construction.rs │ │ ├── p2tr_spend.rs │ │ ├── schnorr_example.rs │ │ └── slh_dsa_verification_example.rs │ ├── src/ │ │ ├── bin/ │ │ │ └── slh_dsa_key_gen.rs │ │ ├── data_structures.rs │ │ ├── error.rs │ │ └── lib.rs │ └── tests/ │ ├── p2mr_construction.rs │ ├── p2mr_pqc_construction.rs │ └── p2mr_spend.rs ├── bip-0360.mediawiki ├── bip-0370.mediawiki ├── bip-0371.mediawiki ├── bip-0372.mediawiki ├── bip-0373.mediawiki ├── bip-0374/ │ ├── gen_test_vectors.py │ ├── reference.py │ ├── run_test_vectors.py │ ├── secp256k1lab/ │ │ ├── .github/ │ │ │ └── workflows/ │ │ │ └── main.yml │ │ ├── .python-version │ │ ├── CHANGELOG.md │ │ ├── COPYING │ │ ├── README.md │ │ ├── pyproject.toml │ │ └── src/ │ │ └── secp256k1lab/ │ │ ├── __init__.py │ │ ├── bip340.py │ │ ├── ecdh.py │ │ ├── keys.py │ │ ├── py.typed │ │ ├── secp256k1.py │ │ └── util.py │ ├── test_vectors_generate_proof.csv │ └── test_vectors_verify_proof.csv ├── bip-0374.mediawiki ├── bip-0375.mediawiki ├── bip-0379.md ├── bip-0380.mediawiki ├── bip-0381.mediawiki ├── bip-0382.mediawiki ├── bip-0383.mediawiki ├── bip-0384.mediawiki ├── bip-0385.mediawiki ├── bip-0386.mediawiki ├── bip-0387.mediawiki ├── bip-0388/ │ └── wallet_policies.py ├── bip-0388.mediawiki ├── bip-0389.mediawiki ├── bip-0390.mediawiki ├── bip-0392.mediawiki ├── bip-0431.mediawiki ├── bip-0433.mediawiki ├── bip-0434.md ├── bip-0442.md ├── bip-0443.mediawiki ├── bip-0446/ │ ├── README.md │ ├── basics.json │ └── script_assets_test.json ├── bip-0446.md ├── bip-0448.md └── scripts/ ├── buildtable.pl ├── diffcheck.expected ├── diffcheck.sh └── link-format-chk.sh ================================================ FILE CONTENTS ================================================ ================================================ FILE: .gitattributes ================================================ *.mediawiki linguist-detectable ================================================ FILE: .github/workflows/github-action-checks.yml ================================================ name: GitHub Actions Check run-name: ${{ github.actor }} Checks 🚀 on: [push, pull_request] jobs: Link-Format-Checks: runs-on: ubuntu-latest steps: - uses: actions/checkout@v5 - run: scripts/link-format-chk.sh Build-Table-Checks: runs-on: ubuntu-latest steps: - uses: actions/checkout@v5 - run: scripts/buildtable.pl >/tmp/table.mediawiki || exit 1 Diff-Checks: name: "Diff Checks (fails until number assignment)" runs-on: ubuntu-latest steps: - uses: actions/checkout@v5 with: fetch-depth: 2 - run: scripts/diffcheck.sh Typo-Checks: name: "Typo Checks" runs-on: ubuntu-latest steps: - name: Checkout Actions Repository uses: actions/checkout@v5 - name: Check spelling uses: crate-ci/typos@master ================================================ FILE: .gitignore ================================================ bip-0174/coinjoin-workflow.aux bip-0174/coinjoin-workflow.log bip-0174/coinjoin-workflow.pdf bip-0174/multisig-workflow.aux bip-0174/multisig-workflow.log bip-0174/multisig-workflow.pdf ================================================ FILE: .typos.toml ================================================ [default] extend-ignore-re = [ # NOTE: use here for regex patterns "xpub.*", "xprv.*", "3.*", # address "5.*", # address "private_key .*", "privkey .*", "tt.*", # tags "code.*", # tags "\\w*", # prefix for tags "OP_SUCCESSx|\\d+", "pay.*", "ser.*", "prefix.*", "value: .*", "pqNTRUsign", "Strnad", ] [default.extend-words] # NOTE: use here for false-positives anc = "anc" PSBT = "PSBT" ser = "ser" # Names Atack = "Atack" Falke = "Falke" Meni = "Meni" Ono = "Ono" [files] extend-exclude = [ "/*/*.csv", "/*.d*", "/*/*.d*", "/*/*.go", "/*/*.json", "/*/*/*.json", "/*/*.mod", "/*/*.proto", "/*/*.py", "scripts", "/*/*.s*", "/*/*.t*", ] ================================================ FILE: CONTRIBUTING.md ================================================ # Contributing Guidelines Apart from following [BIP 2](./bip-0002.mediawiki), we do CI checks to ensure that the proposed BIPs do not have common typos. These checks are done using [`typos`](https://github.com/crate-ci/typos). To check for typos locally, install [`typos`](https://github.com/crate-ci/typos) and then run in the root directory: ```bash typos ``` ================================================ FILE: README.mediawiki ================================================ People wishing to submit a BIP should first describe their idea to the [https://groups.google.com/g/bitcoindev bitcoindev@googlegroups.com] mailing list to gather feedback on viability and community interest before working on a formal description. Please open a pull request to this repository only when substantial progress on the draft has been made, preferably when the draft is nearing completion. Authors do not assign a number to their own proposal. After a proposal meets the editorial criteria, a BIP Editor will assign a number to it and publish the proposal by merging the pull request to the repository. Please see [[bip-0003.md|BIP 3: Updated BIP Process]] for the full process. The BIPs repository serves as a publication medium and archive. Having a BIP published here indicates that the proposal is in scope and has met other formal criteria for this repository, but does not indicate that it is a good idea, has community consensus, or that it is about to be adopted. The BIP Editors are expected to be liberal with publishing BIPs and to try not to be too involved in decision-making on behalf of the community. Beyond the formal criteria, evaluation of the proposals is left to the audience of the repository. When a proposal is controversial and it cannot be agreed upon whether it should be published, the conservative option will always be preferred: the proposal will be closed. Those proposing and opposing changes should consider that ultimately acceptance and adoption rests with the Bitcoin users (see also: [https://en.bitcoin.it/wiki/Economic_majority economic majority]). {| class="wikitable sortable" style="width: auto; text-align: center; font-size: smaller; table-layout: fixed;" !Number !Layer !Title !Owner !Type !Status |- style="background-color: #ffcfcf" | [[bip-0001.mediawiki|1]] | | BIP Purpose and Guidelines | Amir Taaki | Process | Closed |- style="background-color: #ffcfcf" | [[bip-0002.mediawiki|2]] | | BIP process, revised | Luke Dashjr | Process | Closed |- style="background-color: #cfffcf" | [[bip-0003.md|3]] | | Updated BIP Process | Murch | Process | Deployed |- | [[bip-0008.mediawiki|8]] | | Version bits with lock-in by height | Shaolin Fry, Luke Dashjr | Informational | Draft |- style="background-color: #cfffcf" | [[bip-0009.mediawiki|9]] | | Version bits with timeout and delay | Pieter Wuille, Peter Todd, Greg Maxwell, Rusty Russell | Informational | Deployed |- style="background-color: #ffcfcf" | [[bip-0010.mediawiki|10]] | Applications | Multi-Sig Transaction Distribution | Alan Reiner | Informational | Closed |- style="background-color: #cfffcf" | [[bip-0011.mediawiki|11]] | Applications | M-of-N Standard Transactions | Gavin Andresen | Specification | Deployed |- style="background-color: #ffcfcf" | [[bip-0012.mediawiki|12]] | Consensus (soft fork) | OP_EVAL | Gavin Andresen | Specification | Closed |- style="background-color: #cfffcf" | [[bip-0013.mediawiki|13]] | Applications | Address Format for pay-to-script-hash | Gavin Andresen | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0014.mediawiki|14]] | Peer Services | Protocol Version and User Agent | Amir Taaki, Patrick Strateman | Specification | Deployed |- style="background-color: #ffcfcf" | [[bip-0015.mediawiki|15]] | Applications | Aliases | Amir Taaki | Specification | Closed |- style="background-color: #cfffcf" | [[bip-0016.mediawiki|16]] | Consensus (soft fork) | Pay to Script Hash | Gavin Andresen | Specification | Deployed |- style="background-color: #ffcfcf" | [[bip-0017.mediawiki|17]] | Consensus (soft fork) | OP_CHECKHASHVERIFY (CHV) | Luke Dashjr | Specification | Closed |- style="background-color: #ffffcf" | [[bip-0018.mediawiki|18]] | Consensus (soft fork) | hashScriptCheck | Luke Dashjr | Specification | Complete |- style="background-color: #ffcfcf" | [[bip-0019.mediawiki|19]] | Applications | M-of-N Standard Transactions (Low SigOp) | Luke Dashjr | Specification | Closed |- style="background-color: #ffcfcf" | [[bip-0020.mediawiki|20]] | Applications | URI Scheme | Luke Dashjr | Specification | Closed |- style="background-color: #ffcfcf" | [[bip-0021.mediawiki|21]] | Applications | URI Scheme | Nils Schneider, Matt Corallo | Specification | Closed |- style="background-color: #cfffcf" | [[bip-0022.mediawiki|22]] | API/RPC | getblocktemplate - Fundamentals | Luke Dashjr | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0023.mediawiki|23]] | API/RPC | getblocktemplate - Pooled Mining | Luke Dashjr | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0030.mediawiki|30]] | Consensus (soft fork) | Duplicate transactions | Pieter Wuille | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0031.mediawiki|31]] | Peer Services | Pong message | Mike Hearn | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0032.mediawiki|32]] | Applications | Hierarchical Deterministic Wallets | Pieter Wuille | Informational | Deployed |- style="background-color: #ffcfcf" | [[bip-0033.mediawiki|33]] | Peer Services | Stratized Nodes | Amir Taaki | Specification | Closed |- style="background-color: #cfffcf" | [[bip-0034.mediawiki|34]] | Consensus (soft fork) | Block v2, Height in Coinbase | Gavin Andresen | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0035.mediawiki|35]] | Peer Services | mempool message | Jeff Garzik | Specification | Deployed |- style="background-color: #ffcfcf" | [[bip-0036.mediawiki|36]] | Peer Services | Custom Services | Stefan Thomas | Specification | Closed |- style="background-color: #cfffcf" | [[bip-0037.mediawiki|37]] | Peer Services | Connection Bloom filtering | Mike Hearn, Matt Corallo | Specification | Deployed |- | [[bip-0038.mediawiki|38]] | Applications | Passphrase-protected private key | Mike Caldwell, Aaron Voisine | Specification | Draft |- style="background-color: #cfffcf" | [[bip-0039.mediawiki|39]] | Applications | Mnemonic code for generating deterministic keys | Marek Palatinus, Pavol Rusnak, Aaron Voisine, Sean Bowe | Specification | Deployed |- | 40 | API/RPC | Stratum wire protocol | Marek Palatinus | Standard | BIP number allocated |- | 41 | API/RPC | Stratum mining protocol | Marek Palatinus | Standard | BIP number allocated |- style="background-color: #cfffcf" | [[bip-0042.mediawiki|42]] | Consensus (soft fork) | A finite monetary supply for Bitcoin | Pieter Wuille | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0043.mediawiki|43]] | Applications | Purpose Field for Deterministic Wallets | Marek Palatinus, Pavol Rusnak | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0044.mediawiki|44]] | Applications | Multi-Account Hierarchy for Deterministic Wallets | Marek Palatinus, Pavol Rusnak | Specification | Deployed |- style="background-color: #ffffcf" | [[bip-0045.mediawiki|45]] | Applications | Structure for Deterministic P2SH Multisignature Wallets | Manuel Araoz, Ryan X. Charles, Matias Alejo Garcia | Specification | Complete |- | [[bip-0046.mediawiki|46]] | Applications | Address Scheme for Timelocked Fidelity Bonds | Chris Belcher, Thebora Kompanioni | Specification | Draft |- style="background-color: #cfffcf" | [[bip-0047.mediawiki|47]] | Applications | Reusable Payment Codes for Hierarchical Deterministic Wallets | Justus Ranvier | Informational | Deployed |- style="background-color: #cfffcf" | [[bip-0048.mediawiki|48]] | Applications | Multi-Script Hierarchy for Multi-Sig Wallets | Fontaine | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0049.mediawiki|49]] | Applications | Derivation scheme for P2WPKH-nested-in-P2SH based accounts | Daniel Weigl | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0050.mediawiki|50]] | | March 2013 Chain Fork Post-Mortem | Gavin Andresen | Informational | Deployed |- | [[bip-0052.mediawiki|52]] | Consensus (hard fork) | Durable, Low Energy Bitcoin PoW | Michael Dubrovsky, Bogdan Penkovsky | Specification | Draft |- | [[bip-0053.mediawiki|53]] | Consensus (soft fork) | Disallow 64-byte transactions | Chris Stewart | Specification | Draft |- | [[bip-0054.md|54]] | Consensus (soft fork) | Consensus Cleanup | Antoine Poinsot, Matt Corallo | Specification | Draft |- style="background-color: #ffcfcf" | [[bip-0060.mediawiki|60]] | Peer Services | Fixed Length "version" Message (Relay-Transactions Field) | Amir Taaki | Specification | Closed |- style="background-color: #cfffcf" | [[bip-0061.mediawiki|61]] | Peer Services | Reject P2P message | Gavin Andresen | Specification | Deployed |- style="background-color: #ffcfcf" | [[bip-0062.mediawiki|62]] | Consensus (soft fork) | Dealing with malleability | Pieter Wuille | Specification | Closed |- | 63 | Applications | Stealth Addresses | Peter Todd | Standard | BIP number allocated |- style="background-color: #ffcfcf" | [[bip-0064.mediawiki|64]] | Peer Services | getutxo message | Mike Hearn | Specification | Closed |- style="background-color: #cfffcf" | [[bip-0065.mediawiki|65]] | Consensus (soft fork) | OP_CHECKLOCKTIMEVERIFY | Peter Todd | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0066.mediawiki|66]] | Consensus (soft fork) | Strict DER signatures | Pieter Wuille | Specification | Deployed |- style="background-color: #ffffcf" | [[bip-0067.mediawiki|67]] | Applications | Deterministic Pay-to-script-hash multi-signature addresses through public key sorting | Thomas Kerin, Jean-Pierre Rupp, Ruben de Vries | Specification | Complete |- style="background-color: #cfffcf" | [[bip-0068.mediawiki|68]] | Consensus (soft fork) | Relative lock-time using consensus-enforced sequence numbers | Mark Friedenbach, BtcDrak, Nicolas Dorier, kinoshitajona | Specification | Deployed |- style="background-color: #ffffcf" | [[bip-0069.mediawiki|69]] | Applications | Lexicographical Indexing of Transaction Inputs and Outputs | Kristov Atlas | Informational | Complete |- style="background-color: #cfffcf" | [[bip-0070.mediawiki|70]] | Applications | Payment Protocol | Gavin Andresen, Mike Hearn | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0071.mediawiki|71]] | Applications | Payment Protocol MIME types | Gavin Andresen | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0072.mediawiki|72]] | Applications | bitcoin: uri extensions for Payment Protocol | Gavin Andresen | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0073.mediawiki|73]] | Applications | Use "Accept" header for response type negotiation with Payment Request URLs | Stephen Pair | Specification | Deployed |- style="background-color: #ffcfcf" | [[bip-0074.mediawiki|74]] | Applications | Allow zero value OP_RETURN in Payment Protocol | Toby Padilla | Specification | Closed |- style="background-color: #cfffcf" | [[bip-0075.mediawiki|75]] | Applications | Out of Band Address Exchange using Payment Protocol Encryption | Justin Newton, Matt David, Aaron Voisine, James MacWhyte | Specification | Deployed |- | [[bip-0077.md|77]] | Applications | Async Payjoin | Dan Gould, Yuval Kogman | Specification | Draft |- | [[bip-0078.mediawiki|78]] | Applications | A Simple Payjoin Proposal | Nicolas Dorier | Specification | Draft |- style="background-color: #ffcfcf" | [[bip-0079.mediawiki|79]] | Applications | Bustapay :: a practical coinjoin protocol | Ryan Havar | Informational | Closed |- style="background-color: #ffcfcf" | [[bip-0080.mediawiki|80]] | | Hierarchy for Non-Colored Voting Pool Deterministic Multisig Wallets | Justus Ranvier, Jimmy Song | Informational | Closed |- style="background-color: #ffcfcf" | [[bip-0081.mediawiki|81]] | | Hierarchy for Colored Voting Pool Deterministic Multisig Wallets | Justus Ranvier, Jimmy Song | Informational | Closed |- style="background-color: #ffcfcf" | [[bip-0083.mediawiki|83]] | Applications | Dynamic Hierarchical Deterministic Key Trees | Eric Lombrozo | Specification | Closed |- style="background-color: #cfffcf" | [[bip-0084.mediawiki|84]] | Applications | Derivation scheme for P2WPKH based accounts | Pavol Rusnak | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0085.mediawiki|85]] | Applications | Deterministic Entropy From BIP32 Keychains | Ethan Kosakovsky, Aneesh Karve | Informational | Deployed |- style="background-color: #cfffcf" | [[bip-0086.mediawiki|86]] | Applications | Key Derivation for Single Key P2TR Outputs | Ava Chow | Specification | Deployed |- style="background-color: #ffffcf" | [[bip-0087.mediawiki|87]] | Applications | Hierarchy for Deterministic Multisig Wallets | Robert Spigler | Specification | Complete |- style="background-color: #ffffcf" | [[bip-0088.mediawiki|88]] | Applications | Hierarchical Deterministic Path Templates | Dmitry Petukhov | Informational | Complete |- | [[bip-0089.mediawiki|89]] | Applications | Chain Code Delegation | Jesse Posner, Jurvis Tan | Specification | Draft |- style="background-color: #cfffcf" | [[bip-0090.mediawiki|90]] | | Buried Deployments | Suhas Daftuar | Informational | Deployed |- style="background-color: #cfffcf" | [[bip-0091.mediawiki|91]] | Consensus (soft fork) | Reduced threshold Segwit MASF | James Hilliard | Specification | Deployed |- | [[bip-0093.mediawiki|93]] | Applications | codex32: Checksummed SSSS-aware BIP32 seeds | Leon Olsson Curr, Pearlwort Sneed, Andrew Poelstra | Informational | Draft |- style="background-color: #cfffcf" | [[bip-0094.mediawiki|94]] | Applications | Testnet 4 | Fabian Jahr | Specification | Deployed |- | [[bip-0098.mediawiki|98]] | Consensus (soft fork) | Fast Merkle Trees | Mark Friedenbach, Kalle Alm, BtcDrak | Specification | Draft |- style="background-color: #ffcfcf" | [[bip-0099.mediawiki|99]] | | Motivation and deployment of consensus rule changes ([soft/hard]forks) | Jorge Timón | Informational | Closed |- style="background-color: #ffcfcf" | [[bip-0100.mediawiki|100]] | Consensus (hard fork) | Dynamic maximum block size by miner vote | Jeff Garzik, Tom Harding, Dagur Valberg Johannsson | Specification | Closed |- style="background-color: #ffcfcf" | [[bip-0101.mediawiki|101]] | Consensus (hard fork) | Increase maximum block size | Gavin Andresen | Specification | Closed |- style="background-color: #ffcfcf" | [[bip-0102.mediawiki|102]] | Consensus (hard fork) | Block size increase to 2MB | Jeff Garzik | Specification | Closed |- style="background-color: #ffcfcf" | [[bip-0103.mediawiki|103]] | Consensus (hard fork) | Block size following technological growth | Pieter Wuille | Specification | Closed |- style="background-color: #ffcfcf" | [[bip-0104.mediawiki|104]] | Consensus (hard fork) | 'Block75' - Max block size like difficulty | t.khan | Specification | Closed |- style="background-color: #ffcfcf" | [[bip-0105.mediawiki|105]] | Consensus (hard fork) | Consensus based block size retargeting algorithm | BtcDrak | Specification | Closed |- style="background-color: #ffcfcf" | [[bip-0106.mediawiki|106]] | Consensus (hard fork) | Dynamically Controlled Bitcoin Block Size Max Cap | Upal Chakraborty | Specification | Closed |- style="background-color: #ffcfcf" | [[bip-0107.mediawiki|107]] | Consensus (hard fork) | Dynamic limit on the block size | Washington Y. Sanchez | Specification | Closed |- style="background-color: #ffcfcf" | [[bip-0109.mediawiki|109]] | Consensus (hard fork) | Two million byte size limit with sigop and sighash limits | Gavin Andresen | Specification | Closed |- | [[bip-0110.mediawiki|110]] | Consensus (soft fork) | Reduced Data Temporary Softfork | Dathon Ohm | Specification | Draft |- style="background-color: #cfffcf" | [[bip-0111.mediawiki|111]] | Peer Services | NODE_BLOOM service bit | Matt Corallo, Peter Todd | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0112.mediawiki|112]] | Consensus (soft fork) | CHECKSEQUENCEVERIFY | BtcDrak, Mark Friedenbach, Eric Lombrozo | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0113.mediawiki|113]] | Consensus (soft fork) | Median time-past as endpoint for lock-time calculations | Thomas Kerin, Mark Friedenbach | Specification | Deployed |- style="background-color: #ffcfcf" | [[bip-0114.mediawiki|114]] | Consensus (soft fork) | Merkelized Abstract Syntax Tree | Johnson Lau | Specification | Closed |- style="background-color: #ffcfcf" | [[bip-0115.mediawiki|115]] | Consensus (soft fork) | Generic anti-replay protection using Script | Luke Dashjr | Specification | Closed |- | [[bip-0116.mediawiki|116]] | Consensus (soft fork) | MERKLEBRANCHVERIFY | Mark Friedenbach, Kalle Alm, BtcDrak | Specification | Draft |- | [[bip-0117.mediawiki|117]] | Consensus (soft fork) | Tail Call Execution Semantics | Mark Friedenbach, Kalle Alm, BtcDrak | Specification | Draft |- | [[bip-0118.mediawiki|118]] | Consensus (soft fork) | SIGHASH_ANYPREVOUT for Taproot Scripts | Christian Decker, Anthony Towns | Specification | Draft |- | [[bip-0119.mediawiki|119]] | Consensus (soft fork) | CHECKTEMPLATEVERIFY | Jeremy Rubin | Specification | Draft |- style="background-color: #ffcfcf" | [[bip-0120.mediawiki|120]] | Applications | Proof of Payment | Kalle Rosenbaum | Specification | Closed |- style="background-color: #ffcfcf" | [[bip-0121.mediawiki|121]] | Applications | Proof of Payment URI scheme | Kalle Rosenbaum | Specification | Closed |- | [[bip-0122.mediawiki|122]] | Applications | URI scheme for Blockchain references / exploration | Marco Pontello | Specification | Draft |- style="background-color: #cfffcf" | [[bip-0123.mediawiki|123]] | | BIP Classification | Eric Lombrozo | Process | Deployed |- style="background-color: #ffcfcf" | [[bip-0124.mediawiki|124]] | Applications | Hierarchical Deterministic Script Templates | Eric Lombrozo, William Swanson | Informational | Closed |- style="background-color: #cfffcf" | [[bip-0125.mediawiki|125]] | Applications | Opt-in Full Replace-by-Fee Signaling | David A. Harding, Peter Todd | Specification | Deployed |- | [[bip-0126.mediawiki|126]] | | Best Practices for Heterogeneous Input Script Transactions | Kristov Atlas | Informational | Draft |- | [[bip-0127.mediawiki|127]] | Applications | Simple Proof-of-Reserves Transactions | Steven Roose | Specification | Draft |- | [[bip-0128.mediawiki|128]] | Applications | Timelock-Recovery Storage Format | Oren Z | Specification | Draft |- style="background-color: #ffffcf" | [[bip-0129.mediawiki|129]] | Applications | Bitcoin Secure Multisig Setup (BSMS) | Hugo Nguyen, Peter Gray, Marko Bencun, Aaron Chen, Rodolfo Novak | Specification | Complete |- style="background-color: #cfffcf" | [[bip-0130.mediawiki|130]] | Peer Services | sendheaders message | Suhas Daftuar | Specification | Deployed |- style="background-color: #ffcfcf" | [[bip-0131.mediawiki|131]] | Consensus (hard fork) | "Coalescing Transaction" Specification (wildcard inputs) | Chris Priest | Specification | Closed |- style="background-color: #ffcfcf" | [[bip-0132.mediawiki|132]] | | Committee-based BIP Acceptance Process | Andy Chase | Process | Closed |- style="background-color: #cfffcf" | [[bip-0133.mediawiki|133]] | Peer Services | feefilter message | Alex Morcos | Specification | Deployed |- style="background-color: #ffcfcf" | [[bip-0134.mediawiki|134]] | Consensus (hard fork) | Flexible Transactions | Tom Zander | Specification | Closed |- style="background-color: #ffcfcf" | [[bip-0135.mediawiki|135]] | | Generalized version bits voting | Sancho Panza | Informational | Closed |- | [[bip-0136.mediawiki|136]] | Applications | Bech32 Encoded Tx Position References | Велеслав, Jonas Schnelli, Daniel Pape | Informational | Draft |- style="background-color: #cfffcf" | [[bip-0137.mediawiki|137]] | Applications | Signatures of Messages using Private Keys | Christopher Gilliard | Specification | Deployed |- style="background-color: #ffcfcf" | [[bip-0140.mediawiki|140]] | Consensus (soft fork) | Normalized TXID | Christian Decker | Specification | Closed |- style="background-color: #cfffcf" | [[bip-0141.mediawiki|141]] | Consensus (soft fork) | Segregated Witness (Consensus layer) | Eric Lombrozo, Johnson Lau, Pieter Wuille | Specification | Deployed |- style="background-color: #ffcfcf" | [[bip-0142.mediawiki|142]] | Applications | Address Format for Segregated Witness | Johnson Lau | Specification | Closed |- style="background-color: #cfffcf" | [[bip-0143.mediawiki|143]] | Consensus (soft fork) | Transaction Signature Verification for Version 0 Witness Program | Johnson Lau, Pieter Wuille | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0144.mediawiki|144]] | Peer Services | Segregated Witness (Peer Services) | Eric Lombrozo, Pieter Wuille | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0145.mediawiki|145]] | API/RPC | getblocktemplate Updates for Segregated Witness | Luke Dashjr | Specification | Deployed |- style="background-color: #ffcfcf" | [[bip-0146.mediawiki|146]] | Consensus (soft fork) | Dealing with signature encoding malleability | Johnson Lau, Pieter Wuille | Specification | Closed |- style="background-color: #cfffcf" | [[bip-0147.mediawiki|147]] | Consensus (soft fork) | Dealing with dummy stack element malleability | Johnson Lau | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0148.mediawiki|148]] | Consensus (soft fork) | Mandatory activation of segwit deployment | Shaolin Fry | Specification | Deployed |- style="background-color: #ffcfcf" | [[bip-0149.mediawiki|149]] | Consensus (soft fork) | Segregated Witness (second deployment) | Shaolin Fry | Specification | Closed |- style="background-color: #ffcfcf" | [[bip-0150.mediawiki|150]] | Peer Services | Peer Authentication | Jonas Schnelli | Specification | Closed |- style="background-color: #ffcfcf" | [[bip-0151.mediawiki|151]] | Peer Services | Peer-to-Peer Communication Encryption | Jonas Schnelli | Specification | Closed |- style="background-color: #cfffcf" | [[bip-0152.mediawiki|152]] | Peer Services | Compact Block Relay | Matt Corallo | Specification | Deployed |- style="background-color: #ffcfcf" | [[bip-0154.mediawiki|154]] | Peer Services | Rate Limiting via peer specified challenges | Karl-Johan Alm | Specification | Closed |- style="background-color: #cfffcf" | [[bip-0155.mediawiki|155]] | Peer Services | addrv2 message | Wladimir J. van der Laan | Specification | Deployed |- style="background-color: #ffcfcf" | [[bip-0156.mediawiki|156]] | Peer Services | Dandelion - Privacy Enhancing Routing | Brad Denby, Andrew Miller, Giulia Fanti, Surya Bakshi, Shaileshh Bojja Venkatakrishnan, Pramod Viswanath | Specification | Closed |- style="background-color: #cfffcf" | [[bip-0157.mediawiki|157]] | Peer Services | Client Side Block Filtering | Olaoluwa Osuntokun, Alex Akselrod, Jim Posen | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0158.mediawiki|158]] | Peer Services | Compact Block Filters for Light Clients | Olaoluwa Osuntokun, Alex Akselrod | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0159.mediawiki|159]] | Peer Services | NODE_NETWORK_LIMITED service bit | Jonas Schnelli | Specification | Deployed |- style="background-color: #ffcfcf" | [[bip-0171.mediawiki|171]] | Applications | Currency/exchange rate information API | Luke Dashjr | Specification | Closed |- | [[bip-0172.mediawiki|172]] | Applications | Define Bitcoin Subunits as Satoshis | OceanSlim | Informational | Draft |- style="background-color: #cfffcf" | [[bip-0173.mediawiki|173]] | Applications | Base32 address format for native v0-16 witness outputs | Pieter Wuille, Greg Maxwell | Informational | Deployed |- style="background-color: #cfffcf" | [[bip-0174.mediawiki|174]] | Applications | Partially Signed Bitcoin Transaction Format | Ava Chow | Specification | Deployed |- style="background-color: #ffcfcf" | [[bip-0175.mediawiki|175]] | Applications | Pay to Contract Protocol | Omar Shibli, Nicholas Gregory | Informational | Closed |- | [[bip-0176.mediawiki|176]] | | Bits Denomination | Jimmy Song | Informational | Draft |- | [[bip-0177.mediawiki|177]] | | Redefine Bitcoin's Base Unit | John Carvalho | Informational | Draft |- | [[bip-0178.mediawiki|178]] | Applications | Version Extended WIF | Karl-Johan Alm | Specification | Draft |- | [[bip-0179.mediawiki|179]] | | Name for payment recipient identifiers | Emil Engler, Luke Dashjr | Informational | Draft |- style="background-color: #ffcfcf" | [[bip-0180.mediawiki|180]] | Peer Services | Block size/weight fraud proof | Luke Dashjr | Specification | Closed |- | [[bip-0197.mediawiki|197]] | Applications | Hashed Time-Locked Collateral Contract | Matthew Black, Tony Cai | Specification | Draft |- style="background-color: #ffcfcf" | [[bip-0199.mediawiki|199]] | Applications | Hashed Time-Locked Contract transactions | Sean Bowe, Daira Hopwood | Specification | Closed |- | [[bip-0300.mediawiki|300]] | Consensus (soft fork) | Hashrate Escrows (Consensus layer) | Paul Sztorc, CryptAxe | Specification | Draft |- | [[bip-0301.mediawiki|301]] | Consensus (soft fork) | Blind Merged Mining (Consensus layer) | Paul Sztorc, CryptAxe | Specification | Draft |- | [[bip-0310.mediawiki|310]] | Applications | Stratum protocol extensions | Pavel Moravec, Jan Čapek | Informational | Draft |- | [[bip-0320.mediawiki|320]] | | nVersion bits for general purpose use | BtcDrak | Specification | Draft |- style="background-color: #ffffcf" | [[bip-0321.mediawiki|321]] | Applications | URI Scheme | Matt Corallo | Specification | Complete |- | [[bip-0322.mediawiki|322]] | Applications | Generic Signed Message Format | Karl-Johan Alm | Specification | Draft |- style="background-color: #cfffcf" | [[bip-0324.mediawiki|324]] | Peer Services | Version 2 P2P Encrypted Transport Protocol | Dhruv Mehta, Tim Ruffing, Jonas Schnelli, Pieter Wuille | Specification | Deployed |- style="background-color: #ffffcf" | [[bip-0325.mediawiki|325]] | Applications | Signet | Karl-Johan Alm, Anthony Towns | Specification | Complete |- | [[bip-0326.mediawiki|326]] | Applications | Anti-fee-sniping in taproot transactions | Chris Belcher | Informational | Draft |- style="background-color: #cfffcf" | [[bip-0327.mediawiki|327]] | | MuSig2 for BIP340-compatible Multi-Signatures | Jonas Nick, Tim Ruffing, Elliott Jin | Informational | Deployed |- style="background-color: #ffffcf" | [[bip-0328.mediawiki|328]] | Applications | Derivation Scheme for MuSig2 Aggregate Keys | Ava Chow | Informational | Complete |- | [[bip-0329.mediawiki|329]] | Applications | Wallet Labels Export Format | Craig Raw | Informational | Draft |- | [[bip-0330.mediawiki|330]] | Peer Services | Transaction announcements reconciliation | Gleb Naumenko, Pieter Wuille | Specification | Draft |- | [[bip-0331.mediawiki|331]] | Peer Services | Ancestor Package Relay | Gloria Zhao | Specification | Draft |- | [[bip-0337.mediawiki|337]] | API/RPC | Compressed Transactions | Tom Briar | Specification | Draft |- style="background-color: #ffcfcf" | [[bip-0338.mediawiki|338]] | Peer Services | Disable transaction relay message | Suhas Daftuar | Specification | Closed |- style="background-color: #cfffcf" | [[bip-0339.mediawiki|339]] | Peer Services | WTXID-based transaction relay | Suhas Daftuar | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0340.mediawiki|340]] | | Schnorr Signatures for secp256k1 | Pieter Wuille, Jonas Nick, Tim Ruffing | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0341.mediawiki|341]] | Consensus (soft fork) | Taproot: SegWit version 1 spending rules | Pieter Wuille, Jonas Nick, Anthony Towns | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0342.mediawiki|342]] | Consensus (soft fork) | Validation of Taproot Scripts | Pieter Wuille, Jonas Nick, Anthony Towns | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0343.mediawiki|343]] | Consensus (soft fork) | Mandatory activation of taproot deployment | Shinobius, Michael Folkson | Specification | Deployed |- style="background-color: #ffcfcf" | [[bip-0345.mediawiki|345]] | Consensus (soft fork) | OP_VAULT | James O'Beirne, Greg Sanders | Specification | Closed |- | [[bip-0346.md|346]] | Consensus (soft fork) | OP_TXHASH | Steven Roose, Brandon Black | Specification | Draft |- style="background-color: #ffffcf" | [[bip-0347.mediawiki|347]] | Consensus (soft fork) | OP_CAT in Tapscript | Ethan Heilman, Armin Sabouri | Specification | Complete |- | [[bip-0348.md|348]] | Consensus (soft fork) | CHECKSIGFROMSTACK | Brandon Black, Jeremy Rubin | Specification | Draft |- | [[bip-0349.md|349]] | Consensus (soft fork) | OP_INTERNALKEY | Brandon Black, Jeremy Rubin | Specification | Draft |- style="background-color: #cfffcf" | [[bip-0350.mediawiki|350]] | Applications | Bech32m format for v1+ witness addresses | Pieter Wuille | Specification | Deployed |- | [[bip-0351.mediawiki|351]] | Applications | Private Payments | Alfred Hodler, Clark Moody | Informational | Draft |- style="background-color: #ffffcf" | [[bip-0352.mediawiki|352]] | Applications | Silent Payments | josibake, Ruben Somsen, Sebastian Falbesoner | Specification | Complete |- style="background-color: #ffffcf" | [[bip-0353.mediawiki|353]] | Applications | DNS Payment Instructions | Matt Corallo, Bastien Teinturier | Specification | Complete |- | [[bip-0360.mediawiki|360]] | Consensus (soft fork) | Pay-to-Merkle-Root (P2MR) | Hunter Beast, Ethan Heilman, Isabel Foxen Duke | Specification | Draft |- style="background-color: #cfffcf" | [[bip-0370.mediawiki|370]] | Applications | PSBT Version 2 | Ava Chow | Specification | Deployed |- style="background-color: #cfffcf" | [[bip-0371.mediawiki|371]] | Applications | Taproot Fields for PSBT | Ava Chow | Specification | Deployed |- | [[bip-0372.mediawiki|372]] | Applications | Pay-to-contract tweak fields for PSBT | Maxim Orlovsky | Specification | Draft |- style="background-color: #ffffcf" | [[bip-0373.mediawiki|373]] | Applications | MuSig2 PSBT Fields | Ava Chow | Specification | Complete |- | [[bip-0374.mediawiki|374]] | Applications | Discrete Log Equality Proofs | Andrew Toth, Ruben Somsen, Sebastian Falbesoner | Specification | Draft |- | [[bip-0375.mediawiki|375]] | Applications | Sending Silent Payments with PSBTs | Andrew Toth, Ava Chow, josibake | Specification | Draft |- | [[bip-0379.md|379]] | Applications | Miniscript | Pieter Wuille, Andrew Poelstra, Sanket Kanjalkar, Antoine Poinsot, Ava Chow | Informational | Draft |- style="background-color: #cfffcf" | [[bip-0380.mediawiki|380]] | Applications | Output Script Descriptors General Operation | Pieter Wuille, Ava Chow | Informational | Deployed |- style="background-color: #cfffcf" | [[bip-0381.mediawiki|381]] | Applications | Non-Segwit Output Script Descriptors | Pieter Wuille, Ava Chow | Informational | Deployed |- style="background-color: #cfffcf" | [[bip-0382.mediawiki|382]] | Applications | Segwit Output Script Descriptors | Pieter Wuille, Ava Chow | Informational | Deployed |- style="background-color: #cfffcf" | [[bip-0383.mediawiki|383]] | Applications | Multisig Output Script Descriptors | Pieter Wuille, Ava Chow | Informational | Deployed |- style="background-color: #cfffcf" | [[bip-0384.mediawiki|384]] | Applications | combo() Output Script Descriptors | Pieter Wuille, Ava Chow | Informational | Deployed |- style="background-color: #cfffcf" | [[bip-0385.mediawiki|385]] | Applications | raw() and addr() Output Script Descriptors | Pieter Wuille, Ava Chow | Informational | Deployed |- style="background-color: #cfffcf" | [[bip-0386.mediawiki|386]] | Applications | tr() Output Script Descriptors | Pieter Wuille, Ava Chow | Informational | Deployed |- style="background-color: #cfffcf" | [[bip-0387.mediawiki|387]] | Applications | Tapscript Multisig Output Script Descriptors | Pieter Wuille, Ava Chow | Informational | Deployed |- style="background-color: #ffffcf" | [[bip-0388.mediawiki|388]] | Applications | Wallet Policies for Descriptor Wallets | Salvatore Ingala | Specification | Complete |- | [[bip-0389.mediawiki|389]] | Applications | Multipath Descriptor Key Expressions | Ava Chow | Informational | Draft |- | [[bip-0390.mediawiki|390]] | Applications | musig() Descriptor Key Expression | Ava Chow | Informational | Draft |- | [[bip-0392.mediawiki|392]] | Applications | Silent Payment Output Script Descriptors | Craig Raw | Specification | Draft |- | [[bip-0431.mediawiki|431]] | Applications | Topology Restrictions for Pinning | Gloria Zhao | Informational | Draft |- | [[bip-0433.mediawiki|433]] | Applications | Pay to Anchor (P2A) | Gregory Sanders | Informational | Draft |- | [[bip-0434.md|434]] | Peer Services | Peer Feature Negotiation | Anthony Towns | Specification | Draft |- | [[bip-0442.md|442]] | Consensus (soft fork) | OP_PAIRCOMMIT | moonsettler, Brandon Black | Specification | Draft |- | [[bip-0443.mediawiki|443]] | Consensus (soft fork) | OP_CHECKCONTRACTVERIFY | Salvatore Ingala | Specification | Draft |- | [[bip-0446.md|446]] | Consensus (soft fork) | OP_TEMPLATEHASH | Gregory Sanders, Antoine Poinsot, Steven Roose | Specification | Draft |- | [[bip-0448.md|448]] | Consensus (soft fork) | Taproot-native (Re)bindable Transactions | Gregory Sanders, Antoine Poinsot, Steven Roose | Specification | Draft |} ================================================ FILE: bip-0001.mediawiki ================================================
  BIP: 1
  Title: BIP Purpose and Guidelines
  Authors: Amir Taaki 
  Status: Closed
  Type: Process
  Assigned: 2011-09-19
  Proposed-Replacement: 2
==What is a BIP?== BIP stands for Bitcoin Improvement Proposal. A BIP is a design document providing information to the Bitcoin community, or describing a new feature for Bitcoin or its processes or environment. The BIP should provide a concise technical specification of the feature and a rationale for the feature. We intend BIPs to be the primary mechanisms for proposing new features, for collecting community input on an issue, and for documenting the design decisions that have gone into Bitcoin. The BIP author is responsible for building consensus within the community and documenting dissenting opinions. Because the BIPs are maintained as text files in a versioned repository, their revision history is the historical record of the feature proposal. ==BIP Types== There are three kinds of BIP: * A Standards Track BIP describes any change that affects most or all Bitcoin implementations, such as a change to the network protocol, a change in block or transaction validity rules, or any change or addition that affects the interoperability of applications using Bitcoin. * An Informational BIP describes a Bitcoin design issue, or provides general guidelines or information to the Bitcoin community, but does not propose a new feature. Informational BIPs do not necessarily represent a Bitcoin community consensus or recommendation, so users and implementers are free to ignore Informational BIPs or follow their advice. * A Process BIP describes a process surrounding Bitcoin, or proposes a change to (or an event in) a process. Process BIPs are like Standards Track BIPs but apply to areas other than the Bitcoin protocol itself. They may propose an implementation, but not to Bitcoin's codebase; they often require community consensus; unlike Informational BIPs, they are more than recommendations, and users are typically not free to ignore them. Examples include procedures, guidelines, changes to the decision-making process, and changes to the tools or environment used in Bitcoin development. Any meta-BIP is also considered a Process BIP. ==BIP Work Flow== The BIP process begins with a new idea for Bitcoin. Each potential BIP must have a champion -- someone who writes the BIP using the style and format described below, shepherds the discussions in the appropriate forums, and attempts to build community consensus around the idea. The BIP champion (a.k.a. Author) should first attempt to ascertain whether the idea is BIP-able. Posting to the [https://lists.linuxfoundation.org/mailman/listinfo/bitcoin-dev bitcoin-dev@lists.linuxfoundation.org] mailing list (and maybe the [https://bitcointalk.org/index.php?board=6.0 Development & Technical Discussion] forum) is the best way to go about this. Vetting an idea publicly before going as far as writing a BIP is meant to save both the potential author and the wider community time. Many ideas have been brought forward for changing Bitcoin that have been rejected for various reasons. Asking the Bitcoin community first if an idea is original helps prevent too much time being spent on something that is guaranteed to be rejected based on prior discussions (searching the internet does not always do the trick). It also helps to make sure the idea is applicable to the entire community and not just the author. Just because an idea sounds good to the author does not mean it will work for most people in most areas where Bitcoin is used. Small enhancements or patches often don't need standardisation between multiple projects; these don't need a BIP and should be injected into the relevant Bitcoin development work flow with a patch submission to the applicable Bitcoin issue tracker. Once the champion has asked the Bitcoin community as to whether an idea has any chance of acceptance, a draft BIP should be presented to the [https://lists.linuxfoundation.org/mailman/listinfo/bitcoin-dev bitcoin-dev] mailing list. This gives the author a chance to flesh out the draft BIP to make it properly formatted, of high quality, and to address additional concerns about the proposal. Following a discussion, the proposal should be sent to the bitcoin-dev list and the BIP editor with the draft BIP. This draft must be written in BIP style as described below, else it will be sent back without further regard until proper formatting rules are followed. BIP authors are responsible for collecting community feedback on both the initial idea and the BIP before submitting it for review. However, wherever possible, long open-ended discussions on public mailing lists should be avoided. Strategies to keep the discussions efficient include: setting up a separate SIG mailing list for the topic, having the BIP author accept private comments in the early design phases, setting up a wiki page or git repository, etc. BIP authors should use their discretion here. It is highly recommended that a single BIP contain a single key proposal or new idea. The more focused the BIP, the more successful it tends to be. If in doubt, split your BIP into several well-focused ones. The BIP editors assign BIP numbers and change their status. Please send all BIP-related email to the BIP editor, which is listed under [[#BIP_Editors|BIP Editors]] below. Also see [[#BIP_Editor_Responsibilities__Workflow|BIP Editor Responsibilities & Workflow]]. The BIP editor reserves the right to reject BIP proposals if they appear too unfocused or too broad. Authors MUST NOT self assign BIP numbers, but should use an alias such as "bip-johndoe-infinitebitcoins" which includes the author's name/nick and the BIP subject. If the BIP editor approves, he will assign the BIP a number, label it as Standards Track, Informational, or Process, give it status "Draft", and add it to the BIPs git repository. The BIP editor will not unreasonably deny a BIP. Reasons for denying BIP status include duplication of effort, disregard for formatting rules, being too unfocused or too broad, being technically unsound, not providing proper motivation or addressing backwards compatibility, or not in keeping with the Bitcoin philosophy. For a BIP to be accepted it must meet certain minimum criteria. It must be a clear and complete description of the proposed enhancement. The enhancement must represent a net improvement. The proposed implementation, if applicable, must be solid and must not complicate the protocol unduly. The BIP author may update the Draft as necessary in the git repository. Updates to drafts may also be submitted by the author as pull requests. Standards Track BIPs consist of two parts, a design document and a reference implementation. The BIP should be reviewed and accepted before a reference implementation is begun, unless a reference implementation will aid people in studying the BIP. Standards Track BIPs must include an implementation -- in the form of code, a patch, or a URL to same -- before it can be considered Final. Once a BIP has been accepted, the reference implementation must be completed. When the reference implementation is complete and accepted by the community, the status will be changed to "Final". A BIP can also be assigned status "Deferred". The BIP author or editor can assign the BIP this status when no progress is being made on the BIP. Once a BIP is deferred, the BIP editor can re-assign it to draft status. A BIP can also be "Rejected". Perhaps after all is said and done it was not a good idea. It is still important to have a record of this fact. BIPs can also be superseded by a different BIP, rendering the original obsolete. This is intended for Informational BIPs, where version 2 of an API can replace version 1. The possible paths of the status of BIPs are as follows: Some Informational and Process BIPs may also have a status of "Active" if they are never meant to be completed. E.g. BIP 1 (this BIP). ==What belongs in a successful BIP?== Each BIP should have the following parts: * Preamble -- RFC 822 style headers containing meta-data about the BIP, including the BIP number, a short descriptive title (limited to a maximum of 44 characters), the names, and optionally the contact info for each author, etc. * Abstract -- a short (~200 word) description of the technical issue being addressed. * Copyright/public domain -- Each BIP must either be explicitly labelled as placed in the public domain (see this BIP as an example) or licensed under the Open Publication License. * Specification -- The technical specification should describe the syntax and semantics of any new feature. The specification should be detailed enough to allow competing, interoperable implementations for any of the current Bitcoin platforms (Satoshi, BitcoinJ, bitcoin-js, libbitcoin). * Motivation -- The motivation is critical for BIPs that want to change the Bitcoin protocol. It should clearly explain why the existing protocol specification is inadequate to address the problem that the BIP solves. BIP submissions without sufficient motivation may be rejected outright. * Rationale -- The rationale fleshes out the specification by describing what motivated the design and why particular design decisions were made. It should describe alternate designs that were considered and related work, e.g. how the feature is supported in other languages. * The rationale should provide evidence of consensus within the community and discuss important objections or concerns raised during discussion. * Backwards Compatibility -- All BIPs that introduce backwards incompatibilities must include a section describing these incompatibilities and their severity. The BIP must explain how the author proposes to deal with these incompatibilities. BIP submissions without a sufficient backwards compatibility treatise may be rejected outright. * Reference Implementation -- The reference implementation must be completed before any BIP is given status "Final", but it need not be completed before the BIP is accepted. It is better to finish the specification and rationale first and reach consensus on it before writing code. * The final implementation must include test code and documentation appropriate for the Bitcoin protocol. ==BIP Formats and Templates== BIPs should be written in mediawiki or markdown format. ===BIP Header Preamble=== Each BIP must begin with an RFC 822 style header preamble. The headers must appear in the following order. Headers marked with "*" are optional and are described below. All other headers are required.
  BIP: 
  Title: 
  Author: 
* Discussions-To: 
  Status: 
  Type: 
  Created: 
* Post-History: 
* Replaces: 
* Superseded-By: 
* Resolution: 
The Author header lists the names, and optionally the email addresses of all the authors/owners of the BIP. The format of the Author header value must be Random J. User if the email address is included, and just Random J. User if the address is not given. If there are multiple authors, each should be on a separate line following RFC 2822 continuation line conventions. Note: The Resolution header is required for Standards Track BIPs only. It contains a URL that should point to an email message or other web resource where the pronouncement about the BIP is made. While a BIP is in private discussions (usually during the initial Draft phase), a Discussions-To header will indicate the mailing list or URL where the BIP is being discussed. No Discussions-To header is necessary if the BIP is being discussed privately with the author, or on the bitcoin email mailing lists. The Type header specifies the type of BIP: Standards Track, Informational, or Process. The Created header records the date that the BIP was assigned a number, while Post-History is used to record the dates of when new versions of the BIP are posted to bitcoin mailing lists. Both headers should be in yyyy-mm-dd format, e.g. 2001-08-14. BIPs may have a Requires header, indicating the BIP numbers that this BIP depends on. BIPs may also have a Superseded-By header indicating that a BIP has been rendered obsolete by a later document; the value is the number of the BIP that replaces the current document. The newer BIP must have a Replaces header containing the number of the BIP that it rendered obsolete. ===Auxiliary Files=== BIPs may include auxiliary files such as diagrams. Image files should be included in a subdirectory for that BIP. Auxiliary files must be named BIP-XXXX-Y.ext, where "XXXX" is the BIP number, "Y" is a serial number (starting at 1), and "ext" is replaced by the actual file extension (e.g. "png"). ==Transferring BIP Ownership== It occasionally becomes necessary to transfer ownership of BIPs to a new champion. In general, we'd like to retain the original author as a co-author of the transferred BIP, but that's really up to the original author. A good reason to transfer ownership is because the original author no longer has the time or interest in updating it or following through with the BIP process, or has fallen off the face of the 'net (i.e. is unreachable or not responding to email). A bad reason to transfer ownership is because you don't agree with the direction of the BIP. We try to build consensus around a BIP, but if that's not possible, you can always submit a competing BIP. If you are interested in assuming ownership of a BIP, send a message asking to take over, addressed to both the original author and the BIP editor. If the original author doesn't respond to email in a timely manner, the BIP editor will make a unilateral decision (it's not like such decisions can't be reversed :). ==BIP Editors== The current BIP editor is Luke Dashjr who can be contacted at [[mailto:luke_bipeditor@dashjr.org|luke_bipeditor@dashjr.org]]. ==BIP Editor Responsibilities & Workflow== The BIP editor subscribes to the Bitcoin development mailing list. All BIP-related correspondence should be sent (or CC'd) to luke_bipeditor@dashjr.org. For each new BIP that comes in an editor does the following: * Read the BIP to check if it is ready: sound and complete. The ideas must make technical sense, even if they don't seem likely to be accepted. * The title should accurately describe the content. * Edit the BIP for language (spelling, grammar, sentence structure, etc.), markup (for reST BIPs), code style (examples should match BIP 8 & 7). If the BIP isn't ready, the editor will send it back to the author for revision, with specific instructions. Once the BIP is ready for the repository it should be submitted as a "pull request" to the [https://github.com/bitcoin/bips bitcoin/bips] repository on GitHub where it may get further feedback. The BIP editor will: * Assign a BIP number (almost always just the next available number, but sometimes it's a special/joke number, like 666 or 3141) in the pull request comments. * Merge the pull request when the author is ready (allowing some time for further peer review). * List the BIP in [[README.mediawiki]] * Send email back to the BIP author with next steps (post to bitcoin-dev mailing list). The BIP editors are intended to fulfill administrative and editorial responsibilities. The BIP editors monitor BIP changes, and correct any structure, grammar, spelling, or markup mistakes we see. ==History== This document was derived heavily from Python's PEP-0001. In many places text was simply copied and modified. Although the PEP-0001 text was written by Barry Warsaw, Jeremy Hylton, and David Goodger, they are not responsible for its use in the Bitcoin Improvement Process, and should not be bothered with technical questions specific to Bitcoin or the BIP process. Please direct all comments to the BIP editors or the Bitcoin development mailing list. ==Changelog== 10 Oct 2015 - Added clarifications about submission process and BIP number assignment. 01 Jan 2016 - Clarified early stages of BIP idea championing, collecting community feedback, etc. ================================================ FILE: bip-0002.mediawiki ================================================
  BIP: 2
  Title: BIP process, revised
  Authors: Luke Dashjr 
  Status: Closed
  Type: Process
  Assigned: 2016-02-03
  License: BSD-2-Clause OR OPUBL-1.0
  Replaces: 1
  Proposed-Replacement: 3
==Abstract== A Bitcoin Improvement Proposal (BIP) is a design document providing information to the Bitcoin community, or describing a new feature for Bitcoin or its processes or environment. The BIP should provide a concise technical specification of the feature and a rationale for the feature. We intend BIPs to be the primary mechanisms for proposing new features, for collecting community input on an issue, and for documenting the design decisions that have gone into Bitcoin. The BIP author is responsible for building consensus within the community and documenting dissenting opinions. Because the BIPs are maintained as text files in a versioned repository, their revision history is the historical record of the feature proposal. This particular BIP replaces BIP 1 with a more well-defined and clear process. ==Copyright== This BIP is dual-licensed under the Open Publication License and BSD 2-clause license. ==BIP workflow== The BIP process begins with a new idea for Bitcoin. Each potential BIP must have a champion -- someone who writes the BIP using the style and format described below, shepherds the discussions in the appropriate forums, and attempts to build community consensus around the idea. The BIP champion (a.k.a. Author) should first attempt to ascertain whether the idea is BIP-able. Small enhancements or patches to a particular piece of software often don't require standardisation between multiple projects; these don't need a BIP and should be injected into the relevant project-specific development workflow with a patch submission to the applicable issue tracker. Additionally, many ideas have been brought forward for changing Bitcoin that have been rejected for various reasons. The first step should be to search past discussions to see if an idea has been considered before, and if so, what issues arose in its progression. After investigating past work, the best way to proceed is by posting about the new idea to the [https://groups.google.com/g/bitcoindev Bitcoin development mailing list]. Vetting an idea publicly before going as far as writing a BIP is meant to save both the potential author and the wider community time. Asking the Bitcoin community first if an idea is original helps prevent too much time being spent on something that is guaranteed to be rejected based on prior discussions (searching the internet does not always do the trick). It also helps to make sure the idea is applicable to the entire community and not just the author. Just because an idea sounds good to the author does not mean it will work for most people in most areas where Bitcoin is used. Once the champion has asked the Bitcoin community as to whether an idea has any chance of acceptance, a draft BIP should be presented to the [https://groups.google.com/g/bitcoindev Bitcoin development mailing list]. This gives the author a chance to flesh out the draft BIP to make it properly formatted, of high quality, and to address additional concerns about the proposal. Following a discussion, the proposal should be submitted to the [https://github.com/bitcoin/bips BIPs git repository] as a pull request. This draft must be written in BIP style as described below, and named with an alias such as "bip-johndoe-infinitebitcoins" until an editor has assigned it a BIP number (authors MUST NOT self-assign BIP numbers). BIP authors are responsible for collecting community feedback on both the initial idea and the BIP before submitting it for review. However, wherever possible, long open-ended discussions on public mailing lists should be avoided. Strategies to keep the discussions efficient include: setting up a separate SIG mailing list for the topic, having the BIP author accept private comments in the early design phases, setting up a wiki page or git repository, etc. BIP authors should use their discretion here. It is highly recommended that a single BIP contain a single key proposal or new idea. The more focused the BIP, the more successful it tends to be. If in doubt, split your BIP into several well-focused ones. When the BIP draft is complete, a BIP editor will assign the BIP a number, label it as Standards Track, Informational, or Process, and merge the pull request to the BIPs git repository. The BIP editors will not unreasonably reject a BIP. Reasons for rejecting BIPs include duplication of effort, disregard for formatting rules, being too unfocused or too broad, being technically unsound, not providing proper motivation or addressing backwards compatibility, or not in keeping with the Bitcoin philosophy. For a BIP to be accepted it must meet certain minimum criteria. It must be a clear and complete description of the proposed enhancement. The enhancement must represent a net improvement. The proposed implementation, if applicable, must be solid and must not complicate the protocol unduly. The BIP author may update the draft as necessary in the git repository. Updates to drafts should also be submitted by the author as pull requests. ===Transferring BIP Ownership=== It occasionally becomes necessary to transfer ownership of BIPs to a new champion. In general, we'd like to retain the original author as a co-author of the transferred BIP, but that's really up to the original author. A good reason to transfer ownership is because the original author no longer has the time or interest in updating it or following through with the BIP process, or has fallen off the face of the 'net (i.e. is unreachable or not responding to email). A bad reason to transfer ownership is because you don't agree with the direction of the BIP. We try to build consensus around a BIP, but if that's not possible, you can always submit a competing BIP. If you are interested in assuming ownership of a BIP, send a message asking to take over, addressed to both the original author and the BIP editors. If the original author doesn't respond to email in a timely manner, the BIP editors will make a unilateral decision (it's not like such decisions can't be reversed :). ===BIP Editors=== The current BIP editors are: * Bryan Bishop ([[mailto:kanzure@gmail.com|kanzure@gmail.com]]) * Jon Atack ([[mailto:jon@atack.com|jon@atack.com]]) * Luke Dashjr ([[mailto:luke_bipeditor@dashjr.org|luke_bipeditor@dashjr.org]]) * Mark "Murch" Erhardt ([[mailto:murch@murch.one|murch@murch.one]]) * Olaoluwa Osuntokun ([[mailto:laolu32@gmail.com|laolu32@gmail.com]]) * Ruben Somsen ([[mailto:rsomsen@gmail.com|rsomsen@gmail.com]]) ===BIP Editor Responsibilities & Workflow=== The BIP editors subscribe to the Bitcoin development mailing list. Off-list BIP-related correspondence should be sent (or CC'd) to the BIP editors. For each new BIP that comes in an editor does the following: * Read the BIP to check if it is ready: sound and complete. The ideas must make technical sense, even if they don't seem likely to be accepted. * The title should accurately describe the content. * The BIP draft must have been sent to the Bitcoin development mailing list for discussion. * Motivation and backward compatibility (when applicable) must be addressed. * The defined Layer header must be correctly assigned for the given specification. * Licensing terms must be acceptable for BIPs. If the BIP isn't ready, the editor will send it back to the author for revision, with specific instructions. Once the BIP is ready for the repository it should be submitted as a "pull request" to the [https://github.com/bitcoin/bips BIPs git repository] where it may get further feedback. The BIP editor will: * Assign a BIP number in the pull request. * Merge the pull request when it is ready. * List the BIP in [[README.mediawiki]] The BIP editors are intended to fulfill administrative and editorial responsibilities. The BIP editors monitor BIP changes, and update BIP headers as appropriate. BIP editors may also, at their option, unilaterally make and merge strictly-editorial changes to BIPs, such as correcting misspellings, fixing broken links, etc. ==BIP format and structure== ===Specification=== BIPs should be written in mediawiki or markdown format. Each BIP should have the following parts: * Preamble -- Headers containing metadata about the BIP ([[#BIP header preamble|see below]]). * Abstract -- A short (~200 word) description of the technical issue being addressed. * Copyright -- The BIP must be explicitly licensed under acceptable copyright terms ([[#BIP licensing|see below]]). * Specification -- The technical specification should describe the syntax and semantics of any new feature. The specification should be detailed enough to allow competing, interoperable implementations for any of the current Bitcoin platforms. * Motivation -- The motivation is critical for BIPs that want to change the Bitcoin protocol. It should clearly explain why the existing protocol is inadequate to address the problem that the BIP solves. * Rationale -- The rationale fleshes out the specification by describing what motivated the design and why particular design decisions were made. It should describe alternate designs that were considered and related work. The rationale should provide evidence of consensus within the community and discuss important objections or concerns raised during discussion. * Backwards compatibility -- All BIPs that introduce backwards incompatibilities must include a section describing these incompatibilities and their severity. The BIP must explain how the author proposes to deal with these incompatibilities. * Reference implementation -- The reference implementation must be completed before any BIP is given status "Final", but it need not be completed before the BIP is accepted. It is better to finish the specification and rationale first and reach consensus on it before writing code. The final implementation must include test code and documentation appropriate for the Bitcoin protocol. ====BIP header preamble==== Each BIP must begin with an RFC 822 style header preamble. The headers must appear in the following order. Headers marked with "*" are optional and are described below. All other headers are required.
  BIP: 
* Layer: 
  Title: 
  Author: 
* Discussions-To: 
* Comments-Summary: 
  Comments-URI: 
  Status: 
  Type: 
  Created: 
  License: 
* License-Code: 
* Post-History: 
* Requires: 
* Replaces: 
* Superseded-By: 
The Layer header (only for Standards Track BIPs) documents which layer of Bitcoin the BIP applies to. See [[bip-0123.mediawiki|BIP 123]] for definitions of the various BIP layers. Activation of this BIP implies activation of BIP 123. The Author header lists the names and email addresses of all the authors/owners of the BIP. The format of the Author header value must be Random J. User If there are multiple authors, each should be on a separate line following RFC 2822 continuation line conventions. While a BIP is in private discussions (usually during the initial Draft phase), a Discussions-To header will indicate the mailing list or URL where the BIP is being discussed. No Discussions-To header is necessary if the BIP is being discussed privately with the author, or on the bitcoin email mailing lists. The Type header specifies the type of BIP: Standards Track, Informational, or Process. The Created header records the date that the BIP was assigned a number, while Post-History is used to record when new versions of the BIP are posted to bitcoin mailing lists. Dates should be in yyyy-mm-dd format, e.g. 2001-08-14. Post-History is permitted to be a link to a specific thread in a mailing list archive. BIPs may have a Requires header, indicating the BIP numbers that this BIP depends on. BIPs may also have a Superseded-By header indicating that a BIP has been rendered obsolete by a later document; the value is the number of the BIP that replaces the current document. The newer BIP must have a Replaces header containing the number of the BIP that it rendered obsolete. ====Auxiliary Files==== BIPs may include auxiliary files such as diagrams. Auxiliary files should be included in a subdirectory for that BIP, or must be named BIP-XXXX-Y.ext, where "XXXX" is the BIP number, "Y" is a serial number (starting at 1), and "ext" is replaced by the actual file extension (e.g. "png"). ==BIP types== There are three kinds of BIP: * A Standards Track BIP describes any change that affects most or all Bitcoin implementations, such as a change to the network protocol, a change in block or transaction validity rules, or any change or addition that affects the interoperability of applications using Bitcoin. Standards Track BIPs consist of two parts, a design document and a reference implementation. * An Informational BIP describes a Bitcoin design issue, or provides general guidelines or information to the Bitcoin community, but does not propose a new feature. Informational BIPs do not necessarily represent a Bitcoin community consensus or recommendation, so users and implementers are free to ignore Informational BIPs or follow their advice. * A Process BIP describes a process surrounding Bitcoin, or proposes a change to (or an event in) a process. Process BIPs are like Standards Track BIPs but apply to areas other than the Bitcoin protocol itself. They may propose an implementation, but not to Bitcoin's codebase; they often require community consensus; unlike Informational BIPs, they are more than recommendations, and users are typically not free to ignore them. Examples include procedures, guidelines, changes to the decision-making process, and changes to the tools or environment used in Bitcoin development. Any meta-BIP is also considered a Process BIP. ==BIP status field== ===Specification=== The typical paths of the status of BIPs are as follows: Champions of a BIP may decide on their own to change the status between Draft, Deferred, or Withdrawn. A BIP editor may also change the status to Deferred when no progress is being made on the BIP. A BIP may only change status from Draft (or Rejected) to Proposed, when the author deems it is complete, has a working implementation (where applicable), and has community plans to progress it to the Final status. BIPs should be changed from Draft or Proposed status, to Rejected status, upon request by any person, if they have not made progress in three years. Such a BIP may be changed to Draft status if the champion provides revisions that meaningfully address public criticism of the proposal, or to Proposed status if it meets the criteria required as described in the previous paragraph. A Proposed BIP may progress to Final only when specific criteria reflecting real-world adoption has occurred. This is different for each BIP depending on the nature of its proposed changes, which will be expanded on below. Evaluation of this status change should be objectively verifiable, and/or be discussed on the development mailing list. When a Final BIP is no longer relevant, its status may be changed to Replaced or Obsolete (which is equivalent to Replaced). This change must also be objectively verifiable and/or discussed. A process BIP may change status from Draft to Active when it achieves rough consensus on the mailing list. Such a proposal is said to have rough consensus if it has been open to discussion on the development mailing list for at least one month, and no person maintains any unaddressed substantiated objections to it. Addressed or obstructive objections may be ignored/overruled by general agreement that they have been sufficiently addressed, but clear reasoning must be given in such circumstances. ====Progression to Final status==== A soft-fork BIP strictly requires a clear miner majority expressed by blockchain voting (eg, using BIP 9). In addition, if the economy seems willing to make a "no confidence" hard-fork (such as a change in proof-of-work algorithm), the soft-fork does not become Final for as long as such a hard-fork might have majority support, or at most three months. Soft-fork BIPs may also set additional requirements for their adoption. Because of the possibility of changes to miner dynamics, especially in light of delegated voting (mining pools), it is highly recommended that a supermajority vote around 95% be required by the BIP itself, unless rationale is given for a lower threshold. A hard-fork BIP requires adoption from the entire Bitcoin economy, particularly including those selling desirable goods and services in exchange for bitcoin payments, as well as Bitcoin holders who wish to spend or would spend their bitcoins (including selling for other currencies) differently in the event of such a hard-fork. Adoption must be expressed by de facto usage of the hard-fork in practice (ie, not merely expressing public support, although that is a good step to establish agreement before adoption of the BIP). This economic adoption cannot be established merely by a super-majority, except by literally forcing the minority to accept the hard-fork (whether this is viable or not is outside the scope of this document). Peer services BIPs should be observed to be adopted by at least 1% of public listening nodes for one month. API/RPC and application layer BIPs must be implemented by at least two independent and compatible software applications. Software authors are encouraged to publish summaries of what BIPs their software supports to aid in verification of status changes. Good examples of this at the time of writing this BIP, can be observed in [https://github.com/bitcoin/bitcoin/blob/master/doc/bips.md Bitcoin Core's doc/bips.md file] as well as [https://github.com/bitcoin-wallet/bitcoin-wallet/blob/master/wallet/README.specs.md Bitcoin Wallet for Android's wallet/README.specs.md file]. These criteria are considered objective ways to observe the de facto adoption of the BIP, and are not to be used as reasons to oppose or reject a BIP. Should a BIP become actually and unambiguously adopted despite not meeting the criteria outlined here, it should still be updated to Final status. ===Rationale=== Why is this necessary at all? * BIP 1 defines an ambiguous criteria for the Status field of BIPs, which is often a source of confusion. As a result, many BIPs with significant real-world use have been left as Draft or Proposed status longer than appropriate. By giving objective criteria to judge the progression of BIPs, this proposal aims to help keep the Status accurate and up-to-date. How is the entire Bitcoin economy defined by people selling goods/services and holders? * For Bitcoin to function as a currency, it must be accepted as payment. Bitcoins have no value if you cannot acquire anything in exchange for them. If everyone accepting such payments requires a particular set of consensus rules, "bitcoins" are de facto defined by that set of rules - this is already the case today. If those consensus rules are expected to broaden (as with a hard-fork), those merchants need to accept payments made under the new set of rules, or they will reject "bitcoins" as invalid. Holders are relevant to the degree in that they choose the merchants they wish to spend their bitcoins with, and could also as a whole decide to sell under one set of consensus rules or the other, thus flooding the market with bitcoins and crashing the price. Why aren't included in the economy? * Some entities may, to some degree, also be involved in offering goods and/or services in exchange for bitcoins, thus in that capacity (but not their capacity as ) be involved in the economy. * Miners are not included in the economy, because they merely *rely on* others to sell/spend their otherwise-worthless mined produce. Therefore, they must accept everyone else's direction in deciding the consensus rules. * Exchanges are not included in the economy, because they merely provide services of connecting the merchants and users who wish to trade. Even if all exchanges were to defect from Bitcoin, those merchants and users can always trade directly and/or establish their own exchanges. * Developers are not included in the economy, since they merely write code, and it is up to others to decide to use that code or not. But they're doing something important and have invested a lot in Bitcoin! Shouldn't they be included in such an important decision? * This BIP does not aim to address what "should" be the basis of decisions. Such a statement, no matter how perfect in its justification, would be futile without some way to force others to use it. The BIP process does not aim to be a kind of forceful "governance" of Bitcoin, merely to provide a collaborative repository for proposing and providing information on standards, which people may voluntarily adopt or not. It can only hope to achieve accuracy in regard to the "Status" field by striving to reflect the reality of *how things actually are*, rather than *how they should be*. What if a single merchant wishes to block a hard-fork? * This BIP addresses only the progression of the BIP Status field, not the deployment of the hard-fork (or any other change) itself. * Regardless, one shop cannot operate in a vacuum: if they are indeed alone, they will soon find themselves no longer selling in exchange for bitcoin payments, as nobody else would exist willing to use the previous blockchain to pay them. If they are no longer selling, they cease to meet the criteria herein which enables their veto. How about a small number of merchants (maybe only two) who sell products to each other? * In this scenario, it would seem the previous Bitcoin is alive and working, and that the hard-fork has failed. How to resolve such a split is outside the scope of this BIP. How can economic agreement veto a soft-fork? * The group of miners is determined by the consensus rules for the dynamic-membership multi-party signature (for Bitcoin, the proof-of-work algorithm), which can be modified with a hard-fork. Thus, if the same conditions required to modify this group are met in opposition to a soft-fork, the miner majority supporting the soft-fork is effectively void because the economy can decide to replace them with another group of would-be miners who do not support the soft-fork. What happens if the economy decides to hard-fork away from a controversial soft-fork, more than three months later? * The controversial soft-fork, in this circumstance, changes from Final to Replaced status to reflect the nature of the hard-fork replacing the previous (final) soft-fork. What is the ideal percentage of listening nodes needed to adopt peer services proposals? * This is unknown, and set rather arbitrarily at this time. For a random selection of peers to have at least one other peer implementing the extension, 13% or more would be necessary, but nodes could continue to scan the network for such peers with perhaps some reasonable success. Furthermore, service bits exist to help identification upfront. Why is it necessary for at least two software projects to release an implementation of API/RPC and application layer BIPs, before they become Final? * If there is only one implementation of a specification, there is no other program for which a standard interface is used with or needed. * Even if there are only two projects rather than more, some standard coordination between them exists. What if a BIP is proposed that only makes sense for a single specific project? * The BIP process exists for standardisation between independent projects. If something only affects one project, it should be done through that project's own internal processes, and never be proposed as a BIP in the first place. ==BIP comments== ===Specification=== Each BIP should, in its preamble, link to a public wiki page with a summary tone of the comments on that page. Reviewers of the BIP who consider themselves qualified, should post their own comments on this wiki page. The comments page should generally only be used to post final comments for a completed BIP. If a BIP is not yet completed, reviewers should instead post on the applicable development mailing list thread to allow the BIP author(s) to address any concerns or problems pointed out by the review. Some BIPs receive exposure outside the development community prior to completion, and other BIPs might not be completed at all. To avoid a situation where critical BIP reviews may go unnoticed during this period, reviewers may, at their option, still post their review on the comments page, provided they first post it to the mailing list and plan to later remove or revise it as applicable based on the completed version. Such revisions should be made by editing the previous review and updating the timestamp. Reviews made prior to the complete version may be removed if they are no longer applicable and have not been updated in a timely manner (eg, within one month). Pages must be named after the full BIP number (eg, "BIP 0001") and placed in the "Comments" namespace. For example, the link for BIP 1 will be https://github.com/bitcoin/bips/wiki/Comments:BIP-0001 . Comments posted to this wiki should use the following format: --, BIPs may also choose to list a second forum for BIP comments, in addition to the BIPs wiki. In this case, the second forum's URI should be listed below the primary wiki's URI. After some time, the BIP itself may be updated with a summary tone of the comments. Summary tones may be chosen from the following, but this BIP does not intend to cover all possible nuances and other summaries may be used as needed: * No comments yet. * Unanimously Recommended for implementation * Unanimously Discourage for implementation * Mostly Recommended for implementation, with some Discouragement * Mostly Discouraged for implementation, with some Recommendation For example, the preamble to BIP 1 might be updated to include the line: Comments-Summary: No comments yet. Comments-URI: https://github.com/bitcoin/bips/wiki/Comments:BIP-0001 https://some-other-wiki.org/BIP_1_Comments These fields must follow the "Discussions-To" header defined in BIP 1 (if that header is not present, it should follow the position where it would be present; generally this is immediately above the Status header). To avoid doubt: comments and status are unrelated metrics to judge a BIP, and neither should be directly influencing the other. ===Rationale=== What is the purpose of BIP comments? * Various BIPs have been adopted (the criteria required for "Final" Status) despite being considered generally inadvisable. Some presently regard BIPs as a "good idea" simply by virtue of them being assigned a BIP number. Due to the low barrier of entry for submission of new BIPs, it seems advisable for a way for reviewers to express their opinions on them in a way that is consumable to the public without needing to review the entire development discussion. Will BIP comments be censored or limited to particular participants/"experts"? * Participants should freely refrain from commenting outside of their area of knowledge or expertise. However, comments should not be censored, and participation should be open to the public. ==BIP licensing== ===Specification=== New BIPs may be accepted with the following licenses. Each new BIP must identify at least one acceptable license in its preamble. The License header in the preamble must be placed after the Created header. Each license must be referenced by their respective abbreviation given below. For example, a preamble might include the following License header: License: BSD-2-Clause GNU-All-Permissive In this case, the BIP text is fully licensed under both the OSI-approved BSD 2-clause license as well as the GNU All-Permissive License, and anyone may modify and redistribute the text provided they comply with the terms of *either* license. In other words, the license list is an "OR choice", not an "AND also" requirement. It is also possible to license source code differently from the BIP text. An optional License-Code header is placed after the License header. Again, each license must be referenced by their respective abbreviation given below. For example, a preamble specifying the optional License-Code header might look like: License: BSD-2-Clause GNU-All-Permissive License-Code: GPL-2.0+ In this case, the code in the BIP is not available under the BSD or All-Permissive licenses, but only under the terms of the GNU General Public License (GPL), version 2 or newer. If the code were to be available under *only* version 2 exactly, the "+" symbol should be removed from the license abbreviation. For a later version (eg, GPL 3.0), you would increase the version number (and retain or remove the "+" depending on intent). License-Code: GPL-2.0 # This refers to GPL v2.0 *only*, no later license versions are acceptable. License-Code: GPL-2.0+ # This refers to GPL v2.0 *or later*. License-Code: GPL-3.0 # This refers to GPL v3.0 *only*, no later license versions are acceptable. License-Code: GPL-3.0+ # This refers to GPL v3.0 *or later*. In the event that the licensing for the text or code is too complicated to express with a simple list of alternatives, the list should instead be replaced with the single term "Complex". In all cases, details of the licensing terms must be provided in the Copyright section of the BIP. BIPs are not required to be *exclusively* licensed under approved terms, and may also be licensed under unacceptable licenses *in addition to* at least one acceptable license. In this case, only the acceptable license(s) should be listed in the License and License-Code headers. ====Recommended licenses==== * BSD-2-Clause: [https://opensource.org/license/BSD-2-Clause OSI-approved BSD 2-clause license] * BSD-3-Clause: [https://opensource.org/license/BSD-3-Clause OSI-approved BSD 3-clause license] * CC0-1.0: [https://creativecommons.org/publicdomain/zero/1.0/ Creative Commons CC0 1.0 Universal] * FSFAP: [https://www.gnu.org/prep/maintain/html_node/License-Notices-for-Other-Files.html FSF All Permissive License] In addition, it is recommended that literal code included in the BIP be dual-licensed under the same license terms as the project it modifies. For example, literal code intended for Bitcoin Core would ideally be dual-licensed under the MIT license terms as well as one of the above with the rest of the BIP text. ====Not recommended, but acceptable licenses==== * Apache-2.0: [https://www.apache.org/licenses/LICENSE-2.0 Apache License, version 2.0] * BSL-1.0: [https://www.boost.org/LICENSE_1_0.txt Boost Software License, version 1.0] * CC-BY-4.0: [https://creativecommons.org/licenses/by/4.0/ Creative Commons Attribution 4.0 International] * CC-BY-SA-4.0: [https://creativecommons.org/licenses/by-sa/4.0/ Creative Commons Attribution-ShareAlike 4.0 International] * MIT: [https://opensource.org/license/MIT The MIT License] * AGPL-3.0+: [https://www.gnu.org/licenses/agpl-3.0.en.html GNU Affero General Public License (AGPL), version 3 or newer] * FDL-1.3: [https://www.gnu.org/licenses/fdl-1.3.en.html GNU Free Documentation License, version 1.3] * GPL-2.0+: [https://www.gnu.org/licenses/old-licenses/gpl-2.0.en.html GNU General Public License (GPL), version 2 or newer] * LGPL-2.1+: [https://www.gnu.org/licenses/old-licenses/lgpl-2.1.en.html GNU Lesser General Public License (LGPL), version 2.1 or newer] ====Not acceptable licenses==== All licenses not explicitly included in the above lists are not acceptable terms for a Bitcoin Improvement Proposal unless a later BIP extends this one to add them. However, BIPs predating the acceptance of this BIP were allowed under other terms, and should use these abbreviation when no other license is granted: * OPUBL-1.0: [https://opencontent.org/openpub/ Open Publication License, version 1.0] * PD: Released into the public domain ===Rationale=== BIP 1 allowed the Open Publication License or releasing into the public domain; was this insufficient? * The OPUBL-1.0 is generally regarded as obsolete, and not a license suitable for new publications. * Many are unfamiliar with the OPUBL-1.0 terms, and may just prefer to use the public domain rather than license under uncertain terms. * The OPUBL-1.0 license terms allowed for the author to prevent publication and derived works, which was widely considered inappropriate for Bitcoin standards. * Public domain is not universally recognised as a legitimate action, thus it is inadvisable. Why are there software licenses included? * Some BIPs, especially consensus layer, may include literal code in the BIP itself which may not be available under the exact license terms of the BIP. * Despite this, not all software licenses would be acceptable for content included in BIPs. Why is Public Domain no longer acceptable for new BIPs? * In some jurisdictions, public domain is not recognised as a legitimate legal action, leaving the BIP simply copyrighted with no redistribution or modification allowed at all. ==Changes from BIP 1== * Acceptable licenses are entirely rechosen, allowing a wide variety of open licenses, while prohibiting the problematic older choices. * Accepted Status has been renamed to Proposed. * An implementation is now required (when applicable) before BIPs can proceed to Proposed Status. * BIP Comments are newly introduced. * The License preamble headers have been added. * The Layer header is included from BIP 123. * Non-image auxiliary files are permitted in the bip-XXXX subdirectory. * Email addresses are now required for authors. * The Post-History header may be provided as a link instead of a simple date. * The Resolution header has been dropped, as it is not applicable to a decentralised system where no authority exists to make final decisions. ==See Also== * [[bip-0001.mediawiki|BIP 1: BIP Purpose and Guidelines]] * [[bip-0123.mediawiki|BIP 123: BIP Classification]] * [https://tools.ietf.org/html/rfc7282 RFC 7282: On Consensus and Humming in the IETF] ================================================ FILE: bip-0003.md ================================================ ``` BIP: 3 Title: Updated BIP Process Authors: Murch Status: Deployed Type: Process Assigned: 2025-01-09 License: BSD-2-Clause Discussion: https://github.com/murchandamus/bips/pull/2 https://gnusha.org/pi/bitcoindev/59fa94cea6f70e02b1ce0da07ae230670730171c.camel@timruffing.de/#t Version: 1.4.0 Requires: 123 Replaces: 2 ``` ## Abstract This _Bitcoin Improvement Proposal (BIP)_ provides information about the preparation of BIPs and policies relating to the publication of BIPs. It replaces [BIP 2](bip-0002.mediawiki) with a streamlined process, and may be amended to address the evolving needs of the BIP process. ## Motivation BIP 2 was written in 2016. This BIP revisits aspects of the BIP 2 process that did not achieve broad adoption, reduces the judgment calls assigned to the BIP Editor role, delineates the BIP types more clearly, and generalizes the BIP process to fit the community’s use of the repository. ## Fundamentals ### What is a BIP? BIPs are improvement proposals for Bitcoin. The main topic is information and technologies that support and expand the utility of the Bitcoin currency. Most BIPs provide a concise, self-contained, technical description of one new concept, feature, or standard. Some BIPs describe processes, implementation guidelines, best practices, incident reports (e.g., [BIP 50](bip-0050.mediawiki)), or other information relevant to the Bitcoin community. However, any topics related to the Bitcoin protocol, peer-to-peer network, and client software may be acceptable. BIPs are intended to be a means for proposing new protocol features, coordinating client standards, and documenting design decisions that have gone into implementations. BIPs may be submitted by anyone, provided the content is of high quality, e.g., does not waste the community’s time. The scope of the BIPs repository is limited to BIPs that do not oppose the fundamental principle that Bitcoin constitutes a peer-to-peer electronic cash system for the Bitcoin currency. ### BIP Ownership Each BIP is primarily owned by its authors and represents the authors’ opinion or recommendation. The authors are expected to foster discussion, address feedback and dissenting opinions, and, if applicable, advance the adoption of their proposal within the Bitcoin community. As a BIP progresses through the workflow, it becomes increasingly co-owned by the Bitcoin community. #### Authors and Deputies Authors may want additional help with the BIP process after writing an initial draft. In that case, they may assign one or more Deputies to their BIP. Deputies are stand-in owners of a BIP who were not involved in writing the document. They support the authors in advancing the proposal, or act as a point of contact for the BIP in the absence of the authors. Deputies may perform the role of Authors for any aspect of the BIP process unless overruled by an Author. Deputies share ownership of the BIP at the discretion of the Authors. ### What is the Significance of BIPs? BIPs do not define what Bitcoin is: individual BIPs do not represent Bitcoin community consensus or a general recommendation for implementation. A BIP represents a personal recommendation by the BIP authors to the Bitcoin community. Some BIPs may never be adopted. Some BIPs may be adopted by one or more Bitcoin clients or other related software. Some may even end up changing the consensus rules that the Bitcoin ecosystem jointly enforces. ### What is the Purpose of the BIPs Repository? The [BIPs repository](https://github.com/bitcoin/bips/) serves as a publication medium and archive for mature proposals. Through its high visibility, it facilitates the community-wide consideration of BIPs and provides a well-established source to retrieve the latest version of any BIP. The repository transparently records all changes to each BIP and allows any community member to retain a complete copy of the archive easily. The BIPs repository neither tracks community sentiment[^acceptance] nor ecosystem adoption[^adoption] of BIPs beyond the brief overview provided via the BIP status (see [Workflow](#workflow) below). Proposals are published in this repository if they are on-topic and fulfill the editorial criteria. No formal or informal decision body governs Bitcoin development or decides adoption of BIPs. ## BIP Format and Structure ### Specification Authors may choose to submit BIPs in MediaWiki or Markdown[^markdown] format. Each BIP must have a _Preamble_, an _Abstract_, a _Copyright_, and a _Motivation_ section. Authors should consider all issues in the following list and address each as appropriate. * Preamble — Headers containing metadata about the BIP (see the section [BIP Header Preamble](#bip-header-preamble) below). * Abstract — A short description of the issue being addressed. * Motivation — Why is this BIP being written? Clearly explain how the existing situation presents a problem and why the proposed idea resolves the issue or improves upon the current situation. * Specification — The technical specification should describe the syntax and semantics of any new feature. The specification should be detailed enough to enable any Bitcoin project to create an interoperable implementation. * Rationale — The rationale fleshes out the specification by describing what inspired the design and why particular design decisions were made. It should describe related work and alternate designs that were considered. The rationale should record relevant objections or important concerns that were raised and addressed as this proposal was developed. * Backward Compatibility — Any BIP that introduces incompatibilities must include a section describing these incompatibilities and their severity as well as provide instructions on how implementers and users should deal with these incompatibilities. * Reference Implementation — Where applicable, a reference implementation, test vectors, and documentation must be finished before the BIP can be given the status "Complete". Test vectors must be provided in the BIP or as auxiliary files (see [Auxiliary Files](#auxiliary-files)) under an acceptable license. The reference implementation can be provided in the BIP, as an auxiliary file, or per linking another code reference that is expected to remain available permanently such as a pull request, a dedicated branch, a new repository, or similar. * Changelog — A section to track modifications to a BIP after reaching Complete status. * Copyright — The BIP must be placed under an acceptable license (see [BIP Licensing](#bip-licensing) below). #### BIP Header Preamble Each BIP must begin with an [RFC 822-style header preamble](https://www.w3.org/Protocols/rfc822/). The headers must appear in the following order. Headers marked with "\*" are optional. All other headers are required. ##### Overview ``` BIP: * Layer: Title: Authors: * Deputies: Status: Type: Assigned: License: * Discussion: * Version: * Requires: * Replaces: * Proposed-Replacement: ``` ##### Header Descriptions * BIP — The assigned number of the BIP (without leading zeros). Please use "?" before a number has been assigned by the BIP Editors. * Layer — The layer of Bitcoin the BIP applies to using the BIP classification defined in [BIP 123](bip-0123.mediawiki). * Authors — The names (or pseudonyms) and email addresses of all authors of the BIP. The format of each authors header value must be Random J. User Multiple authors are recorded on separate lines: Authors: Random J. User Anata Sample * Deputies — Additional owners of the BIP that are not authors. The Deputies header uses the same format as the Authors header. See the [BIP Ownership](#bip-ownership) section above. * Status — The stage of the workflow of the proposal. See the [Workflow](#workflow) section below. * Type — See the [BIP Types](#bip-types) section below for a description of the three BIP types. * Assigned – The date a BIP was assigned its number. Please use "?" before a number has been assigned by the BIP Editors. * License — The License header specifies SPDX License Expressions describing the terms under which the BIP and its auxiliary files are available. See the [BIP Licensing](#bip-licensing) section below. * Discussion — The Discussion header points the audience to relevant discussions of the BIP, e.g., the mailing list thread in which the idea for the BIP was discussed, a thread where a new version of the BIP was presented, or relevant discussion threads on other platforms. Entries take the format "yyyy-mm-dd: URL", e.g., `2009-01-09: https://www.mail-archive.com/cryptography@metzdowd.com/msg10142.html`, using the date and URL of the start of the conversation. Multiple discussions should be listed on separate lines. * Version — The current version number of this BIP. See the [Changelog](#changelog-section-and-version-header) section below. * Requires — A list of existing BIPs the new proposal depends on. If multiple BIPs are required, they should be listed in one line separated by a comma and space (e.g., "1, 2"). * Replaces[^proposes-to-replace] — BIP authors may put the numbers of one or more prior BIPs in the Replaces header to recommend that their BIP succeeds, supersedes, or renders obsolete those prior BIPs. * Proposed-Replacement[^superseded-by-proposed-replacement] — When a later BIP indicates that it intends to supersede an existing BIP, the later BIP’s number is added to the Proposed-Replacement header of the existing BIP to indicate the potential successor BIP. #### Auxiliary Files BIPs may include auxiliary files such as diagrams and source code. Auxiliary files must be included in a subdirectory for that BIP named `bip-XXXX`, where "XXXX" is the BIP number zero-padded to four digits. File names in the subdirectory do not need to adhere to a specific convention. ### BIP Types * A **Specification BIP** defines a set of technical rules describing a new feature or affecting the interoperability of implementations. The distinguishing characteristic of a Specification BIP is that it can be implemented, and implementations can be compliant with it. Specification BIPs must have a Specification section, must have a Backward Compatibility section (if incompatibilities are introduced), and can only be advanced to Complete after they contain or refer to a reference implementation and test vectors. * An **Informational BIP** describes a Bitcoin design issue, or provides general guidelines or other information to the Bitcoin community. * A **Process BIP** describes a process surrounding Bitcoin, or proposes a change to (or an event in) a process. Process BIPs are like Specification BIPs, but apply to topics other than the Bitcoin protocol and Bitcoin implementations. They often require community consensus and are typically binding for the corresponding process. Examples include procedures, guidelines, and changes to decision-making processes such as the BIP process. ## Workflow The BIP process starts with a new idea for Bitcoin. Each potential BIP must have authors—people who write the BIP, gather feedback, shepherd the discussion in the appropriate forums, and finally recommend a mature proposal to the community. ![Status Diagram](bip-0003/status-diagram.png "Status Diagram for the BIP Workflow") ### Ideation After having an idea, the authors should evaluate whether it meets the criteria to become a BIP, as described in this BIP. The idea must be of interest to the broader community or relevant to multiple software projects. Minor improvements and matters concerning only a single project usually do not require standardization and should instead be brought up directly to the relevant project. The authors should first research whether their idea has been considered before. Ideas in Bitcoin are often rediscovered, and prior related discussions may inform the authors of the issues that may arise in its progression. After some investigation, the novelty and viability of the idea should be tested by posting a new, dedicated thread about the idea to the [Bitcoin Development Mailing List](https://groups.google.com/g/bitcoindev). Prior correspondence can be found in the [mailing list archive](https://gnusha.org/pi/bitcoindev/). It is recommended that authors establish before or at the start of working on a draft whether their idea may be of interest to the Bitcoin community. Authors should avoid opening a pull request with a BIP draft out of the blue. Vetting an idea publicly before investing time and effort to formally describe the idea is meant to save time for both the authors and the community. Not only may someone point out relevant discussion topics that were missed in the authors’ research, or that an idea is guaranteed to be rejected based on prior discussions, but describing an idea publicly also tests whether it is of interest to more people beside the authors. As a first sketch of the proposal is taking shape, the authors should present it to the [Bitcoin Development Mailing List](https://groups.google.com/g/bitcoindev). This gives the authors a chance to collect initial feedback and address fundamental concerns. If the authors wish to work in public on the proposal at this stage, it is recommended that they open a pull request against one of their forks of the BIPs repository instead of the main BIPs repository. It is recommended that complicated proposals be split into separate BIPs that each focus on a specific component of the overall proposal. ### Progression through BIP Statuses The following sections refer to BIP Status field values. The BIP Status field is defined in the Header Preamble specification above. #### Draft After fleshing out the proposal further and ensuring that it is of high quality and properly formatted, the authors should open a pull request to the [BIPs repository](https://github.com/bitcoin/bips). The document must adhere to the formatting requirements specified above and should be provided as a file named with a working title of the form "bip-title.[md|mediawiki]". Only BIP Editors may assign BIP numbers. Until one has done so, authors should refer to their BIP by name only. BIPs that (1) adhere to the formatting requirements, (2) are on-topic, and (3) have materially progressed beyond the ideation phase, e.g., by generating substantial public discussion and commentary from diverse contributors, by independent Bitcoin projects working on adopting the proposal, or by the authors working for an extended period toward improving the proposal based on community feedback, will be assigned a number by a BIP Editor. A number may be considered assigned only after it has been publicly announced in the pull request by a BIP Editor. The BIP Editors should not assign a number when they perceive a proposal being met with lack of interest: number assignment facilitates the distributed discussion of ideas, but before a proposal garners some interest in the Bitcoin community, there is no need to refer to it by a number. Proposals are also not ready for number assignment if they duplicate efforts, disregard formatting rules, are too unfocused or too broad, fail to provide proper motivation, fail to address backward compatibility where necessary, or fail to specify the feature clearly and comprehensively. Reviewers and BIP Editors should provide guidance on how the proposal may be improved to progress toward readiness. Pull requests that are proposing off-topic ideas or have stopped making progress may be closed. When the proposal is ready and has been assigned a number, a BIP Editor will merge it into the BIPs repository. After the BIP has been merged to the repository, its main focus should no longer shift significantly, even while the authors may continue to update the proposal as necessary. Updates to merged documents by the authors should also be submitted as pull requests. #### Complete[^complete] When the authors have concluded all planned work on their proposal, are confident that their BIP represents a net improvement, is clear, comprehensive, and is ready for adoption by the Bitcoin community, they may update the BIP’s status to Complete to indicate that they recommend adoption, implementation, or deployment of the BIP. Where applicable, the authors must ensure that any proposed specification is solid, not unduly complicated, and definitive. Specification BIPs must come with or refer to a working reference implementation and comprehensive test vectors before they can be moved to Complete. Subsequently, the BIP’s content should only be adjusted in minor details, e.g., to improve language, clarify ambiguities, backfill omissions in the specification, add test vectors for edge cases, or address other issues discovered as the BIP is being adopted. A Complete BIP can only move to Deployed or Closed. Any necessary changes to the specification should be minimal and interfere as little as possible with ongoing adoption. If a Complete BIP is found to need substantial functional changes, it may be preferable to move it to Closed[^new-BIP], and to start a new BIP with the changes instead. Otherwise, it could cause confusion as to what being compliant with the BIP means. A BIP may remain in the Complete status indefinitely unless its authors or deputies decide to move it to Closed or it is advanced to Deployed. Complete is the final status for most successful Informational BIPs. #### Deployed A Complete BIP should only be moved to Deployed once it is settled: after its approach has solidified, its Specification has been put through its paces, feedback from early adopters has been processed, and amendments to the BIP have stopped. Then, a BIP may be advanced to Deployed upon request by any community member with evidence[^evidence] that the BIP is in active use. Convincing evidence includes for example: an established project having deployed support for the BIP in mainnet software releases, a soft fork proposal’s activation criteria having been met on the network, or rough consensus for the BIP having been demonstrated. Once Deployed, the BIP is considered final. Any modifications to the BIP beyond bug fixes, other minor amendments, additions to the test vectors, or editorial changes should be avoided. Any breaking changes to the BIP’s Specification should be proposed as a new separate BIP.[^new-BIP] ##### Process BIPs A Process BIP may change status from Complete to Deployed when it achieves rough consensus on the Bitcoin Development Mailing List. A proposal is said to have rough consensus if its advancement has been open to discussion on the mailing list for at least one month, the discussion achieved meaningful engagement, and no person maintains any unaddressed substantiated objections to it. Addressed or obstructive objections may be ignored/overruled by general agreement that they have been sufficiently addressed, but clear reasoning must be given in such circumstances. Deployed Process BIPs may be modified indefinitely as long as a proposed modification has rough consensus per the same criteria.[^living-documents] #### Closed[^closed] A BIP that is of historical interest only, and is not being actively worked on, promoted or in active use, should be marked as Closed. The reason for moving the proposal to (or from) Closed should be recorded in the Changelog section in the same commit that updates the status. BIPs do not get deleted, they are retained even after being updated to Closed. Transitions involving the Closed state are: ##### Draft ↦ Closed BIP authors may decide on their own to change their BIP’s status from Draft to Closed. If a Draft BIP stops making progress, sees accumulated feedback unaddressed, or otherwise appears stalled for a year, anyone may propose the BIP status be updated to Closed. The BIP is then updated to Closed unless the authors assert that they intend to continue work within four weeks of being contacted. ##### Complete ↦ Closed BIPs that had attained the Complete status, i.e., that had been recommended for adoption, may be moved to Closed per the authors’ announcement to the Bitcoin Development Mailing List[^bip-announcements-to-list]. However, if someone volunteers to adopt the proposal within four weeks, they become the BIP's author or deputy (see [Transferring BIP Ownership](#transferring-bip-ownership) below), and the BIP will remain Complete instead. ##### Deployed ↦ Closed A BIP may evolve from Deployed to Closed when it is no longer in active use. Any community member may initiate this Status update by announcing it to the mailing list[^bip-announcements-to-list], and proceed if no objections have been raised for four weeks. ##### Closed ↦ Draft The Closed status is generally intended to be a final status for BIPs, and if BIP authors decide to make another attempt at a previously Closed BIP, it is generally recommended to create a new proposal. (Obviously, the authors may borrow any amount of inspiration or actual text from any prior BIPs as licensing permits.) The authors should take special care to address the issues that caused the prior attempt’s abandonment. Even if the prior attempt had been assigned a number, the new BIP will generally be assigned a distinct number. However, if it is obvious that the new attempt directly continues work on the same idea, it may be reasonable to return the Closed BIP to Draft status. ### Changelog Section and Version Header To help implementers understand updates to a BIP, any changes after it has reached Complete must be tracked with version, date, and description in a Changelog section sorted by most recent version first. The version number is inspired by semantic versioning (MAJOR.MINOR.PATCH). The MAJOR version is incremented if changes to the BIP’s Specification are introduced that are incompatible with prior versions (which should be rare after a BIP is Complete, and only happen in well-grounded exceptional cases to a BIP that is Deployed). The MINOR version is incremented whenever the specification of the BIP is changed or extended in a backward-compatible way. The PATCH version is incremented for other changes to the BIP that are noteworthy (bug fixes, test vectors, important clarifications, etc.). Version 1.0.0 is used to label the promotion to Complete. A Changelog section may be introduced during the Draft phase to record significant changes (using versions 0.x.y). Example: > __Changelog__ > > * __2.0.0__ (2025-01-22): > * Introduce a breaking change in the specification to fix a bug. > * __1.1.0__ (2025-01-17): > * Add a backward compatible extension to the BIP. > * __1.0.1__ (2025-01-15): > * Clarify an edge case and add corresponding test vectors. > * __1.0.0__ (2025-01-14): > * Complete planned work on the BIP. After a BIP receives a Changelog, the Preamble must indicate the latest version in the Version header. The Changelog highlights revisions to BIPs to human readers. A single BIP shall not recommend more than one variant of an idea at the same time. A different or competing variant of an existing BIP must be published as a separate BIP. ### Adoption of Proposals The BIPs repository does not track the sentiment on proposals and does not track the adoption of BIPs beyond whether they are in active use or not. It is not intended for BIPs to list additional implementations beyond the reference implementation: the BIPs repository is not a signpost where to find implementations.[^OtherImplementations] After a BIP is advanced to Complete, it is up to the Bitcoin community to evaluate, adopt, ignore, or reject a BIP. Individual Bitcoin projects are encouraged to publish a list of BIPs they implement. A good example of this at the time of writing this BIP can be observed in Bitcoin Core’s [doc/bips.md](https://github.com/bitcoin/bitcoin/blob/master/doc/bips.md) file. ### Transferring BIP Ownership It occasionally becomes necessary to transfer ownership of BIPs to new owners. In general, it would be preferable to retain the original authors of the transferred BIP, but that is up to the original authors. A good reason to transfer ownership is because the original authors no longer have the time or interest in updating it or following through with the BIP process, or are unreachable or unresponsive. A bad reason to transfer ownership is because someone doesn't agree with the direction of the BIP. The community tries to build consensus around a BIP, but if that's not possible, rather than fighting over control, the dissenters should supply a competing BIP. If someone is interested in assuming ownership of a BIP, they should send an email asking to take over, addressed to the original authors, the BIP Editors, and the Bitcoin Development Mailing List[^bip-announcements-to-list]. If the authors are unreachable or do not respond in a timely manner (e.g., four weeks), the BIP Editors will make a unilateral decision whether to appoint the applicants as [Authors or Deputies](#authors-and-deputies) (which may be amended should the original authors make a delayed reappearance). ## BIP Licensing The Bitcoin project develops a global peer-to-peer digital cash system. Open standards are indispensable for continued interoperability. Open standards reduce friction, and encourage anybody and everyone to contribute, compete, and innovate on a level playing field. Only freely licensed contributions are accepted to the BIPs repository. ### Specification Each new BIP must specify in two ways under which license terms it is made available. First, it must specify an [SPDX License Expression](https://spdx.dev/ids/) in the License field in the preamble. Second, it must include a matching Copyright section, possibly providing further details on licensing. For example, a preamble might include the following License header: License: CC0-1.0 OR MIT In this case, the BIP (including all auxiliary files) is made available under the terms of both CC0 1.0 Universal as well as the MIT License, and anyone may modify and redistribute it provided they comply with the terms of *either* license, at their option. In other words, the license list is an "OR choice", not an "AND also" requirement. See the [SPDX documentation](https://spdx.dev/ids/) and the [SPDX License List](https://spdx.org/licenses/) for further details. Wherever different from those specified in the License header, an auxiliary file or directory should specify the license terms under which it is made available as is common in software (e.g., with a [`SPDX-License-Identifier: ` comment](https://spdx.dev/ids/), a license header, or a LICENSE/COPYING file). Such exceptions should also be mentioned in the Copyright section. It is recommended to make any test vectors available under CC0-1.0 or FSFAP in addition to any other licenses to allow anyone to copy test vectors into their implementations without introducing license hindrances. A few BIP2-era BIPs (98, 116, 117, 330, 340) have a no longer used "License-Code" header indicating the license terms applicable to auxiliary source code files. For such cases, please refer to BIP2. It is recommended that source code included in a BIP (whether within the text or in auxiliary files) be licensed under the same license terms as the project it is proposed to modify, if any. For example, changes intended for Bitcoin Core would ideally be licensed (also) under the MIT License. In all cases, details of the licensing terms must be provided in the Copyright section of the BIP. #### Acceptable Licenses[^licenses] Each new BIP must be made available under at least one acceptable license as listed below. BIPs are not required to be *exclusively* licensed under approved terms, and may also be licensed under other licenses *in addition to* at least one acceptable license. In other words, a new BIP must specify an SPDX License Expression that is either "L" or equivalent to "L OR E" for some acceptable license L from the following list and another SPDX License Expression E. * BSD-2-Clause: [BSD 2-Clause License](https://opensource.org/license/BSD-2-Clause) * BSD-3-Clause: [BSD 3-Clause License](https://opensource.org/license/BSD-3-Clause) * CC0-1.0: [CC0 1.0 Universal](https://creativecommons.org/publicdomain/zero/1.0/) * FSFAP: [FSF All Permissive License](https://www.gnu.org/prep/maintain/html_node/License-Notices-for-Other-Files.html) * CC-BY-4.0: [Creative Commons Attribution 4.0 International](https://creativecommons.org/licenses/by/4.0/) * MIT: [The MIT License](https://opensource.org/license/MIT) * MIT-0: [MIT No Attribution License](https://opensource.org/license/MIT-0) * Apache-2.0: [Apache License 2.0](https://www.apache.org/licenses/LICENSE-2.0) * BSL-1.0: [Boost Software License 1.0](https://www.boost.org/LICENSE_1_0.txt) #### Not Acceptable Licenses All licenses not explicitly included in the above lists are not acceptable terms for a Bitcoin Improvement Proposal. However, BIPs predating this proposal were accepted under other terms, and should use one of the following identifiers. * LicenseRef-PD: Placed into the public domain * OPUBL-1.0: [Open Publication License 1.0](https://opencontent.org/openpub/) ## BIP Editors The current BIP Editors are: * Bryan Bishop ([kanzure@gmail.com](mailto:kanzure@gmail.com)) * Jon Atack ([jon@atack.com](mailto:jon@atack.com)) * Luke Dashjr ([luke_bipeditor@dashjr.org](mailto:luke_bipeditor@dashjr.org)) * Mark "Murch" Erhardt ([murch@murch.one](mailto:murch@murch.one)) * Olaoluwa Osuntokun ([laolu32@gmail.com](mailto:laolu32@gmail.com)) * Ruben Somsen ([rsomsen@gmail.com](mailto:rsomsen@gmail.com)) ### BIP Editor Responsibilities and Workflow The BIP Editors subscribe to the Bitcoin Development Mailing List and watch the [BIPs repository](https://github.com/bitcoin/bips). When either a new BIP idea or an early draft is submitted to the mailing list, BIP Editors or other community members should comment in regard to: * Novelty of the idea * Viability, utility, and relevance of the concept * Readiness of the proposal * On-topic for the Bitcoin community Discussion in pull request comments can often be hard to follow as feedback gets marked as resolved when it is addressed by authors. Substantive discussion of ideas may be more accessible to a broader audience on the mailing list, where it is also more likely to be retained by the community memory. If the BIP needs more work, an editor should ensure that constructive, actionable feedback is provided to the authors for revision. Once the BIP is ready it should be submitted as a "pull request" to the [BIPs repository](https://github.com/bitcoin/bips) where it may get further feedback. For each new BIP pull request that comes in, an editor checks the following: * The idea has been previously proposed to the Bitcoin Development Mailing List and discussed there * The described idea is on-topic for the repository * A draft of the BIP by one of the authors has been previously discussed on the Bitcoin Development Mailing List * Title accurately describes the content * Proposal is of general interest and/or pertains to more than one Bitcoin project/implementation * Document is properly formatted * Licensing terms are acceptable * Motivation, Rationale, and Backward Compatibility have been addressed * Specification provides sufficient detail for implementation * The defined Layer and Type headers must be correctly assigned for the given specification * The BIP is ready: it is comprehensible, technically feasible and sound, and all aspects are addressed as necessary Editors do NOT evaluate whether the proposal is likely to be adopted. Then, a BIP Editor will: * Assign a BIP number in the pull request * Ensure that the BIP is listed in the [README](README.mediawiki) * Merge the pull request when it is ready The BIP Editors are intended to fulfill administrative and editorial responsibilities. The BIP Editors monitor BIP changes, and update BIP headers as appropriate. BIP Editors may also, at their option, unilaterally make and merge strictly editorial changes to BIPs, such as correcting misspellings, mending grammar mistakes, fixing broken links, etc. as long as they do not change the meaning or conflict with the original intent of the authors. Such a change must be recorded in the Changelog if it’s noteworthy per the criteria mentioned in the [Changelog](#changelog) section. ## Backward Compatibility ### Changes from BIP 2 #### Workflow - Status field values are reduced from nine to four: - Deferred, Obsolete, Rejected, Replaced, and Withdrawn are gathered up into Closed.[^closed] - Final and Active are collapsed into Deployed. - Proposed is renamed to Complete. - The remaining statuses are Draft, Complete, Deployed, and Closed. - The comment system is abolished.[^comments] - A BIP in Draft or Complete status may no longer be closed solely on grounds of not making progress for three years.[^rejection] - A BIP in Draft status may be updated to Closed status if it appears to have stopped making progress for at least a year and its authors do not assert within four weeks of being contacted that they intend to continue working on it. - Complete BIPs can only be moved to Closed by its authors and may remain in Complete indefinitely. - A Changelog section is introduced to track significant changes to BIPs after they have reached the Complete status. - Process BIPs are living documents that do not ossify and may be modified indefinitely. - Some judgment calls previously required from BIP Editors are reassigned either to the BIP authors or the repository’s audience. #### BIP Format - The Standards Track type is superseded by the similar Specification type.[^standard-track] - Many sections are declared optional; it is up to the authors and reviewers to judge whether all relevant topics have been comprehensively addressed and which topics require a designated section to do so. - "Other Implementations" sections are discouraged.[^OtherImplementations] - Auxiliary files are only permitted in the corresponding BIP’s subdirectory, as no one used the alternative of labeling them with the BIP number. - Tracking of community consensus and adoption is out of scope for the BIPs repository, except to determine whether a BIP is in active use for the move into or out of the Deployed status. - The distinction between recommended and acceptable licenses was dropped. - Most licenses that have not been used in the BIP process have been dropped from the list of acceptable licenses. #### Preamble - "Comments-URI" and "Comments-Summary" headers are dropped from the preamble.[^comments] - The "Superseded-By" header is replaced with the "Proposed-Replacement" header. - The "Post-History" header is replaced with the "Discussion" header. - The optional "Version" header is introduced. - The "Discussions-To" header is dropped, as it has never been used in any BIP. - The "License-Code" header has been sunset, as it was used by only five BIPs (98, 116, 117, 330, 340) and created more ambiguity than clarity. - The "Created" header is renamed to "Assigned", as the header’s value is the date of number assignment.[^assigned] - Introduce Deputies and optional "Deputies" header. - The BIP "Title" header may now contain up to 50 characters (increased from 44 in BIP 2). - The "Layer" header is optional for Specification BIPs or Informational BIPs, as it does not make sense for all BIPs.[^layer] - Rename the "Author" field to "Authors". ### Updates to Existing BIPs should this BIP be Activated #### Previous BIP Process This BIP replaces BIP 2 as the guideline for the BIP process. #### BIP Types Standards Track BIPs and eligible Informational BIPs are assigned the Specification type. The Standards Track type is considered obsolete. Specification BIPs use the Layer header rules specified in [BIP 123](bip-0123.mediawiki). #### Comments The Comments-URI and Comments-Summary headers should be removed from all BIPs whose comment page in the wiki is empty. For existing BIPs whose comment page has content, BIP Authors may keep both headers or remove both headers at their discretion. It is recommended that existing wiki pages are not modified due to the activation of this BIP. #### Status Field After the activation of this BIP, the Status fields of existing BIPs that do not fit the specification in this BIP are updated to the corresponding values prescribed in this BIP. BIPs that have had Draft status for extended periods will be moved to Complete or Deployed as applicable in collaboration with their authors. The authors of incomplete Draft BIPs will be contacted to learn whether the BIPs are still in progress toward Complete, and will otherwise be updated to Closed as described in the [Workflow](#workflow) section above. #### Authors Header The Author header is replaced with the Authors header in all BIPs. #### Discussion Header The Post-History header is replaced with the Discussion header in all BIPs. #### Proposed-Replacement Header The Superseded-By header is replaced with the Proposed-Replacement header in all BIPs. #### Licenses Existing BIPs retain their license terms unchanged. The License and License-Code headers of BIPs are updated to express those terms using SPDX License Expressions. ## Changelog * __1.4.0__ (2025-12-09): * Revert AI guidance, add Changelog section, broaden reference implementation formats, move Type header responsibility to authors, other editorial changes * __1.3.1__ (2025-11-10): * Reiterate that numbers are assigned by BIP Editors in pull requests * __1.3.0__ (2025-10-22): * Restrict use of AI/LLM tools, require original work. * __1.2.1__ (2025-09-19): * Clarify that idea should be discussed on dedicated mailing list thread * __1.2.0__ (2025-09-19): * Rename Created header to Assigned to clarify that it holds the date of number assignment * __1.1.0__ (2025-07-18): * Switch to SPDX License Expressions, drop License-Code header, and make editorial changes to BIP Licensing section. * __1.0.1__ (2025-06-27): * Improve description of acceptance, purpose of the BIPs repository, when Draft BIPs can be closed due to not making progress, and make other minor improvements to phrasing. * __1.0.0__ (2025-03-18): * Complete planned work and move to Proposed. ## Copyright This BIP is licensed under the [BSD-2-Clause License](https://opensource.org/licenses/BSD-2-Clause). Some content was adapted from [BIP 2](bip-0002.mediawiki) which was also licensed under the BSD-2-Clause. ## Related Work - [BIP 1: BIP Purpose and Guidelines](bip-0001.mediawiki) - [BIP 2: BIP Process, revised](bip-0002.mediawiki) - [BIP 123: BIP Classification](bip-0123.mediawiki) - [RFC 822: Standard for ARPA Internet Text Messages](https://datatracker.ietf.org/doc/html/rfc822) - [RFC 2223: Instructions to RFC Authors](https://datatracker.ietf.org/doc/html/rfc2223) - [RFC 7282: On Consensus and Humming in the IETF](https://tools.ietf.org/html/rfc7282) ## Acknowledgements We thank AJ Towns, Jon Atack, Jonas Nick, Larry Ruane, Pieter Wuille, Tim Ruffing, and others for their review, feedback, and helpful comments. ## Rationale [^assigned]: **Why was the Created header renamed to Assigned?** Both BIP 1 and BIP 2 described the Created header as "date created on" in the preamble template, but followed that up with "Created header records the date that the BIP was assigned a number" as the description of the field. This has frequently led to confusion, with authors using the date of opening the pull request, the date they started writing their proposal, the date of number assignment (as prescribed), or various other dates. Aligning the name of the header and the text in the preamble template with the descriptions will reduce the confusion. [^standard-track]: **Why was the Specification type introduced?** The definitions of Informational and Standards Track BIPs caused some confusion in the past. Due to Informational BIPs being described as optional, Standards Track BIPs were sometimes misunderstood to be generally recommended. This has led to a number of BIPs that propose new features affecting interoperability of implementations being assigned the Informational type. The situation is remedied by introducing a new _Specification BIP_ type that is inclusive of any BIPs that can be implemented and affect interoperability of Bitcoin applications. Since all BIPs are individual recommendations by the authors (even if some may eventually achieve endorsement by the majority of the community), the prior reminder that Informational BIPs are optional is dropped. [^comments]: **Why were comments, Comments-URI, and Comments-Summary removed from the process?** The comments feature saw insignificant adoption. Few BIPs received any comments and barely any more than two with only a handful of contributors commenting at all. This led to many situations in which one or two comments ended up dominating the comment summary. While some of those comments may have been representative of broadly held opinions, it also overstated the importance of individual comments directly in the Preamble of BIPs. As collecting feedback in this accessible fashion failed, the new process puts the burden back on the audience to make their own evaluation. [^layer]: **Why is the layer header now permitted for other BIP types?** The layer header had already been used by many Informational BIPs, so the rule that it is only available to Standards Track BIPs is dropped. [^OtherImplementations]: **What is the issue with "Other Implementations" sections in BIPs?** In the past, some BIPs had "Other Implementations" sections that caused frequent change requests to existing BIPs. This put a burden on the BIP authors and BIP Editors, and frequently led to lingering pull requests due to the corresponding BIPs’ authors no longer participating in the process. Many of these alternative implementations eventually became unmaintained or were low-quality to begin with. Therefore, "Other Implementations" sections are heavily discouraged. [^complete]: **Why was the Proposed status renamed to Complete?** Some reviewers of this BIP raised that in a process which outlines the workflow of Bitcoin Improvement _Proposals_ using "Proposed" as a status field value was overloading the term: clearly _proposals_ are proposed at all stages of the process. "Complete" expresses that the authors have concluded planned work on all parts of the proposal and are ready to recommend their BIP for adoption. The term "ready" was also considered, but considered too subjective. [^rejection]: **Why can proposals remain in Draft or Complete indefinitely?** The automatic 3-year timeout of BIPs has led to some disagreement in the past and seems unnecessary in cases where the authors remain active in the community and still consider their idea worth pursuing. On the other hand, Draft proposals that appear stale may be closed after only one year, which should achieve the main goal of the original rule by limiting the effort and attention spent on proposals that never reach Complete. [^closed]: **Why was the Closed Status introduced?** The Closed Status provides value to the audience by indicating which documents are only of historical significance. Previously, the process had Deferred, Obsolete, Rejected, Replaced, and Withdrawn, which all meant some flavor of "work has stopped on this." The many statuses complicated the process, may have contributed to process fatigue, and may have resulted in BIPs’ statuses not being maintained well. The author of this BIP feels that all of the aforementioned can be represented by _Closed_ without significantly impacting the information quality of the overview table. Where the many Status variants provided minuscule additional information, the simplification is more valuable and the Changelog section now collects specific details. [^acceptance]: **When is a BIP "accepted"?** Many standards processes such as the PEPs or the IETF have a mechanism for a proposal to be formally accepted by some council or committee. The BIP Process does not have such a decision body. Bitcoin development and "acceptance" of BIPs emerges from the participation of stakeholders across the ecosystem, and refers to some vague notion of community interest and support for a proposal. BIP 2 had made an attempt to gather community feedback into comment summaries in BIPs directly. Given the low participation and corresponding low information quality of the summaries that resulted from that feature, this BIP instead intends to leave the evaluation of BIPs to the reviewers and users. [^adoption]: **Why does the BIPs repository no longer track adoption?** In the past, some BIPs maintained lists of projects that had implemented the BIP. These lists generated noise for subscribers of the repository, often listed implementations of questionable quality, and quickly grew outdated, therefore providing little value. The repository no longer tracks which projects have implemented BIPs. Instead, it is recommended that projects publish a list of the BIPs they implement. [^markdown]: **Which flavor of Markdown is allowed?** The author of this proposal has no opinion on Markdown flavors, but recommends that proposals stick to the basic Markdown syntax features commonly shared across Markdown dialects. [^living-documents]: **Why are Process BIPs living documents?** In the past years, the existing BIPs process has not always provided a clear approach to all situations. For example, the content of BIP 2 appears to have been penned especially with fork proposals in mind. It seems clear that Bitcoin development will evolve in many surprising ways in the future. Instead of mandating the effort of writing a new process document every time new situations arise, it seems preferable to allow the process to adapt to the concerns of the future in specific aspects. Therefore, Process BIPs are defined as living documents that remain open to amendment. If a Process BIP requires large modifications or even a complete overhaul, a new BIP should be preferred. [^new-BIP]: **Why should the specification of an implemented BIP no longer be changed?** After a Complete or Deployed BIP has been deployed by one or more implementations, breaking changes to the specification could lead to a situation where multiple "compliant" implementations fail at being interoperable, because they implemented different versions of the same BIP. Therefore, even changes to the specification of Complete BIPs should be avoided, but Deployed BIPs should never be subject to breaking changes to their specification. [^bip-announcements-to-list]: **Why are some BIP status changes announced to the mailing list?** The BIPs repository does not and cannot track who might be interested in or has deployed a BIP. While concerns were raised that making announcements to the Bitcoin Developer Mailing List would introduce unnecessary noise, our rationale is that 1) moving Complete and Deployed BIPs to the Closed status will be a rare occurrence, 2) status updates will usually not generate a lot of discussion, 3) while the mailing list should preferably only used for getting review for new BIPs, it is the only channel available to us that can be considered a public announcement to the audience of the BIPs repository: even if the authors, implementers, or other parties interested in a BIP do not see the announcement themselves, they may be made aware by someone that does see it. [^superseded-by-proposed-replacement]: **Why is Superseded-By replaced with Proposed-Replacement?** Reviewers asked who should get to decide whether a BIP is superseded in case of a disagreement among the authors of the original BIP, the authors of the new BIP, the editors, or the community? This is addressed by making the "Replaces" header part of the recommendation of the authors of the new document, and replacing the "Superseded-By" header with the "Proposed-Replacement" header that lists any proposals that recommend replacing the original document. [^proposes-to-replace]: **Why was "Replaces" retained instead of changing it to "Proposes-to-Replace"?** When one BIP proposes to supersede another, it is on the original BIP where things get complicated. The BIP is an author document, but depending on its progress through the workflow, it may meanwhile be co-owned by the community. Who may decide whether the original document should endorse a potential replacement BIP? Is it the original authors, the authors of the new proposal, the BIP Editors, some sort of community process, or a mix of all of the above? On the new BIP these problems don’t exist in the same manner. As it is freshly written, it is wholly owned by its authors. The community is not yet invested and the original BIP’s authors do not have a privileged role in determining the content of the new BIP. The authors of the new BIP can unilaterally recommend that it be considered a replacement for a prior BIP. From there, the community can evaluate the proposal and adopt or reject it, thus establishing whether it is successful in superseding the original or not. [^evidence]: **How is evidence for advancing to Deployed evaluated?** Whether evidence is deemed convincing to move a BIP to Deployed is up to the BIP Editors and Bitcoin community. Running a single instance of a personal fork of a software project might be rejected, while a small software project with dozens of users may be sufficient. The main point of the Deployed status is to indicate that changes to the BIP could negatively impact users of projects that have already implemented support. [^licenses]: **Why were some licenses dropped?** Among the 141 BIPs with licenses in the repository, only nine licenses have ever been used to license BIPs (although, some BIPs were made available under more than one license) and only one license has been used to license code: Licenses used: * BSD-2-Clause: 55 * PD: 42 * CC0-1.0: 23 * BSD-3-Clause: 19 * OPUBL-1.0: 5 * CC-BY-SA-4.0: 4 * FSFAP: 3 * MIT: 2 * CC-BY-4.0: 1 License-Code used (previous BIP2 format): * BSD-2-Clause: 1 * CC0-1.0: 1 * MIT: 5 The following previously acceptable licenses were retained per request of reviewers, even though they have so far never been used in the BIPs process: * Apache-2.0: [Apache License 2.0](https://www.apache.org/licenses/LICENSE-2.0) * BSL-1.0: [Boost Software License 1.0](https://www.boost.org/LICENSE_1_0.txt) The following previously acceptable licenses have never been used in the BIPs Process and have been dropped: * AGPL-3.0+: [GNU Affero General Public License (AGPL) 3](https://www.gnu.org/licenses/agpl-3.0.en.html) * FDL-1.3: [GNU Free Documentation License 1.3](https://www.gnu.org/licenses/fdl-1.3.en.html) * GPL-2.0+: [GNU General Public License (GPL) 2 or newer](https://www.gnu.org/licenses/old-licenses/gpl-2.0.en.html) * LGPL-2.1+: [GNU Lesser General Public License (LGPL) 2.1 or newer](https://www.gnu.org/licenses/old-licenses/lgpl-2.1.en.html) Why are software licenses included? * Some BIPs, in particular those concerning the consensus layer, may include literal code in the BIP itself which may not be available under the license terms the authors wish to use for the BIP. * The author of this BIP has been provided with a learned opinion indicating that software licenses are perfectly acceptable for licensing "human code" i.e., text as well as Markdown or MediaWiki code. Why is CC-BY-SA-4.0 no longer acceptable for new BIPs? * Specification BIPs are required to have a Reference Implementation and Test Vectors to be advanced to Complete. As the BIPs repository is aiming to make proposals easily adoptable, the intention is for the reference implementation and test vectors to be as accessible as possible. Copyleft licenses may introduce friction here, and therefore CC-BY-SA-4.0 (and the GPL-flavors) is no longer considered acceptable for new BIPs. As mentioned above, existing BIPs will retain their original licensing. Why are Open Publication License and Public Domain no longer acceptable for new BIPs? * Public domain is not universally recognised as a legitimate action, thus it is inadvisable. * The Open Publication License is generally regarded as obsolete, and not a license suitable for new publications. ================================================ FILE: bip-0008/assignments.mediawiki ================================================ ==Deployments== List of deployments. State can be defined, active, failed. Dates are in UTC. ================================================ FILE: bip-0008/states.dot ================================================ digraph { rankdir=TD; node [style="rounded,filled,bold", shape=box, fixedsize=true, width=1.5, fontname="Arial"]; edge [weight = 100]; "DEFINED" -> "STARTED" [label="height >= start_height"]; "STARTED" -> "MUST_SIGNAL" [label="height + 2016 >= timeoutheight AND lockinontimeout"]; "STARTED" -> "FAILED" [label="height >= timeoutheight\nAND\nNOT lockinontimeout"]; "LOCKED_IN" -> "ACTIVE" [label="height >= minimum_activation_height"]; "LOCKED_IN":se -> "LOCKED_IN":ne [label="height < minimum_activation_height"]; "MUST_SIGNAL" -> "LOCKED_IN" [label="always"]; edge [weight = 1]; "STARTED" -> "LOCKED_IN" [label="height < timeoutheight\nAND\nthreshold reached"]; "FAILED" -> "LOCKED_IN" [style=invis]; "DEFINED":sw -> "DEFINED":nw; "STARTED":sw -> "STARTED":nw; "ACTIVE":sw -> "ACTIVE":nw; "FAILED":sw -> "FAILED":nw; "STARTED" [fillcolor="#a0a0ff"]; "MUST_SIGNAL" [fillcolor="#a0a0ff"]; "LOCKED_IN" [fillcolor="#ffffa0"]; "ACTIVE" [fillcolor="#a0ffa0"]; "FAILED" [fillcolor="#ffa0a0"]; { rank=same; "STARTED" "MUST_SIGNAL" } { rank=same; "FAILED" "LOCKED_IN" } { rank=sink; "ACTIVE" } } ================================================ FILE: bip-0008.mediawiki ================================================
  BIP: 8
  Title: Version bits with lock-in by height
  Authors: Shaolin Fry 
           Luke Dashjr 
  Status: Draft
  Type: Informational
  Assigned: 2017-02-01
  License: BSD-3-Clause OR CC0-1.0
==Abstract== This document specifies an alternative to [[bip-0009.mediawiki|BIP9]] that corrects for a number of perceived mistakes. Block heights are used for start and timeout rather than POSIX timestamps. It additionally introduces an activation parameter that can guarantee activation of backward-compatible changes (further called "soft forks"). The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED", "MAY", and "OPTIONAL" in this document are to be interpreted as described in RFC 2119. ==Motivation== BIP9 introduced a mechanism for doing parallel soft forking deployments based on repurposing the block nVersion field. Activation is dependent on near unanimous hashrate signalling which may be impractical and result in veto by a small minority of non-signalling hashrate. Super majority hashrate based activation triggers allow for accelerated activation where the majority hash power enforces the new rules in lieu of full nodes upgrading. Since all consensus rules are ultimately enforced by full nodes, eventually any new soft fork will be enforced by the economy. This proposal combines these two aspects to provide optional flag day activation after a reasonable time, as well as for accelerated activation by majority of hash rate before the flag date. Due to using timestamps rather than block heights, it was found to be a risk that a sudden loss of significant hashrate could interfere with a late activation. Block time is somewhat unreliable and may be intentionally or unintentionally inaccurate, so thresholds based on block time are not ideal. Secondly, BIP9 specified triggers based on the first retarget after a given time, which is non-intuitive. Since each new block must increase the height by one, thresholds based on block height are much more reliable and intuitive and can be calculated exactly for difficulty retarget. ==Specification== ===Parameters=== Each soft fork deployment is specified by the following per-chain parameters (further elaborated below): # The '''name''' specifies a very brief description of the soft fork, reasonable for use as an identifier. # The '''bit''' determines which bit in the nVersion field of the block is to be used to signal the soft fork lock-in and activation. It is chosen from the set {0,1,2,...,28}. # The '''startheight''' specifies the height of the first block at which the bit gains its meaning. # The '''timeoutheight''' specifies a block height at which the miner signalling ends. Once this height has been reached, if the soft fork has not yet locked in (excluding this block's bit state), the deployment is considered failed on all descendants of the block. # The '''threshold''' specifies the minimum number of block per retarget period which indicate lock-in of the soft fork during the subsequent period. # The '''minimum_activation_height''' specifies the height of the first block at which the soft fork is allowed to become active. # The '''lockinontimeout''' boolean if set to true, blocks are required to signal in the final period, ensuring the soft fork has locked in by timeoutheight. ===Selection guidelines=== The following guidelines are suggested for selecting these parameters for a soft fork: # '''name''' should be selected such that no two softforks, concurrent or otherwise, ever use the same name. For deployments described in a single BIP, it is recommended to use the name "bipN" where N is the appropriate BIP number. # '''bit''' should be selected such that no two concurrent softforks use the same bit. The bit chosen should not overlap with active usage (legitimately or otherwise) for other purposes. # '''startheight''' should be set to some block height in the future. If '''minimum_activation_height''' is not going to be set, then '''startheight''' should be set to a height when a majority of economic activity is expected to have upgraded to software including the activation parameters. Some allowance should be made for potential release delays. If '''minimum_activation_height''' is going to be set, then '''startheight''' can be set to be soon after software with parameters is expected to be released. This shifts the time for upgrading from before signaling begins to during the LOCKED_IN state. # '''timeoutheight''' should be set to a block height when it is considered reasonable to expect the entire economy to have upgraded by, probably at least 1 year, or 52416 blocks (26 retarget intervals) after '''startheight'''. # '''threshold''' should be 1815 blocks (90% of 2016), or 1512 (75%) for testnet. # '''minimum_activation_height''' should be set to several retarget periods in the future if the '''startheight''' is to be very soon after software with parameters is expected to be released. '''minimum_activation_height''' should be set to a height when a majority of economic activity is expected to have upgraded to software including the activation parameters. This allows more time to be spent in the LOCKED_IN state so that nodes can upgrade. This may be set to 0 to have the LOCKED_IN state be a single retarget period. # '''lockinontimeout''' should be set to true for any softfork that is expected or found to have political opposition from a non-negligible percent of miners. (It can be set after the initial deployment, but cannot be cleared once set.) A later deployment using the same bit is possible as long as the startheight is after the previous one's timeoutheight or activation, but it is discouraged until necessary, and even then recommended to have a pause in between to detect buggy software. '''startheight''', '''timeoutheight''', and '''minimum_activation_height''' must be an exact multiple of 2016 (ie, at a retarget boundary), and '''timeoutheight''' must be at least 4032 blocks (2 retarget intervals) after '''startheight'''. ===States=== With each block and soft fork, we associate a deployment state. The possible states are: # '''DEFINED''' is the first state that each soft fork starts out as. The genesis block is by definition in this state for each deployment. # '''STARTED''' for blocks at or beyond the startheight. # '''MUST_SIGNAL''' for one retarget period prior to the timeout, if LOCKED_IN was not reached and '''lockinontimeout''' is true. # '''LOCKED_IN''' for at least one retarget period after the first retarget period with STARTED (or MUST_SIGNAL) blocks of which at least threshold have the associated bit set in nVersion. A soft fork remains in LOCKED_IN until at least '''minimum_activation_height''' is reached. # '''ACTIVE''' for all blocks after the LOCKED_IN state. # '''FAILED''' for all blocks after the timeoutheight if LOCKED_IN is not reached. ===Bit flags=== The nVersion block header field is to be interpreted as a 32-bit little-endian integer (as present), and bits are selected within this integer as values (1 << N) where N is the bit number. Blocks in the STARTED state get an nVersion whose bit position bit is set to 1. The top 3 bits of such blocks must be 001, so the range of actually possible nVersion values is [0x20000000...0x3FFFFFFF], inclusive. Due to the constraints set by BIP 34, BIP 66 and BIP 65, we only have 0x7FFFFFFB possible nVersion values available. This restricts us to at most 30 independent deployments. By restricting the top 3 bits to 001 we get 29 out of those for the purposes of this proposal, and support two future upgrades for different mechanisms (top bits 010 and 011). When a block nVersion does not have top bits 001, it is treated as if all bits are 0 for the purposes of deployments. Miners should continue setting the bit in LOCKED_IN phase so uptake is visible, though this has no effect on consensus rules. ===New consensus rules=== The new consensus rules for each soft fork are enforced for each block that has ACTIVE state. During the MUST_SIGNAL phase, if '''(2016 - threshold)''' blocks in the retarget period have already failed to signal, any further blocks that fail to signal are invalid. ===State transitions=== Note that when '''lockinontimeout''' is true, the LOCKED_IN state will be reached no later than at a height of '''timeoutheight'''. Regardless of the value of '''lockinontimeout''', if LOCKED_IN is reached, ACTIVE will be reached either one retarget period later, or at '''minimum_activation_height''', whichever comes later. The genesis block has state DEFINED for each deployment, by definition. State GetStateForBlock(block) { if (block.height == 0) { return DEFINED; } All blocks within a retarget period have the same state. This means that if floor(block1.height / 2016) = floor(block2.height / 2016), they are guaranteed to have the same state for every deployment. if ((block.height % 2016) != 0) { return GetStateForBlock(block.parent); } Otherwise, the next state depends on the previous state: switch (GetStateForBlock(GetAncestorAtHeight(block, block.height - 2016))) { We remain in the initial state until we reach the start block height. case DEFINED: if (block.height >= startheight) { return STARTED; } return DEFINED; After a period in the STARTED state, we tally the bits set, and transition to LOCKED_IN if a sufficient number of blocks in the past period set the deployment bit in their version numbers. If the threshold hasn't been met, lockinontimeout is true, and we are at the last period before the timeout, then we transition to MUST_SIGNAL. If the threshold hasn't been met and we reach the timeout, we transition directly to FAILED. Note that a block's state never depends on its own nVersion; only on that of its ancestors. case STARTED: int count = 0; walk = block; for (i = 0; i < 2016; i++) { walk = walk.parent; if (walk.nVersion & 0xE0000000 == 0x20000000 && (walk.nVersion >> bit) & 1 == 1) { ++count; } } if (count >= threshold) { return LOCKED_IN; } else if (lockinontimeout && block.height + 2016 >= timeoutheight) { return MUST_SIGNAL; } else if (block.height >= timeoutheight) { return FAILED; } return STARTED; If we have finished a period of MUST_SIGNAL, we transition directly to LOCKED_IN. case MUST_SIGNAL: return LOCKED_IN; After at least one retarget period of LOCKED_IN, we automatically transition to ACTIVE if the minimum activation height is reached. Otherwise LOCKED_IN continues. case LOCKED_IN: if (block.height >= minimum_activation_height) { return ACTIVE; } else { return LOCKED_IN; } And ACTIVE and FAILED are terminal states, which a deployment stays in once they're reached. case ACTIVE: return ACTIVE; case FAILED: return FAILED; } } '''Implementation''' It should be noted that the states are maintained along block chain branches, but may need recomputation when a reorganization happens. Given that the state for a specific block/deployment combination is completely determined by its ancestry before the current retarget period (i.e. up to and including its ancestor with height block.height - 1 - (block.height % 2016)), it is possible to implement the mechanism above efficiently and safely by caching the resulting state of every multiple-of-2016 block, indexed by its parent. ===Mandatory signalling=== Blocks received while in the MUST_SIGNAL phase must be checked to ensure that they signal as required. For example: if (GetStateForBlock(block) == MUST_SIGNAL) { int nonsignal = 0; walk = block; while (true) { if ((walk.nVersion & 0xE0000000) != 0x20000000 || ((walk.nVersion >> bit) & 1) != 1) { ++nonsignal; if (nonsignal > 2016 - threshold) { return state.Invalid(BlockValidationResult::RECENT_CONSENSUS_CHANGE, "bad-version-bip8-must-signal"); } } if (walk.nHeight % 2016 == 0) { // checked every block in this retarget period break; } walk = walk.parent; } } Implementations should be careful not to ban peers that send blocks that are invalid due to not signalling (or blocks that build on those blocks), as that would allow an incompatible chain that is only briefly longer than the compliant chain to cause a split of the p2p network. If that occurred, nodes that have not set ''lockinontimeout'' may not see new blocks in the compliant chain, and thus not reorg to it at the point when it has more work, and would thus not be following the valid chain with the most work. Implementations with ''lockinontimeout'' set to true may potentially follow a lower work chain than nodes with ''lockinontimeout'' set to false for an extended period. In order for this not to result in a net split nodes with ''lockinontimeout'' set to true, those nodes may need to preferentially connect to each other. Deployments proposing that implementations set ''lockinontimeout'' to true should either use parameters that do not risk there being a higher work alternative chain, or specify a mechanism for implementations that support the deployment to preferentially peer with each other. ===Warning mechanism=== To support upgrade warnings, an extra "unknown upgrade" is tracked, using the "implicit bit" mask = (block.nVersion & ~expectedVersion) != 0. Mask will be non-zero whenever an unexpected bit is set in nVersion. Whenever LOCKED_IN for the unknown upgrade is detected, the software should warn loudly about the upcoming soft fork. It should warn even more loudly after the next retarget period (when the unknown upgrade is in the ACTIVE state). ===getblocktemplate changes=== The template request Object is extended to include a new item: {| class="wikitable" !colspan=4| template request |- ! Key !! Required !! Type !! Description |- | rules || No || Array of Strings || list of supported softfork deployments, by name |} The template Object is also extended: {| class="wikitable" !colspan=4| template |- ! Key !! Required !! Type !! Description |- | rules || Yes || Array of Strings || list of softfork deployments, by name, that are active state |- | vbavailable || Yes || Object || set of pending, supported softfork deployments; each uses the softfork name as the key, and the softfork bit as its value |- | vbrequired || No || Number || bit mask of softfork deployment version bits the server requires enabled in submissions |} The "version" key of the template is retained, and used to indicate the server's preference of deployments. If versionbits is being used, "version" MUST be within the versionbits range of [0x20000000...0x3FFFFFFF]. Miners MAY clear or set bits in the block version WITHOUT any special "mutable" key, provided they are listed among the template's "vbavailable" and (when clearing is desired) NOT included as a bit in "vbrequired". Servers MUST set bits in "vbrequired" for deployments in MUST_SIGNAL state, to ensure blocks produced are valid. Softfork deployment names listed in "rules" or as keys in "vbavailable" may be prefixed by a '!' character. Without this prefix, GBT clients may assume the rule will not impact usage of the template as-is; typical examples of this would be when previously valid transactions cease to be valid, such as BIPs 16, 65, 66, 68, 112, and 113. If a client does not understand a rule without the prefix, it may use it unmodified for mining. On the other hand, when this prefix is used, it indicates a more subtle change to the block structure or generation transaction; examples of this would be BIP 34 (because it modifies coinbase construction) and 141 (since it modifies the txid hashing and adds a commitment to the generation transaction). A client that does not understand a rule prefixed by '!' must not attempt to process the template, and must not attempt to use it for mining even unmodified. === Reference implementation === https://github.com/bitcoin/bitcoin/compare/master...luke-jr:bip8 ==Contrasted with BIP 9== * The '''lockinontimeout''' flag is added, providing a way to guarantee transition to LOCKED_IN. * Block heights are used for the deployment monotonic clock, rather than median-time-past. ==Backwards compatibility== BIP8 and BIP9 deployments should not share concurrent active deployment bits. Nodes that only implement BIP9 will not activate a BIP8 soft fork if hashpower threshold is not reached by '''timeoutheight''', however, those nodes will still accept the blocks generated by activated nodes. ==Deployments== A living list of deployment proposals can be found [[bip-0008/assignments.mediawiki|here]]. ==References== [[bip-0009.mediawiki|BIP9]] [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2017-February/013643.html Mailing list discussion] ==Copyright== This document is dual licensed as BSD 3-clause, and Creative Commons CC0 1.0 Universal. ================================================ FILE: bip-0009/assignments.mediawiki ================================================ ==Deployments== List of proposed deployments. State can be defined, active, failed. Dates are in UTC. {| class="wikitable sortable" ! Name ! Bit ! Mainnet Start ! Mainnet Expire ! Mainnet State ! Testnet Start ! Testnet Expire ! Testnet State ! BIPs |- | csv | 0 | 2016-05-01 00:00:00 | 2017-05-01 00:00:00 | active since #419328 | 2016-03-01 00:00:00 | 2017-05-01 00:00:00 | active since #770112 | [[/bip-0068.mediawiki|68]], [[/bip-0112.mediawiki|112]], [[/bip-0113.mediawiki|113]] |- | segwit | 1 | 2016-11-15 00:00:00 | 2017-11-15 00:00:00 | active since #481824 | 2016-05-01 00:00:00 | 2017-05-01 00:00:00 | active since #834624 | [[/bip-0141.mediawiki|141]], [[/bip-0143.mediawiki|143]], [[/bip-0147.mediawiki|147]] |} ================================================ FILE: bip-0009/states.gv ================================================ /* There are many ways to compile this, but one of them is: * * $ dot -Tpng states.gv -o states.png */ digraph { /* States. */ DEFINED; FAILED; STARTED; LOCKED_IN; ACTIVE; /* Relationships between states, labeled where applicable. */ DEFINED -> DEFINED; DEFINED -> FAILED [label = "timeout ≤ MTP"]; DEFINED -> STARTED [label = "starttime ≤ MTP < timeout"]; FAILED -> FAILED; STARTED -> STARTED; STARTED -> FAILED [label = "timeout ≤ MTP"]; STARTED -> LOCKED_IN [label = "(MTP < timeout) AND (threshold reached)"]; LOCKED_IN -> ACTIVE [label = "Always"]; ACTIVE -> ACTIVE; /* Visualization hack to unclutter output. */ nodesep = 1.2; } ================================================ FILE: bip-0009.mediawiki ================================================
  BIP: 9
  Title: Version bits with timeout and delay
  Authors: Pieter Wuille 
           Peter Todd 
           Greg Maxwell 
           Rusty Russell 
  Status: Deployed
  Type: Informational
  Assigned: 2015-10-04
  License: PD
==Abstract== This document specifies a proposed change to the semantics of the 'version' field in Bitcoin blocks, allowing multiple backward-compatible changes (further called "soft forks") to be deployed in parallel. It relies on interpreting the version field as a bit vector, where each bit can be used to track an independent change. These are tallied each retarget period. Once the consensus change succeeds or times out, there is a "fallow" pause after which the bit can be reused for later changes. ==Motivation== [[bip-0034.mediawiki|BIP 34]] introduced a mechanism for doing soft-forking changes without a predefined flag timestamp (or flag block height), instead relying on measuring miner support indicated by a higher version number in block headers. As it relies on comparing version numbers as integers however, it only supports one single change being rolled out at once, requiring coordination between proposals, and does not allow for permanent rejection: as long as one soft fork is not fully rolled out, no future one can be scheduled. In addition, BIP 34 made the integer comparison (nVersion >= 2) a consensus rule after its 95% threshold was reached, removing 231+2 values from the set of valid version numbers (all negative numbers, as nVersion is interpreted as a signed integer, as well as 0 and 1). This indicates another downside this approach: every upgrade permanently restricts the set of allowed nVersion field values. This approach was later reused in [[bip-0066.mediawiki|BIP 66]] and [[bip-0065.mediawiki|BIP 65]], which further removed nVersions 2 and 3 as valid options. As will be shown further, this is unnecessary. ==Specification== Each soft fork deployment is specified by the following per-chain parameters (further elaborated below): # The '''name''' specifies a very brief description of the soft fork, reasonable for use as an identifier. For deployments described in a single BIP, it is recommended to use the name "bipN" where N is the appropriate BIP number. # The '''bit''' determines which bit in the nVersion field of the block is to be used to signal the soft fork lock-in and activation. It is chosen from the set {0,1,2,...,28}. # The '''starttime''' specifies a minimum median time past of a block at which the bit gains its meaning. # The '''timeout''' specifies a time at which the deployment is considered failed. If the median time past of a block >= timeout and the soft fork has not yet locked in (including this block's bit state), the deployment is considered failed on all descendants of the block. ===Selection guidelines=== The following guidelines are suggested for selecting these parameters for a soft fork: # '''name''' should be selected such that no two softforks, concurrent or otherwise, ever use the same name. # '''bit''' should be selected such that no two concurrent softforks use the same bit. # '''starttime''' should be set to some date in the future, approximately one month after a software release date including the soft fork. This allows for some release delays, while preventing triggers as a result of parties running pre-release software. # '''timeout''' should be 1 year (31536000 seconds) after starttime. A later deployment using the same bit is possible as long as the starttime is after the previous one's timeout or activation, but it is discouraged until necessary, and even then recommended to have a pause in between to detect buggy software. ===States=== With each block and soft fork, we associate a deployment state. The possible states are: # '''DEFINED''' is the first state that each soft fork starts out as. The genesis block is by definition in this state for each deployment. # '''STARTED''' for blocks past the starttime. # '''LOCKED_IN''' for one retarget period after the first retarget period with STARTED blocks of which at least threshold have the associated bit set in nVersion. # '''ACTIVE''' for all blocks after the LOCKED_IN retarget period. # '''FAILED''' for one retarget period past the timeout time, if LOCKED_IN was not reached. ===Bit flags=== The nVersion block header field is to be interpreted as a 32-bit little-endian integer (as present), and bits are selected within this integer as values (1 << N) where N is the bit number. Blocks in the STARTED state get an nVersion whose bit position bit is set to 1. The top 3 bits of such blocks must be 001, so the range of actually possible nVersion values is [0x20000000...0x3FFFFFFF], inclusive. Due to the constraints set by BIP 34, BIP 66 and BIP 65, we only have 0x7FFFFFFB possible nVersion values available. This restricts us to at most 30 independent deployments. By restricting the top 3 bits to 001 we get 29 out of those for the purposes of this proposal, and support two future upgrades for different mechanisms (top bits 010 and 011). When a block nVersion does not have top bits 001, it is treated as if all bits are 0 for the purposes of deployments. Miners should continue setting the bit in LOCKED_IN phase so uptake is visible, though this has no effect on consensus rules. ===New consensus rules=== The new consensus rules for each soft fork are enforced for each block that has ACTIVE state. ===State transitions=== The genesis block has state DEFINED for each deployment, by definition. State GetStateForBlock(block) { if (block.height == 0) { return DEFINED; } All blocks within a retarget period have the same state. This means that if floor(block1.height / 2016) = floor(block2.height / 2016), they are guaranteed to have the same state for every deployment. if ((block.height % 2016) != 0) { return GetStateForBlock(block.parent); } Otherwise, the next state depends on the previous state: switch (GetStateForBlock(GetAncestorAtHeight(block, block.height - 2016))) { We remain in the initial state until either we pass the start time or the timeout. GetMedianTimePast in the code below refers to the median nTime of a block and its 10 predecessors. The expression GetMedianTimePast(block.parent) is referred to as MTP in the diagram above, and is treated as a monotonic clock defined by the chain. case DEFINED: if (GetMedianTimePast(block.parent) >= timeout) { return FAILED; } if (GetMedianTimePast(block.parent) >= starttime) { return STARTED; } return DEFINED; After a period in the STARTED state, if we're past the timeout, we switch to FAILED. If not, we tally the bits set, and transition to LOCKED_IN if a sufficient number of blocks in the past period set the deployment bit in their version numbers. The threshold is ≥1916 blocks (95% of 2016), or ≥1512 for testnet (75% of 2016). The transition to FAILED takes precedence, as otherwise an ambiguity can arise. There could be two non-overlapping deployments on the same bit, where the first one transitions to LOCKED_IN while the other one simultaneously transitions to STARTED, which would mean both would demand setting the bit. Note that a block's state never depends on its own nVersion; only on that of its ancestors. case STARTED: if (GetMedianTimePast(block.parent) >= timeout) { return FAILED; } int count = 0; walk = block; for (i = 0; i < 2016; i++) { walk = walk.parent; if (walk.nVersion & 0xE0000000 == 0x20000000 && (walk.nVersion >> bit) & 1 == 1) { count++; } } if (count >= threshold) { return LOCKED_IN; } return STARTED; After a retarget period of LOCKED_IN, we automatically transition to ACTIVE. case LOCKED_IN: return ACTIVE; And ACTIVE and FAILED are terminal states, which a deployment stays in once they're reached. case ACTIVE: return ACTIVE; case FAILED: return FAILED; } } '''Implementation''' It should be noted that the states are maintained along block chain branches, but may need recomputation when a reorganization happens. Given that the state for a specific block/deployment combination is completely determined by its ancestry before the current retarget period (i.e. up to and including its ancestor with height block.height - 1 - (block.height % 2016)), it is possible to implement the mechanism above efficiently and safely by caching the resulting state of every multiple-of-2016 block, indexed by its parent. ===Warning mechanism=== To support upgrade warnings, an extra "unknown upgrade" is tracked, using the "implicit bit" mask = (block.nVersion & ~expectedVersion) != 0. Mask will be non-zero whenever an unexpected bit is set in nVersion. Whenever LOCKED_IN for the unknown upgrade is detected, the software should warn loudly about the upcoming soft fork. It should warn even more loudly after the next retarget period (when the unknown upgrade is in the ACTIVE state). ===getblocktemplate changes=== The template request Object is extended to include a new item: {| class="wikitable" !colspan=4| template request |- ! Key !! Required !! Type !! Description |- | rules || No || Array of Strings || list of supported softfork deployments, by name |} The template Object is also extended: {| class="wikitable" !colspan=4| template |- ! Key !! Required !! Type !! Description |- | rules || Yes || Array of Strings || list of softfork deployments, by name, that are active state |- | vbavailable || Yes || Object || set of pending, supported softfork deployments; each uses the softfork name as the key, and the softfork bit as its value |- | vbrequired || No || Number || bit mask of softfork deployment version bits the server requires enabled in submissions |} The "version" key of the template is retained, and used to indicate the server's preference of deployments. If versionbits is being used, "version" MUST be within the versionbits range of [0x20000000...0x3FFFFFFF]. Miners MAY clear or set bits in the block version WITHOUT any special "mutable" key, provided they are listed among the template's "vbavailable" and (when clearing is desired) NOT included as a bit in "vbrequired". Softfork deployment names listed in "rules" or as keys in "vbavailable" may be prefixed by a '!' character. Without this prefix, GBT clients may assume the rule will not impact usage of the template as-is; typical examples of this would be when previously valid transactions cease to be valid, such as BIPs [[bip-0016.mediawiki|16]], [[bip-0065.mediawiki|65]], [[bip-0066.mediawiki|66]], [[bip-0068.mediawiki|68]], [[bip-0112.mediawiki|112]], and [[bip-0113.mediawiki|113]]. If a client does not understand a rule without the prefix, it may use it unmodified for mining. On the other hand, when this prefix is used, it indicates a more subtle change to the block structure or generation transaction; examples of this would be [[bip-0034.mediawiki|BIP 34]] (because it modifies coinbase construction) and [[bip-0141.mediawiki|141]] (since it modifies the txid hashing and adds a commitment to the generation transaction). A client that does not understand a rule prefixed by '!' must not attempt to process the template, and must not attempt to use it for mining even unmodified. ==Support for future changes== The mechanism described above is very generic, and variations are possible for future soft forks. Here are some ideas that can be taken into account. '''Modified thresholds''' The 1916 threshold (based on BIP 34's 95%) does not have to be maintained for eternity, but changes should take the effect on the warning system into account. In particular, having a lock-in threshold that is incompatible with the one used for the warning system may have long-term effects, as the warning system cannot rely on a permanently detectable condition anymore. '''Conflicting soft forks''' At some point, two mutually exclusive soft forks may be proposed. The naive way to deal with this is to never create software that implements both, but that is making a bet that at least one side is guaranteed to lose. Better would be to encode "soft fork X cannot be locked-in" as consensus rule for the conflicting soft fork - allowing software that supports both, but can never trigger conflicting changes. '''Multi-stage soft forks''' Soft forks right now are typically treated as booleans: they go from an inactive to an active state in blocks. Perhaps at some point there is demand for a change that has a larger number of stages, with additional validation rules that get enabled one by one. The above mechanism can be adapted to support this, by interpreting a combination of bits as an integer, rather than as isolated bits. The warning system is compatible with this, as (nVersion & ~nExpectedVersion) will always be non-zero for increasing integers. == Rationale == The failure timeout allows eventual reuse of bits even if a soft fork was never activated, so it's clear that the new use of the bit refers to a new BIP. It's deliberately very coarse-grained, to take into account reasonable development and deployment delays. There are unlikely to be enough failed proposals to cause a bit shortage. The fallow period at the conclusion of a soft fork attempt allows some detection of buggy clients, and allows time for warnings and software upgrades for successful soft forks. ==Deployments== A living list of deployment proposals can be found [[bip-0009/assignments.mediawiki|here]]. ==Copyright== This document is placed in the public domain. ================================================ FILE: bip-0010.mediawiki ================================================
  BIP: 10
  Layer: Applications
  Title: Multi-Sig Transaction Distribution
  Authors: Alan Reiner 
  Status: Closed
  Type: Informational
  Assigned: 2011-10-28
A multi-signature transaction is one where a certain number of Bitcoins are "encumbered" with more than one recipient address. The subsequent transaction that spends these coins will require each party involved (or some subset, depending on the script), to see the proposed transaction and sign it with their private key. This necessarily requires collaboration between all parties -- to propose a distribution of encumbered funds, collect signatures from all necessary participants, and then broadcast the completed transaction. This BIP describes a way standardize the encoding of proposal transactions, to assist with signature collection and broadcast (which includes regular, 1-of-1 transactions requiring signatures from an offline computer). The goal is to encourage a standard that guarantees interoperability of all programs that implement it. ==Motivation== The enabling of multi-signature transactions in Bitcoin will introduce a great deal of extra functionality to the users of the network, but also a great deal of extra complexity. Executing a multi-signature tx will be a multi-step process, and will potentially get worse with multiple clients, each implementing this process differently. By providing an efficient, standardized technique, we can improve the chance that developers will adopt compatible protocols and not bifurcate the user-base based on client selection. In addition to providing a general encoding scheme for transaction signing/collection, it does not require the signing device to hold any blockchain information (all information needed for verification and signing is part of the encoding). This enables the existence of very lightweight devices that can be used for signing since they do not need the blockchain -- only a minimal set of Bitcoin tools and an ECDSA module. Therefore, BIP 0010 has benefit beyond just multi-signature transactions. ==Specification== This BIP proposes the following process, with terms in quotes referring to recommended terminology that should be encouraged across all implementations. # One party will initiate this process by creating a "Distribution Proposal", which could be abbreviated DP, or TxDP # The user creating the TxDP (the preparer) will create the transaction as they would like to see it spent, but with blank TxIn scripts (where the signatures scripts will eventually go). # The proposed transaction will be spending a set of unspent TxOuts available in the blockchain. The full transactions containing these TxOuts will be serialized and included, as well. This so that the values of the TxIns can be verified before signing (the prev-tx-hash is part of the data being signed, but the value is not). By including the full tx, the signing party can verify that the tx matches the OutPoint hash, and then verify input values, all without any access to the blockchain. # The TxDP will have an "DP ID" or "Unsigned ID" which is the hash of the proposed transaction with blanked scripts, in Base58. This is a specific naming convention to make sure it is not confused with the actual transaction ID that it will have after it is broadcast (the transaction ID cannot be determined until after all signatures are collected). The final Tx ID can be referred to as its "Broadcast ID", in order to distinguish it from the pre-signed ID. # The TxDP will have a potentially-unordered list of sig-pubkey pairs which represent collected signatures. If you receive a TxDP missing only your signature, you can broadcast it as soon as you sign it. # Identical TxDP objects with different signatures can be easily combined. This allows one party to send out all the requests for signatures at once, and combine them all when they are received (instead of having to "pass it around". # For cases where the TxDP might be put into a file or sent via email, it should use .txdp or .btcdp suffix Anyone adopting BIP 0010 for multi-sig transactions will use the following format (without indentation):
 '-----BEGIN-TRANSACTION-TXDPID-------'
 ("_TXDIST_") (magicBytes) (base58Txid) (varIntTxSize)
    (serializedTxListInHex_Line1)
    (serializedTxListInHex_Line2)
    (serializedTxListInHex_Line3)
    ...
 ("_TXINPUT_") (00) (InputValue)
    ("_SIG_") (AddrBase58) (SigBytes) (SigHexPart0)
    (SigHexRemainingLines)
    ("_SIG_") (AddrBase58) (SigBytes) (SigHexPart0)
    (SigHexRemainingLines)
 ("_TXINPUT_") (01) (InputValue)
    ("_SIG_") (AddrBase58) (SigBytes) (SigHexPart0)
    (SigHexRemainingLines)
 ("_TXINPUT_") (02) (InputValue)
 '-------END-TRANSACTION-TXDPID-------'
The following is an example TxDP from Armory, produced while running on the test network. Its DPID is 3fX59xPj: -----BEGIN-TRANSACTION-3fX59xPj------------------------------------------------- _TXDIST_fabfb5da_3fX59xPj_00a0 010000000292807c8e70a28c687daea2998d6273d074e56fa8a55a0b10556974cf2b526e61000000 0000ffffffffe3c1ee0711611b01af3dee55b1484f0d6b65d17dce4eff0e6e06242e6cf457e10000 000000ffffffff02b0feea0b000000001976a91457996661391fa4e95bed27d7e8fe47f47cb8e428 88ac00a0acb9030000001976a914dc504e07b1107110f601fb679dd3f56cee9ff71e88ac00000000 0100000001eb626e4f73d88f415a8e8cb32b8d73eed47aa1039d0ed2f013abdc741ce6828c010000 008c493046022100b0da540e4924518f8989a9da798ca2d9e761b69a173b8cc41a3e3e3c6d77cd50 022100ecfa61730e58005338420516744ef680428dcfc05022dec70a851365c8575b190141042dc5 be3afa5887aee4a377032ed014361b0b9b61eb3ea6b8a8821bfe13ee4b65cd25d9630e4f227a53e8 bf637f85452c9981bcbd64ef77e22ce97b0f547c783effffffff0200d6117e030000001976a914cf f580fd243f64f0ad7bf69faf41c0bf42d86d8988ac00205fa0120000001976a9148d573ef6984fd9 f8847d420001f7ac49b222a24988ac000000000100000001f2782db40ae147398a31cff9c7cc3423 014a073a92e463741244330cc304168f000000008c493046022100c9311b9eef0cc69219cb96838f dd621530a80c46269a00dccc66498bc03ccf7a0221003742ee652a0a76fd28ad81aa73bb7f7a0a6a 81850af58f62d9a184d10e5eec30014104f815e8ef4cad584e04974889d7636e8933803d2e72991d b5288c9e953c2465533905f98b7b688898c7c1f0708f2e49f0dd0abc06859ffed5144e8a1018a4e8 63ffffffff02008c8647000000001976a914d4e211215967f8e3744693bf85f47eb4ee9567fc88ac 603d4e95010000001976a914e9a6b50901c1969d2b0fd43a3ccfa3fef3291efe88ac00000000 _TXINPUT_00_150.00000000 _SIG_mzUYGfqGpyXmppYpmWJ31Y4zTxR4ZCod22_00_008c 4930460221007699967c3ec09d072599558d2e7082fae0820206b63aa66afea124634ed11a080221 0003346f7e963e645ecae2855026dc7332eb7237012539b34cd441c3cef97fbd4d01410497d5e1a0 0e1db90e893d1f2e547e2ee83b5d6bf4ddaa3d514e6dc2d94b6bcb5a72be1fcec766b8c382502caa 9ec09fe478bad07d3f38ff47b2eb42e681c384cc _TXINPUT_01_12.00000000 _SIG_mzvaN8JUhHLz3Gdec1zBRxs5rNaYLQnbD1_01_008c 49304602210081554f8b08a1ad8caa69e34f4794d54952dac7c5efcf2afe080985d6bd5b00770221 00dea20ca3dbae1d15ec61bec57b4b8062e7d7c47614aba032c5a32f651f471cfd014104c30936d2 456298a566aa76fefeab8a7cb7a91e8a936a11757c911b4c669f0434d12ab0936fc13986b156156f 9b389ed244bbb580112be07dbe23949a4764dffb -------END-TRANSACTION-3fX59xPj------------------------------------------------- In this transaction, there are two inputs, one of 150 BTC and the other of 12 BTC. This transaction combines 162 BTC to create two outputs, one of 160 BTC, one 1.9995 BTC, and a tx fee of 0.0005. In this TxDP, both inputs have been signed, and thus could broadcast immediately. The style of communication is taken directly from PGP/GPG, which uses blocks of ASCII like this to communicate encrypted messages and signatures. This serialization is compact, and will be interpreted the same in all character encodings. It can be copied inline into an email, or saved in a text file. The advantage over the analogous PGP encoding is that there are some human readable elements to it, for users that wish to examine the TxDP packet manually, instead of requiring a program to parse the core elements of the TxDP. A party receiving this TxDP can simply add their signature to the appropriate _TXINPUT_ line. If that is the last signature required, they can broadcast it themselves. Any software that implements this standard should be able to combine multiple TxDPs into a single TxDP. However, even without the programmatic support, a user could manually combine them by copying the appropriate _SIG_ lines between serializations, though it is not the recommended method for combining TxDPs. == Reference Implementation == This proposal was implemented and tested in the older versions of ''Armory'' Bitcoin software for use in offline-wallet transaction signing (as a 1-of-1 transaction). Implementation can be found in https://github.com/etotheipi/BitcoinArmory/blob/v0.91-beta/armoryengine/Transaction.py under the class PyTxDistProposal. However, as of version 0.92 released in July 2014, Armory no longer uses this proposal for offline wallet transaction signing and has moved on to a new format. ================================================ FILE: bip-0011.mediawiki ================================================
  BIP: 11
  Layer: Applications
  Title: M-of-N Standard Transactions
  Authors: Gavin Andresen 
  Status: Deployed
  Type: Specification
  Assigned: 2011-10-18
  Discussion: 2011-10-02
==Abstract== This BIP proposes M-of-N-signatures required transactions as a new 'standard' transaction type. ==Motivation== Enable secured wallets, escrow transactions, and other use cases where redeeming funds requires more than a single signature. A couple of motivating use cases: * A wallet secured by a "wallet protection service" (WPS). 2-of-2 signatures required transactions will be used, with one signature coming from the (possibly compromised) computer with the wallet and the second signature coming from the WPS. When sending protected bitcoins, the user's bitcoin client will contact the WPS with the proposed transaction and it can then contact the user for confirmation that they initiated the transaction and that the transaction details are correct. Details for how clients and WPS's communicate are outside the scope of this BIP. Side note: customers should insist that their wallet protection service provide them with copies of the private key(s) used to secure their wallets that they can safely store off-line, so that their coins can be spent even if the WPS goes out of business. * Three-party escrow (buyer, seller, and trusted dispute agent). 2-of-3 signatures required transactions will be used. The buyer and seller and agent will each provide a public key, and the buyer will then send coins into a 2-of-3 CHECKMULTISIG transaction and send the seller and the agent the transaction id. The seller will fulfill their obligation and then ask the buyer to co-sign a transaction ( already signed by seller ) that sends the tied-up coins to him (seller).
If the buyer and seller cannot agree, then the agent can, with the cooperation of either buyer or seller, decide what happens to the tied-up coins. Details of how buyer, seller, and agent communicate to gather signatures or public keys are outside the scope of this BIP. ==Specification== A new standard transaction type (scriptPubKey) that is relayed by clients and included in mined blocks: m {pubkey}...{pubkey} n OP_CHECKMULTISIG But only for n less than or equal to 3. OP_CHECKMULTISIG transactions are redeemed using a standard scriptSig: OP_0 ...signatures... (OP_0 is required because of a bug in OP_CHECKMULTISIG; it pops one too many items off the execution stack, so a dummy value must be placed on the stack). The current Satoshi bitcoin client does not relay or mine transactions with scriptSigs larger than 200 bytes; to accommodate 3-signature transactions, this will be increased to 500 bytes. ==Rationale== OP_CHECKMULTISIG is already an enabled opcode, and is the most straightforward way to support several important use cases. One argument against using OP_CHECKMULTISIG is that old clients and miners count it as "20 sigops" for purposes of computing how many signature operations are in a block, and there is a hard limit of 20,000 sigops per block-- meaning a maximum of 1,000 multisig transactions per block. Creating multisig transactions using multiple OP_CHECKSIG operations allows more of them per block. The counter-argument is that these new multi-signature transactions will be used in combination with OP_EVAL (see the OP_EVAL BIP), and '''will''' be counted accurately. And in any case, as transaction volume rises the hard-coded maximum block size will have to be addressed, and the rules for counting number-of-signature-operations-in-a-block can be addressed at that time. A weaker argument is OP_CHECKMULTISIG should not be used because it pops one too many items off the stack during validation. Adding an extra OP_0 placeholder to the scriptSig adds only 1 byte to the transaction, and any alternative that avoids OP_CHECKMULTISIG adds at least several bytes of opcodes. ==Implementation== OP_CHECKMULTISIG is already supported by old clients and miners as a non-standard transaction type. https://github.com/gavinandresen/bitcoin-git/tree/77f21f1583deb89bf3fffe80fe9b181fedb1dd60 == Post History == * [https://bitcointalk.org/index.php?topic=46538 OP_EVAL proposal] ================================================ FILE: bip-0012.mediawiki ================================================
  BIP: 12
  Layer: Consensus (soft fork)
  Title: OP_EVAL
  Authors: Gavin Andresen 
  Status: Closed
  Type: Specification
  Assigned: 2011-10-18
==Abstract== This BIP describes a new opcode (OP_EVAL) for the [https://en.bitcoin.it/wiki/Script Bitcoin scripting system], and a new 'standard' transaction type that uses it to enables the receiver of bitcoins to specify the transaction type needed to re-spend them. ==Motivation== Enable "end-to-end" secure wallets and payments to fund escrow transactions or other complex transactions in a way that is backwards-compatible for old clients and miners. ==Specification== OP_EVAL will re-define the existing OP_NOP1 opcode, and will function as follows: * When executed during transaction verification, pops the item from the top of the stack, deserializes it, and executes the resulting script. * If there is no item on the top of the stack or the item is not a valid script then transaction validation fails. * If there are any OP_CODESEPARATORs in the deserialized script then transaction validation fails. * If there are any OP_EVALs in the deserialized script they are also executed, but recursion is limited to a depth of 2. * Transaction verification must fail if interpreting OP_EVAL as a no-op would cause the verification to fail. A new standard transaction type (scriptPubKey) that is relayed by clients and included in mined blocks is also defined: DUP HASH160 {20-byte-hash-value} EQUALVERIFY OP_EVAL Which is redeemed by a standard scriptSig: ...signatures... {serialized script} Transactions that redeem standard OP_EVAL scriptPubKeys are only considered standard if the ''serialized script'' is, itself, one of the standard transaction types. ==Rationale== OP_EVAL allows the receiver of bitcoins to specify how they can be spent when they are spent, instead of requiring the sender of the bitcoins to know the details of how the bitcoins may be redeemed. The sender only needs to know the hash of the ''serialized script'', and one new type of bitcoin address can be used to fund arbitrarily complex transactions. If ''serialized script'' is a large or complicated multi-signature script, then the burden of paying for it (in increased transaction fees due to more signature operations or transaction size) is shifted from the sender to the receiver. The main objection to OP_EVAL is that it adds complexity, and complexity is the enemy of security. Also, evaluating data as code has a long record of being a source of security vulnerabilities. That same argument can be applied to the existing Bitcoin 'scripting' system; scriptPubKeys are transmit as data across the network and are then interpreted by every bitcoin implementation. OP_EVAL just moves the data that will be interpreted. It is debatable whether or not the entire idea of putting a little interpreted expression evaluation language at the core of Bitcoin was brilliant or stupid, but the existence of OP_EVAL does not make the expression language less secure. There is a 1-confirmation attack on old clients that interpret OP_EVAL as a no-op, but it is expensive and difficult in practice. The attack is: # Attacker creates an OP_EVAL transaction that is valid as seen by old clients, but invalid for new clients. # Attacker also creates a standard transaction that spends the OP_EVAL transaction, and pays the victim. # Attacker manages to mine a block that contains both transactions. If the victim accepts the 1-confirmation payment, then the attacker wins because both transactions will be invalidated when the rest of the network overwrites the attacker's invalid block. The attack is expensive because it requires the attacker create a block that they know will be invalidated. It is difficult because bitcoin businesses should not accept 1-confirmation transactions for higher-value transactions. ==Backwards Compatibility== Surprisingly, because OP_EVAL redefines the OP_NOP1 opcode, standard OP_EVAL transactions will validate with old clients and miners. They will check only that the ''serialized script'' hashes to the correct value; the OP_EVAL will be interpreted as a no-op, and as long as the hash is correct the transaction will be considered valid (no signature checking will be done by old clients and miners). Old clients will ignore OP_EVAL transactions and transactions that depend on them until they are put into a block by either an old miner that includes non-standard transactions in its blocks or by a new miner. Avoiding a block-chain split by malicious OP_EVAL transactions requires careful handling of two cases: # An OP_EVAL transaction that is invalid for new clients/miners but valid for old clients/miners. # An OP_EVAL transaction that is valid for new clients/miners but invalid for old clients/miners. For case (1), new clients and miners will be coded to interpret OP_EVAL as a no-op until February 1, 2012. Before then, miners will be asked to put the string "OP_EVAL" in blocks that they produce so that hashing power that supports the new opcode can be gauged. If less than 50% of miners accept the change as of January 15, 2012 the rollout will be postponed until more than 50% of hashing power supports OP_EVAL (the rollout will be rejected if it becomes clear that a majority of hashing power will not be achieved). For case (2), new clients and miners will be written to make sure that transactions involving OP_EVAL are valid if OP_EVAL is interpreted as a no-op. Example of a transaction that must fail for both old and new miners/clients: scriptSig: {serialized OP_11} scriptPubKey: OP_EVAL OP_11 OP_EQUAL ==Reference Implementation== https://github.com/gavinandresen/bitcoin-git/tree/77f21f1583deb89bf3fffe80fe9b181fedb1dd60 ==See Also== https://bitcointalk.org/index.php?topic=46538 "Bitcoin Address 01" BIP M-of-N Multisignature Transactions BIP 11 ================================================ FILE: bip-0013.mediawiki ================================================
  BIP: 13
  Layer: Applications
  Title: Address Format for pay-to-script-hash
  Authors: Gavin Andresen 
  Status: Deployed
  Type: Specification
  Assigned: 2011-10-18
==Abstract== This BIP describes a new type of Bitcoin address to support arbitrarily complex transactions. Complexity in this context is defined as what information is needed by the recipient to respend the received coins, in contrast to needing a single ECDSA private key as in current implementations of Bitcoin. In essence, an address encoded under this proposal represents the encoded hash of a [https://en.bitcoin.it/wiki/Script script], rather than the encoded hash of an ECDSA public key. ==Motivation== Enable "end-to-end" secure wallets and payments to fund escrow transactions or other complex transactions. Enable third-party wallet security services. ==Specification== The new bitcoin address type is constructed in the same manner as existing bitcoin addresses (see [https://en.bitcoin.it/Base58Check_encoding Base58Check encoding]): base58-encode: [one-byte version][20-byte hash][4-byte checksum] Version byte is 5 for a main-network address, 196 for a testnet address. The 20-byte hash is the hash of the script that will be used to redeem the coins. And the 4-byte checksum is the first four bytes of the double SHA256 hash of the version and hash. ==Rationale== One criticism is that bitcoin addresses should be deprecated in favor of a more user-friendly mechanism for payments, and that this will just encourage continued use of a poorly designed mechanism. Another criticism is that bitcoin addresses are inherently insecure because there is no identity information tied to them; if you only have a bitcoin address, how can you be certain that you're paying who or what you think you're paying? Furthermore, truncating SHA256 is not an optimal checksum; there are much better error-detecting algorithms. If we are introducing a new form of Bitcoin address, then perhaps a better algorithm should be used. This is one piece of the simplest path to a more secure bitcoin infrastructure. It is not intended to solve all of bitcoin's usability or security issues, but to be an incremental improvement over what exists today. A future BIP or BIPs should propose more user-friendly mechanisms for making payments, or for verifying that you're sending a payment to the Free Software Foundation and not Joe Random Hacker. Assuming that typing in bitcoin addresses manually will become increasingly rare in the future, and given that the existing checksum method for bitcoin addresses seems to work "well enough" in practice and has already been implemented multiple times, the Author believes no change to the checksum algorithm is necessary. The leading version bytes are chosen so that, after base58 encoding, the leading character is consistent: for the main network, byte 5 becomes the character '3'. For the testnet, byte 196 is encoded into '2'. ==Backwards Compatibility== This proposal is not backwards compatible, but it fails gracefully-- if an older implementation is given one of these new bitcoin addresses, it will report the address as invalid and will refuse to create a transaction. ==Reference Implementation== See base58.cpp/base58.h at https://github.com/bitcoin/bitcoin/tree/master/src ==See Also== * [[bip-0012.mediawiki|BIP 12: OP_EVAL, the original P2SH design]] * [[bip-0016.mediawiki|BIP 16: Pay to Script Hash (aka "/P2SH/")]] * [[bip-0017.mediawiki|BIP 17: OP_CHECKHASHVERIFY, another P2SH design]] ================================================ FILE: bip-0014.mediawiki ================================================
  BIP: 14
  Layer: Peer Services
  Title: Protocol Version and User Agent
  Authors: Amir Taaki 
           Patrick Strateman 
  Status: Deployed
  Type: Specification
  Assigned: 2011-11-10
  Discussion: 2011-11-02: https://gnusha.org/pi/bitcoindev/1320268981.72296.YahooMailNeo@web121003.mail.ne1.yahoo.com/
              2011-11-10: https://gnusha.org/pi/bitcoindev/1320959761.36702.YahooMailNeo@web121014.mail.ne1.yahoo.com/
In this document, bitcoin will be used to refer to the protocol while Satoshi will refer to the current client in order to prevent confusion. == Past Situation == Bitcoin as a protocol began life with the Satoshi client. Now that the community is diversifying, a number of alternative clients with their own codebases written in a variety of languages (Java, Python, Javascript, C++) are rapidly developing their own feature-sets. Embedded in the protocol is a version number. Primarily this version number is in the "version" and "getblocks" messages, but is also in the "block" message to indicate the software version that created that block. Currently this version number is the same version number as that of the client. This document is a proposal to separate the protocol version from the client version, together with a proposed method to do so. == Rationale == With non-separated version numbers, every release of the Satoshi client will increase its internal version number. Primarily this holds every other client hostage to a game of catch-up with Satoshi version number schemes. This plays against the decentralised nature of bitcoin, by forcing every software release to remain in step with the release schedule of one group of bitcoin developers. Version bumping can also introduce incompatibilities and fracture the network. In order that the health of the network is maintained, the development of the protocol as a shared common collaborative process requires being split off from the implementation of that protocol. Neutral third entities to guide the protocol with representatives from all groups, present the chance for bitcoin to grow in a positive manner with minimal risks. By using a protocol version, we set all implementations on the network to a common standard. Everybody is able to agree within their confines what is protocol and what is implementation-dependent. A user agent string is offered as a 'vanity-plate' for clients to distinguish themselves in the network. Separation of the network protocol from the implementation, and forming development of said protocol by means of a mutual consensus among participants, has the democratic disadvantage when agreement is hard to reach on contentious issues. To mitigate this issue, strong communication channels and fast release schedules are needed, and are outside the scope of this document (concerning a process-BIP type). User agents provide extra tracking information that is useful for keeping tabs on network data such as client implementations used or common architectures/operating-systems. In the rare case they may even provide an emergency method of shunning faulty clients that threaten network health- although this is strongly unrecommended and extremely bad form. The user agent does not provide a method for clients to work around and behave differently to different implementations, as this will lead to protocol fracturing. In short: * Protocol version: way to distinguish between nodes and behave different accordingly. * User agent: simple informational tool. Protocol should not be modified depending on user agent. == Browser User-Agents == [http://tools.ietf.org/html/rfc1945 RFC 1945] vaguely specifies a user agent to be a string of the product with optional comments. Mozilla/5.0 (X11; U; Linux i686; en-US; rv:1.9.1.6) Gecko/20100127 Gentoo Shiretoko/3.5.6 User agents are most often parsed by computers more than humans. The space delimited format, does not provide an easy, fast or efficient way for parsing. The data contains no structure indicating hierarchy in this placement. The most immediate pieces of information there are the browser product, rendering engine and the build (Gentoo Shiretoko) together with version number. Various other pieces of information as included as comments such as desktop environment, platform, language and revision number of the build. == Proposal == The version field in "version" and "getblocks" packets will become the protocol version number. The version number in the "blocks" reflects the protocol version from when that block was created. The currently unused sub_version_num field in "version" packets will become the new user-agent string. Bitcoin user agents are a modified browser user agent with more structure to aid parsers and provide some coherence. In bitcoin, the software usually works like a stack starting from the core code-base up to the end graphical interface. Therefore the user agent strings codify this relationship. Basic format: /Name:Version/Name:Version/.../ Example: /Satoshi:5.64/bitcoin-qt:0.4/ /Satoshi:5.12/Spesmilo:0.8/ Here bitcoin-qt and Spesmilo may use protocol version 5.0, however the internal codebase they use are different versions of the same software. The version numbers are not defined to any strict format, although this guide recommends: * Version numbers in the form of Major.Minor.Revision (2.6.41) * Repository builds using a date in the format of YYYYMMDD (20110128) For git repository builds, implementations are free to use the git commitish. However the issue lies in that it is not immediately obvious without the repository which version precedes another. For this reason, we lightly recommend dates in the format specified above, although this is by no means a requirement. Optional -r1, -r2, ... can be appended to user agent version numbers. This is another light recommendation, but not a requirement. Implementations are free to specify version numbers in whatever format needed insofar as it does not include (, ), : or / to interfere with the user agent syntax. An optional comments field after the version number is also allowed. Comments should be delimited by brackets (...). The contents of comments is entirely implementation defined although this BIP recommends the use of semi-colons ; as a delimiter between pieces of information. Example: /BitcoinJ:0.2(iPad; U; CPU OS 3_2_1)/AndroidBuild:0.8/ Reserved symbols are therefore: / : ( ) They should not be misused beyond what is specified in this section. * / separates the code-stack * : specifies the implementation version of the particular stack * ( and ) delimits a comment which optionally separates data using ; == Timeline == When this document was published, the bitcoin protocol and Satoshi client versions were currently at 0.5 and undergoing changes. In order to minimise disruption and allow the undergoing changes to be completed, the next protocol version at 0.6 became peeled from the client version (also at 0.6). As of that time (January 2012), protocol and implementation version numbers are distinct from each other. ================================================ FILE: bip-0015.mediawiki ================================================
  BIP: 15
  Layer: Applications
  Title: Aliases
  Authors: Amir Taaki 
  Status: Closed
  Type: Specification
  Assigned: 2011-12-10
[[bip-0070.mediawiki|BIP 0070]] (payment protocol) may be seen as the alternative to Aliases. Using vanilla bitcoin, to send funds to a destination, an address in the form 1Hd44nkJfNAcPJeZyrGC5sKJS1TzgmCTjjZ is needed. The problem with using addresses is that they are not easy to remember. An analogy can be thought if one were required to enter the IP address of their favourite websites if domain names did not exist. This document aims to layout through careful argument, a bitcoin alias system. This is a big modification to the protocol that is not easily changed in the future and has big ramifications. There is impetus in getting it correct the first time. Aliases have to be robust and secure. == Schemes == Here are a few different proposals and the properties of each system. === FirstBits === FirstBits is a proposal for using the blockchain as an address book. When bitcoins are sent to an address, that address becomes recorded in the blockchain. It is therefore known that this address exists or did exist by simply seeing that there was a payment to that address. FirstBits is a method to have a memorable alias. One first converts the address to lower-case, then takes the first few unique characters. This is your FirstBits alias. As an example, brmlab hackerspace in Prague has an address for purchasing food or drink, or making donations: 1BRMLAB7nryYgFGrG8x9SYaokb8r2ZwAsX Their FirstBits alias becomes: 1brmlab It is enough information to be given the FirstBits alias ''1brmlab''. When someone wishes to make a purchase, without FirstBits, they either have to type out their address laboriously by hand, scan their QR code (which requires a mobile handset that this author does not own) or find their address on the internet to copy and paste into the client to send bitcoins. FirstBits alleviates this impracticality by providing an easy method to make payments. Together with Vanitygen (vanity generator), it becomes possible to create memorable unique named addresses. Addresses that are meaningful, rather than an odd assemblage of letters and numbers but add context to the destination. However FirstBits has its own problems. One is that the possible aliases one is able to generate is limited by the available computing power available. It may not be feasible to generate a complete or precise alias that is wanted- only approximates may be possible. It is also computationally resource intensive which means a large expenditure of power for generating unique aliases in the future, and may not scale up to the level of individuals at home or participants with hand-held devices in an environment of ubiquitous computing. FirstBits scales extremely poorly as the network grows. Each indexer or lookup node needs to keep track of every bitcoin address ever in existence and provide a fast lookup from the aliases to those addresses. As the network grows linearly, the number of addresses should grow exponentially (assuming a networked effect of (n-1)*(n-2)/2) rapidly making this scheme unfeasible. Light clients of the partial merkle root types become dependent on a trusted third party for their alias lookups. The cost of storing every bitcoin address is too high considering their typical use-case on low-resource devices. This factor more than the others, means this scheme is sub-optimal and must be rejected. === DNS TXT Records === DNS allows TXT records to be created containing arbitrary data. In a bitcoin alias system, a custom format mutually agreed upon by a BIP standard would be used to store mappings to bitcoin addresses from domain names. How such a format would look is out of the scope of this document. An issue is that it requires people who wish to create such mappings to be familiar with configuring DNS records, and be able to run the necessary toolsets to insert the correct data. Although not a huge concern, it is a usability issue. Security wise, DNS is unsafe and insecure by design. It is possible to spoof records by being on the same network as another host. A number of revisions to mitigate the issue under the guise of DNSSEC have been in the works since the 1990s and are still being rolled out. As of Dec 2011, DNSSEC is still not yet a defacto standard on the internet. Should a participant in the bitcoin network wish to use DNS TXT records, they would in addition to having to configure DNS, be able to setup DNSSEC. This may not be feasible, especially where some registrars provide access to DNS through a web interface only. The disadvantage of DNS TXT records is that updating a record takes time. This encourages people to not use new addresses per transaction which has certain security issues. === Server Service === Aside from using DNS TXT records, another possibility is using the domain name system to lookup hosts and then contact a service running on a predefined port to get the bitcoin address. # User wishes to send to foo@bar.net # Client uses DNS to find the IP address of bar.net: 123.123.123.123 # Client connects to port 123.123.123.123:4567 and requests the bitcoin address for the user ''foo'' # Server responds with the address or error code and terminates the connection. # Client sends the funds to the address The service would be responsible for providing the mechanisms for changing and storing the mappings on their service. A front-end web interface could be provided to users wishing to use the service and customise their accounts on the server. This approach has the positive aspect of providing the best flexibility for the implementer to store the records however they wish in a database or plaintext file, and then serve them up quickly using a small server side daemon typically written in C. This approach is highly scalable. However this approach also suffers the problem of being reliant on DNS and hence also being vulnerable to spoofing. Hence DNSSEC is also required. This approach is slightly better than the DNS TXT records though since it makes inserting new users and modifying aliases very easy which allows people to run these server services more cheaply. === HTTPS Web Service === HTTPS provides an additional layer of security by encrypting the connection, providing much needed privacy for users. Together with using Certificate Authorities, it fixes the issue with using DNSSEC since an error would be thrown up were someone to try to spoof a domain name on the local network. When trying to send to: genjix@foo.org The request is broken into the handle (genjix) and domain (foo.org) at the last occurrence of the @. The client then constructs a request that will query for the address. https://foo.org/bitcoin-alias/?handle=genjix bitcoin-alias has been chosen as the query suffix because it allows this system to co-exist easily within another web root without the fear of name clashes. The query will then return an address which is used to make the payment. 1Hd44nkJfNAcPJeZyrGC5sKJS1TzgmCTjjZ The details of whether a unique address is returned per query, whether an address is fetched from a pre-existing pool of addresses, and so on is an implementation detail unique to every server. How alias to address mappings are setup is dependent on the site which could have a web-interface and be providing a free service to users or be a private customised service serving pre-existing addresses. This is left up to sysop policy, and deliberately not defined here. A web service is trivial to setup and the cost is low. There are many free out of the box providers on the net that allows anyone with the most basic knowledge of web technologies to create their own website. By providing users with a package, anybody can quickly set themselves up with a bitcoin alias. It could be something as simple as a PHP script that the user edits with their custom settings and uploads themselves to their website. It also scales reasonably- anybody wishing to run a naming service can attach a backend with a variety of database technologies then provide a web frontend for users to customise and create their own aliases. A naive implementation is provided below as an example.
// resolv.h
#ifndef NOMRESOLV_H__
#define NOMRESOLV_H__

#include 
#include "curl/curl.h"

using std::string;

/*

This class resolves against a server to lookup addresses.
To not conflict with the bitcoin addresses, we refer here to people's handles.
A handle is of the form:

   genjix@foo.org

Most characters are valid for the username + password (and handled accordingly), but the domain follows usual web standards. It is possible to affix a path if needed,

   genjix@bar.com/path/to/

*/

class NameResolutionService
{
public:
    NameResolutionService();
    ~NameResolutionService();

    // Three main methods map to RPC actions.
    string FetchAddress(const string& strHandle, string& strAddy);

private:
    // A POST block
    class PostVariables
    {
    public:
        PostVariables();
        ~PostVariables();
        // Add a new key, value pair
        bool Add(const string& strKey, const string& strVal);
        curl_httppost* operator()() const;
    private:
        // CURL stores POST blocks as linked lists.
        curl_httppost *pBegin, *pEnd;
    };

    // Explodes user@domain => user, domain
    static void ExplodeHandle(const string& strHandle, string& strNickname, string& strDomain);
    // Perform the HTTP request. Returns true on success.
    bool Perform();

    // CURL error message
    char pErrorBuffer[CURL_ERROR_SIZE];
    // CURL response
    string strBuffer;
    // CURL handle
    CURL *curl;
};

#endif
// resolv.cpp
#include "resolv.h"

#include 

#include "access.h"

// callback used to write response from the server
static int writer(char *pData, size_t nSize, size_t nNmemb, std::string *pBuffer)
{
  int nResult = 0;
  if (pBuffer != NULL)
  {
    pBuffer->append(pData, nSize * nNmemb);
    // How much did we write?
    nResult = nSize * nNmemb;
  }
  return nResult;
}

NameResolutionService::NameResolutionService()
{
    // Initialise CURL with our various options.
    curl = curl_easy_init();
    // This goes first in case of any problems below. We get an error message.
    curl_easy_setopt(curl, CURLOPT_ERRORBUFFER, pErrorBuffer);
    // fail when server sends >= 404
    curl_easy_setopt(curl, CURLOPT_FAILONERROR, 1);
    curl_easy_setopt(curl, CURLOPT_HEADER, 0);
    curl_easy_setopt(curl, CURLOPT_FOLLOWLOCATION, 1);
    curl_easy_setopt(curl, CURLOPT_POSTREDIR, CURL_REDIR_POST_302);
    curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, writer);
    curl_easy_setopt(curl, CURLOPT_USE_SSL, CURLUSESSL_TRY);
    curl_easy_setopt(curl, CURLOPT_SSL_VERIFYPEER, 1);
    // server response goes in strBuffer
    curl_easy_setopt(curl, CURLOPT_WRITEDATA, &strBuffer);
    pErrorBuffer[0] = '\0';
}
NameResolutionService::~NameResolutionService()
{
    curl_easy_cleanup(curl);
}

void NameResolutionService::ExplodeHandle(const string& strHandle, string& strNickname, string& strDomain)
{
    // split address at @ furthest to the right
    size_t nPosAtsym = strHandle.rfind('@');
    strNickname = strHandle.substr(0, nPosAtsym);
    strDomain = strHandle.substr(nPosAtsym + 1, strHandle.size());
}
bool NameResolutionService::Perform()
{
    // Called after everything has been setup. This actually does the request.
    CURLcode result = curl_easy_perform(curl);
    return (result == CURLE_OK);
}

string NameResolutionService::FetchAddress(const string& strHandle, string& strAddy)
{
    // GET is defined for 'getting' data, so we use GET for the low risk fetching of people's addresses
    if (!curl)
        // For some reason CURL didn't start...
        return pErrorBuffer;
    // Expand the handle
    string strNickname, strDomain;
    ExplodeHandle(strHandle, strNickname, strDomain);
    // url encode the nickname for get request
    const char* pszEncodedNick = curl_easy_escape(curl, strNickname.c_str(), strNickname.size());
    if (!pszEncodedNick)
        return "Unable to encode nickname.";
    // construct url for GET request
    string strRequestUrl = strDomain + "/bitcoin-alias/?handle=" + pszEncodedNick;
    // Pass URL to CURL
    curl_easy_setopt(curl, CURLOPT_URL, strRequestUrl.c_str());
    if (!Perform())
        return pErrorBuffer;
    // Server should respond with a JSON that has the address in.
    strAddy = strBuffer;
    return "";  // no error
}

NameResolutionService::PostVariables::PostVariables()
{
    // pBegin/pEnd *must* be null before calling curl_formadd
    pBegin = NULL;
    pEnd = NULL;
}
NameResolutionService::PostVariables::~PostVariables()
{
    curl_formfree(pBegin);
}
bool NameResolutionService::PostVariables::Add(const string& strKey, const string& strVal)
{
    // Copy strings to this block. Return true on success.
    return curl_formadd(&pBegin, &pEnd, CURLFORM_COPYNAME, strKey.c_str(), CURLFORM_COPYCONTENTS, strVal.c_str(), CURLFORM_END) == CURL_FORMADD_OK;
}

curl_httppost* NameResolutionService::PostVariables::operator()() const
{
    return pBegin;
}



// rpc.cpp
...

const Object CheckMaybeThrow(const string& strJsonIn)
{
    // Parse input JSON
    Value valRequest;
    if (!read_string(strJsonIn, valRequest) || valRequest.type() != obj_type)
        throw JSONRPCError(-32700, "Parse error");
    const Object& request = valRequest.get_obj();
    // Now check for a key called "error"
    const Value& error  = find_value(request, "error");
    // It's an error JSON! so propagate the error.
    if (error.type() != null_type)
        throw JSONRPCError(-4, error.get_str());
    // Return JSON object
    return request;
}

const string CollectAddress(const string& strIn)
{
    // If the handle does not have an @ in it, then it's a normal base58 bitcoin address
    if (strIn.find('@') == (size_t)-1)
        return strIn;

    // Open the lookup service
    NameResolutionService ns;
    // We established that the input string is not a BTC address, so we use it as a handle now.
    string strHandle = strIn, strAddy;
    string strError = ns.FetchAddress(strHandle, strAddy);
    if (!strError.empty())
        throw JSONRPCError(-4, strError);

    const Object& request(CheckMaybeThrow(strAddy));
    // Get the BTC address from the JSON
    const Value& address = find_value(request, "address");
    if (address.type() != str_type)
        throw JSONRPCError(-32600, "Server responded with malformed reply.");
    return address.get_str();
}

// Named this way to prevent possible conflicts.
Value rpc_send(const Array& params, bool fHelp)
{
    if (fHelp || params.size() != 2)
        throw runtime_error(
            "send  \n"
            " is a real and is rounded to the nearest 0.01");

    // Intelligent function which looks up address given handle, or returns address
    string strAddy = CollectAddress(params[0].get_str());
    int64 nAmount = AmountFromValue(params[1]);
    // Do the send
    CWalletTx wtx;
    string strError = SendMoneyToBitcoinAddress(strAddy, nAmount, wtx);
    if (!strError.empty())
        throw JSONRPCError(-4, strError);
    return wtx.GetHash().GetHex();
}

...
=== IP Transactions === An IP transaction is an old transaction format in bitcoin that is disabled and possibly could be deprecated. It involves being given an IP address to make payment to. Upon connecting to the node and requesting their public key using "checkorder", they will respond with a script in the form: OP_CHECKSIG Similar to coinbase output transactions. IP transactions have the advantage of being able to contain additional metadata which can be useful in many transactions. Currently no authentication is done making the scheme insecure against man in the middle (MITM) attacks. This proposal seeks to enable DNS lookups for IP transactions. The "checkorder" message would contain a destination account, which could map to different isolated sets of keypairs/wallets running under the same host. The exact mapping from the checkorder reference info to the local system is implementation defined. By using DNS lookups, the MITM problem with IP transactions could be mitigated by storing a public key in a DNS TXT record. This public key would be used for all future "reply" messages originating from that host. First time use would require a confirmation for acceptance of that public key; like with SSH. Should the "reply" message not match the accepted public key, then the host will be given an error. [[Category:BIP|E]] === Namecoin ID === This proposal uses the Namecoin blockchain to associate an alias with a bitcoin address. Bitcoin queries a namecoin node. This retrieves the structured data containing the bitcoin address(es) associated with this alias. Using a decentralised domain name system like Namecoin, means no external server or entity needs to be trusted unlike the other proposals listed here. This indicates a system with the advantage of having a high availability and ease of entry (no restrictions for users to create aliases). Two examples are presented below. The first shows a simpler format, while the second shows several Bitcoin addresses in a structured format. $ namecoind name_show id/khal { "bitcoin" : "1KHAL8bUjnkMRMg9yd2dNrYnJgZGH8Nj6T" } $ namecoind name_show id/khal { "bitcoin" : { "default" : "1KHAL8bUjnkMRMg9yd2dNrYnJgZGH8Nj6T", "donation": "1J3EKMfboca3SESWGrQKESsG1MA9yK6vN4" } } '''More possibilities :''' * Allow to securely use '''unsecured channels''' You can put an url and a bitcoin address that will be used to sign the result. It means that a query to this url will return a bitcoin address and a signature. Bitcoin can then check (with the verify_message function) that the returned address has not been replaced by another one. $ namecoind name_show id/khal { "bitcoin" : { "url" : "http://merchant.com/bitcoin/getnewaddres/", "signedWith" : "1KHAL8bUjnkMRMg9yd2dNrYnJgZGH8Nj6T" } } * Allow to get a different address each time, or per user, per order, etc $ namecoind name_show id/khal { "bitcoin" : { "url" : "http://merchant.com/bitcoin/getaddres/{Your customer id}", "signedWith" : "1KHAL8bUjnkMRMg9yd2dNrYnJgZGH8Nj6T", "useOnce": false } } In the above example, bitcoin will ask the user for "Your customer id" and replace that value in the url before making the http request. The merchant will receive the request and give the user a payment address associated with that customer. Any text can be put into the brackets, allowing merchants to adapt it to all their needs. * Specification is extensible New features can be added later to support uncovered cases. See the specification of [http://dot-bit.org/Namespace:Identity Namecoin ID] for more information. ================================================ FILE: bip-0016/qa.mediawiki ================================================ This page is a Quality Assurance test plan for [[../bip-0016.mediawiki|BIP 16]]. If you see a test missing, please add it. If you can help test, please edit this page to sign-off on it. {| class="wikitable" |- ! Done !! Test Procedure !! Tested by |- style="color:green;" | ✓ | Run BIP-16-capable Bitcoin 0.6 on testnet and main net
Send coins using GUI, RCP sendtoaddress, and RCP sendmany commands
Result: coins sent in all cases | Gavin Andresen |- style="color:green;" | ✓ | Test multisig 1-of-1
Run 0.6 bitcoind, get a public key with: ./bitcoind -testnet validateaddress $(./bitcoind -testnet getnewaddress)
Generate a multisig 1-of-1 address: ./bitcoind addmultisigaddress 1 {public key from above}
Send-to-self some bitcoins using that address
Result: transaction is confirmed by network, displays properly in listtransactions. Result: balance is unaffected | Gavin Andresen; see transactions in [http://blockexplorer.com/testnet/block/000000001bdceba3936f2ea6a55311ac7b6030e327f1960e892620fcde6abf5f testnet block 44989] |- style="color:green;" | ✓ | Test multisig 1-of-2
Run 0.6 bitcoind, get 2 new bitcoin addresses
Generate a multisig 1-of-2 address: ./bitcoind addmultisigaddress 1 {address1} {address2}
Send-to-self some bitcoins using that address
Result: transaction is confirmed by network, displays properly in listtransactions. Result: bitcoin balance is unaffected. | Gavin Andresen; see transactions in [http://blockexplorer.com/testnet/block/000000001bdceba3936f2ea6a55311ac7b6030e327f1960e892620fcde6abf5f testnet block 44989] |- style="color:green;" | ✓ | Test multisig 1-of-3, 2-of-3, 3-of-3
Repeat test procedures above, with the other new multisignature transaction types | Gavin Andresen; see transactions in [http://blockexplorer.com/testnet/block/000000001bdceba3936f2ea6a55311ac7b6030e327f1960e892620fcde6abf5f testnet block 44989] |- style="color:green;" | ✓ | Test multisig send-to-other
Repeat test procedures above, but use two bitcoinds, prepared as follows:
bitcoind 1 : Run getnewaddress and addmultisigaddress
bitcoind 2 : Just addmultisigaddress
Send coins from 2 to 1 using the address
Result: transaction is accepted/confirmed by network
Result: balance for 2 goes down, listtransactions for 2 displays correct result
Result: balance for 1 goes up, listtransactions for 1 displays correct result
| Gavin Andresen; see transactions in [http://blockexplorer.com/testnet/block/000000001bdceba3936f2ea6a55311ac7b6030e327f1960e892620fcde6abf5f testnet block 44989] |- style="color:green;" | ✓ | Test redeeming multisignature transactions
Fund a new, empty wallet entirely with multisig transactions
Wait for transactions to confirm
Use sendtoaddress and sendmany to generate spend-from-multisig transactions
Spend to both single-address and multisig address, and test send-to-other and send-to-self
Result: transactions are accepted/confirmed by network
Result: balance decreases, listtransactions displays correct information
| Gavin Andresen; see transactions in [http://blockexplorer.com/testnet/block/000000001bdceba3936f2ea6a55311ac7b6030e327f1960e892620fcde6abf5f testnet block 44989] |- style="color:green;" | ✓ | Run 0.6 Bitcoin-Qt GUI on one of the test wallets from above
Result: balance and transactions displayed correctly | Gavin Andresen |- style="color:orange;" | ✓ | Run BIP-16-capable backport Bitcoin 0.3.19 through 0.5.1 on testnet and main net
Send coins using GUI, RCP sendtoaddress, and RCP sendmany commands
Result: coins sent in all cases | Gavin Andresen (tested 0.3.19, 0.3.24 and 0.5.1) |- style="color:green;" | ✓ | Run BIP-16-capable Bitcoin 0.6.0 on testnet
Mine coins using built-in miner
Result: blocks accepted, show up on blockexplorer.com/testnet
Result: mined blocks' coinbase contains /P2SH/ string | Gavin Andresen |- style="color:green;" | ✓ | Run BIP-16-capable Bitcoin 0.6.0 on testnet
Mine coins using getwork interface
Result: blocks accepted, show up on blockexplorer.com/testnet
Result: mined blocks' coinbase contains /P2SH/ string | Gavin Andresen |- style="color:green;" | | Run BIP-16-capable Bitcoin 0.6.0 on testnet
Mine coins using getmemorypool interface
Result: blocks accepted, show up on blockexplorer.com/testnet
Result: mined blocks' coinbase contains /P2SH/ string | Gregory Maxwell; Using p2pool see [https://blockexplorer.com/testnet/rawblock/00000000040367fcb750b6f064db6955b6c7c6218fb625e3dfed6b5c19c97107 testnet block 45400] (and many others, also tested on mainnet) |- style="color:green;" | ✓ | Run BIP-16-capable Bitcoin 0.3.19 through 0.5.1 backports on testnet
Mine coins using built-in miner
Result: blocks accepted, show up on blockexplorer.com/testnet
Result: mined blocks' coinbase contains /P2SH/ string | Gavin Andresen (tested all on a testnet-in-a-box) |- style="color:green;" | ✓ | Run BIP-16-capable Bitcoin 3.19 through 0.5.1 backports on testnet
Mine coins using getwork interface
Result: blocks accepted, show up on blockexplorer.com/testnet
Result: mined blocks' coinbase contains /P2SH/ string | Gavin Andresen (tested all on a testnet-in-a-box) |- style="color:green;" | ✓ | Run BIP-16-capable Bitcoin 0.3.19 through 0.5.1 backports on testnet
Mine coins using built-in miner
Result: blocks accepted, show up on blockexplorer.com/testnet
Result: mined blocks' coinbase contains /P2SH/ string | Gavin Andresen (tested all on a testnet-in-a-box) |- style="color:green;" | ✓ | Run BIP-16-capable Bitcoin 3.19 through 0.5.1 backports on testnet
Mine coins using getwork interface
Result: blocks accepted, show up on blockexplorer.com/testnet
Result: mined blocks' coinbase contains /P2SH/ string | Gavin Andresen (tested all on a testnet-in-a-box) |- style="color:red;" |- style="color:red;" | | Run BIP-16-capable Bitcoin 3.19 through 0.5.1 backports on testnet
Mine coins using getmemorypool interface
Result: blocks accepted, show up on blockexplorer.com/testnet
Result: mined blocks' coinbase contains /P2SH/ string | |- style="color:green;" | ✓ | Create/run unit tests for:
multisignature signing/verification
multisignature invalid signature failure
multisignature IsStandard() success/failure
extraction of addresses from multisignature transactions
BIP 16 IsStandard() success/failure (including failure with OP_PUSHDATA1/2/4)
BIP 16 AreInputsStandard() success/failure
BIP 16 compatibility with other 3 standard transaction types
BIP 16 no-recursion test
BIP 16 switchover date logic
OP_CHECKMULTISIG counting of signature operations inside BIP 16 transactions
| Gavin Andresen (see test/multisig_tests.cpp, test/script_tests.cpp, test/script_P2SH_tests.cpp, test/sigopcount_tests.cpp in the bitcoin source tree; 'make test_bitcoin' in src/ directory to compile) |- style="color:green;" | ✓ | Create/run 'transaction fuzzer' to stress-test BIP 16 transactions | Gavin Andresen (https://github.com/gavinandresen/bitcoin-git/tree/fuzzer , run twice on both testnet-in-a-box and testnet with 100,000 'fuzzed' transactions each test run) Valid fuzzed transactions appeared in (for example) [http://blockexplorer.com/testnet/block/000000001587c859649cea954e921ba4efd77707fb327dd53e122fd7b89636c4 testnet block 44987] |- style="color:green;" | ✓ | Run Bitcoin 0.6 on main net
Result: blocks created properly Result: blocks include /P2SH/ string in their coinbase | various mining pools |- style="color:green;" | ✓ | Run BIP 16 vinced_mergedmine backport on main net
Result: blocks created properly Result: blocks include /P2SH/ string in their coinbase | (Gavin for slush: after bug fixes, running with no issues)
|- style="color:green;" | ✓ | Test chain-split handling on testnet-in-a-box
Create two valid hash, invalid signature transactions in two blocks separated in time on a testnet-in-a-box chain
Run a bitcoind to synchronize with the chain, with -paytoscripthashtime set in between the two blocks
Result: first transaction/block accepted, second causes a chain split
Re-run bitcoind with -paytoscripthashtime in the future
Result: entire chain accepted | Gavin Andresen: testnet-in-a-box files at: http://www.skypaint.com/bitcoin/bip16chain.tar.gz first half-valid BIP16 transaction at block 2431 (time 1328202835) second at block 2436 (time 1328204241)
|} ================================================ FILE: bip-0016.mediawiki ================================================
  BIP: 16
  Layer: Consensus (soft fork)
  Title: Pay to Script Hash
  Authors: Gavin Andresen 
  Status: Deployed
  Type: Specification
  Assigned: 2012-01-03
==Abstract== This BIP describes a new "standard" transaction type for the Bitcoin scripting system, and defines additional validation rules that apply only to the new transactions. ==Motivation== The purpose of pay-to-script-hash is to move the responsibility for supplying the conditions to redeem a transaction from the sender of the funds to the redeemer. The benefit is allowing a sender to fund any arbitrary transaction, no matter how complicated, using a fixed-length 20-byte hash that is short enough to scan from a QR code or easily copied and pasted. ==Specification== A new standard transaction type that is relayed and included in mined blocks is defined: OP_HASH160 [20-byte-hash-value] OP_EQUAL [20-byte-hash-value] shall be the push-20-bytes-onto-the-stack opcode (0x14) followed by exactly 20 bytes. This new transaction type is redeemed by a standard scriptSig: ...signatures... {serialized script} Transactions that redeem these pay-to-script outpoints are only considered standard if the ''serialized script'' - also referred to as the ''redeemScript'' - is, itself, one of the other standard transaction types. The rules for validating these outpoints when relaying transactions or considering them for inclusion in a new block are as follows: # Validation fails if there are any operations other than "push data" operations in the scriptSig. # Normal validation is done: an initial stack is created from the signatures and {serialized script}, and the hash of the script is computed and validation fails immediately if it does not match the hash in the outpoint. # {serialized script} is popped off the initial stack, and the transaction is validated again using the popped stack and the deserialized script as the scriptPubKey. These new rules should only be applied when validating transactions in blocks with timestamps >= 1333238400 (Apr 1 2012) [https://github.com/bitcoin/bitcoin/commit/8f188ece3c82c4cf5d52a3363e7643c23169c0ff Remove -bip16 and -paytoscripthashtime command-line arguments]. There are transactions earlier than 1333238400 in the block chain that fail these new validation rules. [https://web.archive.org/web/20141122040355/http://blockexplorer.com/tx/6a26d2ecb67f27d1fa5524763b49029d7106e91e3cc05743073461a719776192 Transaction 6a26d2ecb67f27d1fa5524763b49029d7106e91e3cc05743073461a719776192]. Older transactions must be validated under the old rules. (see the Backwards Compatibility section for details). For example, the scriptPubKey and corresponding scriptSig for a one-signature-required transaction is: scriptSig: [signature] {[pubkey] OP_CHECKSIG} scriptPubKey: OP_HASH160 [20-byte-hash of {[pubkey] OP_CHECKSIG} ] OP_EQUAL Signature operations in the {serialized script} shall contribute to the maximum number allowed per block (20,000) as follows: # OP_CHECKSIG and OP_CHECKSIGVERIFY count as 1 signature operation, whether or not they are evaluated. # OP_CHECKMULTISIG and OP_CHECKMULTISIGVERIFY immediately preceded by OP_1 through OP_16 are counted as 1 to 16 signature operation, whether or not they are evaluated. # All other OP_CHECKMULTISIG and OP_CHECKMULTISIGVERIFY are counted as 20 signature operations. Examples: +3 signature operations: {2 [pubkey1] [pubkey2] [pubkey3] 3 OP_CHECKMULTISIG} +22 signature operations: {OP_CHECKSIG OP_IF OP_CHECKSIGVERIFY OP_ELSE OP_CHECKMULTISIGVERIFY OP_ENDIF} ==Rationale== This BIP replaces BIP 12, which proposed a new Script opcode ("OP_EVAL") to accomplish everything in this BIP and more. The Motivation for this BIP (and BIP 13, the pay-to-script-hash address type) is somewhat controversial; several people feel that it is unnecessary, and complex/multisignature transaction types should be supported by simply giving the sender the complete {serialized script}. The author believes that this BIP will minimize the changes needed to all of the supporting infrastructure that has already been created to send funds to a base58-encoded-20-byte bitcoin addresses, allowing merchants and exchanges and other software to start supporting multisignature transactions sooner. Recognizing one 'special' form of scriptPubKey and performing extra validation when it is detected is ugly. However, the consensus is that the alternatives are either uglier, are more complex to implement, and/or expand the power of the expression language in dangerous ways. The signature operation counting rules are intended to be easy and quick to implement by statically scanning the {serialized script}. Bitcoin imposes a maximum-number-of-signature-operations per block to prevent denial-of-service attacks on miners. If there was no limit, a rogue miner might broadcast a block that required hundreds of thousands of ECDSA signature operations to validate, and it might be able to get a head start computing the next block while the rest of the network worked to validate the current one. There is a 1-confirmation attack on old implementations, but it is expensive and difficult in practice. The attack is: # Attacker creates a pay-to-script-hash transaction that is valid as seen by old software, but invalid for new implementation, and sends themselves some coins using it. # Attacker also creates a standard transaction that spends the pay-to-script-hash transaction, and pays the victim who is running old software. # Attacker mines a block that contains both transactions. If the victim accepts the 1-confirmation payment, then the attacker wins because both transactions will be invalidated when the rest of the network overwrites the attacker's invalid block. The attack is expensive because it requires the attacker create a block that they know will be invalidated by the rest of the network. It is difficult because creating blocks is difficult and users should not accept 1-confirmation transactions for higher-value transactions. ==Backwards Compatibility== These transactions are non-standard to old implementations, which will (typically) not relay them or include them in blocks. Old implementations will validate that the {serialize script}'s hash value matches when they validate blocks created by software that fully support this BIP, but will do no other validation. Avoiding a block-chain split by malicious pay-to-script transactions requires careful handling of one case: * A pay-to-script-hash transaction that is invalid for new clients/miners but valid for old clients/miners. To gracefully upgrade and ensure no long-lasting block-chain split occurs, more than 50% of miners must support full validation of the new transaction type and must switch from the old validation rules to the new rules at the same time. To judge whether or not more than 50% of hashing power supports this BIP, miners are asked to upgrade their software and put the string "/P2SH/" in the input of the coinbase transaction for blocks that they create. On February 1, 2012, the block-chain will be examined to determine the number of blocks supporting pay-to-script-hash for the previous 7 days. If 550 or more contain "/P2SH/" in their coinbase, then all blocks with timestamps after 15 Feb 2012, 00:00:00 GMT shall have their pay-to-script-hash transactions fully validated. Approximately 1,000 blocks are created in a week; 550 should, therefore, be approximately 55% of the network supporting the new feature. If a majority of hashing power does not support the new validation rules, then rollout will be postponed (or rejected if it becomes clear that a majority will never be achieved). ===520-byte limitation on serialized script size=== As a consequence of the requirement for backwards compatibility the serialized script is itself subject to the same rules as any other PUSHDATA operation, including the rule that no data greater than 520 bytes may be pushed to the stack. Thus it is not possible to spend a P2SH output if the redemption script it refers to is >520 bytes in length. For instance while the OP_CHECKMULTISIG opcode can itself accept up to 20 pubkeys, with 33-byte compressed pubkeys it is only possible to spend a P2SH output requiring a maximum of 15 pubkeys to redeem: 3 bytes + 15 pubkeys * 34 bytes/pubkey = 513 bytes. ==Reference Implementation== https://gist.github.com/gavinandresen/3966071 ==See Also== * https://bitcointalk.org/index.php?topic=46538 * The [[bip-0013.mediawiki|Address format for Pay to Script Hash BIP]] * M-of-N Multisignature Transactions [[bip-0011.mediawiki|BIP 11]] * [[bip-0016/qa.mediawiki|Quality Assurance test checklist]] == References == ================================================ FILE: bip-0017.mediawiki ================================================
  BIP: 17
  Layer: Consensus (soft fork)
  Title: OP_CHECKHASHVERIFY (CHV)
  Authors: Luke Dashjr 
  Status: Closed
  Type: Specification
  Assigned: 2012-01-18
  License: BSD-2-Clause
==Abstract== This BIP describes a new opcode (OP_CHECKHASHVERIFY) for the Bitcoin scripting system, and a new 'standard' transaction type that uses it to enables the receiver of bitcoins to specify the transaction type needed to re-spend them. ==Copyright== This BIP is licensed under the BSD 2-clause license. ==Motivation== The purpose of pay-to-script-hash is to move the responsibility for supplying the conditions to redeem a transaction from the sender of the funds to the redeemer. The benefit is allowing a sender to fund any arbitrary transaction, no matter how complicated, using a fixed-length 20-byte hash that is short enough to scan from a QR code or easily copied and pasted. ==Specification== OP_CHECKHASHVERIFY will re-define the existing OP_NOP2 opcode, and will function as follows when executed: * First, hash the end of the prior script (in the general case, scriptSig; if no prior script, a null string is hashed) beginning from the last evaluated OP_CODESEPARATOR onward (or from the beginning of the script, if no OP_CODESEPARATOR was present) * Then, compare this with the item on the top of the stack (if there is none, the script fails immediately) * If the hashes match, do nothing, proceed as if an OP_NOP; if they do not match, the script fails immediately. * Note that in the case of a matched hash, the top stack item (the hash being compared with) is not popped off the stack. This is for backward compatibility. This opcode reassignment shall be applied when validating transactions in blocks only with timestamps after February 23, 2012 (see the Backwards Compatibility section for details). A new standard transaction type that is relayed and included in mined blocks is defined: [20-byte-hash-value] OP_CHECKHASHVERIFY OP_DROP [20-byte-hash-value] shall be the push-20-bytes-onto-the-stack opcode (0x14) followed by exactly 20 bytes. This new transaction type is redeemed by a standard scriptSig: ...signatures... OP_CODESEPARATOR {script} Transactions that redeem these pay-to-script outpoints are only considered standard if they contain exactly one OP_CODESEPARATOR and the appended ''script'' is, itself, one of the other standard transaction types. ==Example== For example, the scriptPubKey and corresponding scriptSig for a one-signature-required transaction is: scriptSig: [signature] OP_CODESEPARATOR [pubkey] OP_CHECKSIG scriptPubKey: [20-byte-hash of {[pubkey] OP_CHECKSIG} ] OP_CHECKHASHVERIFY OP_DROP 2-of-3: scriptSig: [signatures...] OP_CODESEPARATOR 2 [pubkey1] [pubkey2] [pubkey3] 3 OP_CHECKMULTISIG scriptPubKey: [20-byte-hash of {2 [pubkey1] [pubkey2] [pubkey3] 3 OP_CHECKMULTISIG} ] OP_CHECKHASHVERIFY OP_DROP ==Rationale== This BIP replaces BIP 12 and BIP 16, which propose evaluating a Script from the stack after verifying its hash. The Motivation for this BIP (and BIP 13, the pay-to-script-hash address type) is somewhat controversial; several people feel that it is unnecessary, and complex/multisignature transaction types should be supported by simply giving the sender the complete {serialized script}. The author believes that this BIP will minimize the changes needed to all of the supporting infrastructure that has already been created to send funds to a base58-encoded-20-byte bitcoin addresses, allowing merchants and exchanges and other software to start supporting multisignature transactions sooner. There is a 1-confirmation attack on old implementations, but it is expensive and difficult in practice. The attack is: # Attacker creates a pay-to-script-hash transaction that is valid as seen by old software, but invalid for new implementation, and sends themselves some coins using it. # Attacker also creates a standard transaction that spends the pay-to-script transaction, and pays the victim who is running old software. # Attacker mines a block that contains both transactions. If the victim accepts the 1-confirmation payment, then the attacker wins because both transactions will be invalidated when the rest of the network overwrites the attacker's invalid block. The attack is expensive because it requires the attacker create a block that they know will be invalidated by the rest of the network. It is difficult because creating blocks is difficult and users should not accept 1-confirmation transactions for higher-value transactions. ==Backwards Compatibility== These transactions are non-standard to old implementations, which will (typically) not relay them nor include them in blocks. Old implementations will not validate that the {script}'s hash value matches when they validate blocks created by software that fully support this BIP. Avoiding a block-chain split by malicious pay-to-script transactions requires careful handling of one case: * A pay-to-script-hash transaction that is invalid for new clients/miners but valid for old clients/miners. To gracefully upgrade and ensure no long-lasting block-chain split occurs, more than 50% of miners must support full validation of the new transaction type and must switch from the old validation rules to the new rules at the same time. To judge whether or not more than 50% of hashing power supports this BIP, miners are asked to upgrade their software and put the string "p2sh/CHV" in the input of the coinbase transaction for blocks that they create. On February 8, 2012, the block-chain will be examined to determine the number of blocks supporting pay-to-script-hash for the previous 7 days. If at least 60% contain "p2sh/CHV" in their coinbase, then all blocks with timestamps after 23 Feb 2012, 00:00:00 GMT shall have their pay-to-script-hash transactions validated. If a majority of hashing power does not support the new validation rules, then rollout will be postponed (or rejected if it becomes clear that a majority will never be achieved). OP_NOP2 is used, so existing OP_EVAL (BIP 12) transactions in the block chain can still be redeemed. ==Reference Implementation== [https://gitorious.org/~Luke-Jr/bitcoin/luke-jr-bitcoin/commits/checkhashverify Validation, sending, and receiving for bitcoind git master] [https://gitorious.org/~Luke-Jr/bitcoin/luke-jr-bitcoin/commits/checkhashverify_backport Validation only for 0.3.19+] ==See Also== * The [[bip-0013.mediawiki|Address format for Pay to Script Hash BIP]] * [[bip-0011.mediawiki|M-of-N Multisignature Transactions (BIP 11)]] * Example BIP 17 transaction chain: [http://blockexplorer.com/tx/b8fd633e7713a43d5ac87266adc78444669b987a56b3a65fb92d58c2c4b0e84d a] [http://blockexplorer.com/tx/eb3b82c0884e3efa6d8b0be55b4915eb20be124c9766245bcc7f34fdac32bccb b] [http://blockexplorer.com/tx/055707ce7fea7b9776fdc70413f65ceec413d46344424ab01acd5138767db137 c] [http://blockexplorer.com/tx/6d36bc17e947ce00bb6f12f8e7a56a1585c5a36188ffa2b05e10b4743273a74b d] ================================================ FILE: bip-0018.mediawiki ================================================
  BIP: 18
  Layer: Consensus (soft fork)
  Title: hashScriptCheck
  Authors: Luke Dashjr 
  Status: Complete
  Type: Specification
  Assigned: 2012-01-27
  License: BSD-2-Clause
==Abstract== This BIP modifies the basic format of transaction inputs and outputs, replacing the current scriptSig and scriptPubKey (scripts executed to validate a transaction) with new contents: dataSig, scriptCheck, and hashScriptCheck. ==Copyright== This BIP is licensed under the BSD 2-clause license. ==Motivation== The purpose of pay-to-script-hash is to move the responsibility for supplying the conditions to redeem a transaction from the sender of the funds to the redeemer. The benefit is allowing a sender to fund any arbitrary transaction, no matter how complicated, using a fixed-length 20-byte hash that is short enough to scan from a QR code or easily copied and pasted. ==Specification== scriptSig and scriptPubKey are hereby deemed to be deprecated. Bitcoin-compatible clients MUST still continue to support them for compatibility, but it should not be used for any new transaction types. Services and people which send Bitcoins SHOULD continue to support old pubkey-based addresses for the time being. Services and people which receive Bitcoins MAY continue to generate and use old pubkey-based addresses. To replace these, there are 3 new elements: * dataSig is included in place of scriptSig in transaction inputs, and contains multiple serialized data elements * scriptCheck is the final element of dataSig, and is executed with the preceding dataSig elements preloaded onto the stack (the element immediately before scriptCheck is the top of the stack) * hashScriptCheck is included in place of scriptPubKey in transaction outputs, to specify the hash of the scriptCheck allowed to redeem it dataSig is to be encoded the same as a push-only script. hashScriptCheck must be encoded exactly so: 0xa9 0x14 (20-byte-hash-value) 0x87 This can be interpreted by legacy (pre-BIP 18) clients as the following script: OP_HASH160 [20-byte-hash-value] OP_EQUAL If this template is not matched exactly OR the transaction is in a block with a timestamp before the hashScriptCheck activation date, validation MUST proceed in backward-compatibility mode, using scriptSig+scriptPubKey rather than dataSig+scriptCheck+hashScriptCheck. A hashScriptCheck-compliant input is valid only if: * dataSig MUST NOT contain any operations other than "push data" (it is data, not a script; no mixing scriptSig with hashScriptCheck) * scriptCheck MUST hash (using Bitcoin's Hash160 algorithm) to the output's hashScriptCheck. * scriptCheck MUST be executed with the dataSig-based stack specified above (ie, not including scriptCheck itself) to perform validation (this does not imply clients are required to validate transactions). * scriptCheck must not abort, and must leave a true value on the top of the stack. This is the current behaviour for scriptSig+scriptPubKey. The new scriptCheck SHOULD be checked against "standard transaction" templates by miners. For example, the hashScriptCheck and corresponding dataSig for a one-signature-required transaction is: scriptCheck: [pubkey] OP_CHECKSIG dataSig: [signature] {[pubkey] OP_CHECKSIG} hashScriptCheck: [20-byte-hash of {[pubkey] OP_CHECKSIG}] ===Signature operation limits for scriptCheck=== Signature operations in scriptCheck do not follow the same rules previously applied to scriptSig and scriptPubKey. Instead, they shall contribute to the maximum number allowed per block (20,000) as follows: # OP_CHECKSIG and OP_CHECKSIGVERIFY count as 1 signature operation, whether or not they are evaluated. # OP_CHECKMULTISIG and OP_CHECKMULTISIGVERIFY immediately preceded by OP_1 through OP_16 are counted as 1 to 16 signature operation, whether or not they are evaluated. # All other OP_CHECKMULTISIG and OP_CHECKMULTISIGVERIFY are counted as 20 signature operations. Examples: +3 signature operations: 2 [pubkey1] [pubkey2] [pubkey3] 3 OP_CHECKMULTISIG +22 signature operations OP_CHECKSIG OP_IF OP_CHECKSIGVERIFY OP_ELSE OP_CHECKMULTISIGVERIFY OP_ENDIF ==Rationale== This BIP replaces BIPs 12 and 17, which propose extensions to the Script system to allow scriptPubKey to outsource its verification. It also replaces BIP 16, which is identical in terms of protocol, but suggests a specific implementation and does not deprecate scriptPubKey to maintain protocol consistency. The Motivation for this BIP (and BIP 13, the pay-to-script-hash address type) is somewhat controversial; several people feel that it is unnecessary, and complex/multisignature transaction types should be supported by simply giving the sender the complete {serialized script}. The author believes that this BIP will minimize the changes needed to all of the supporting infrastructure that has already been created to send funds to a base58-encoded-20-byte bitcoin addresses, allowing merchants and exchanges and other software to start supporting multisignature transactions sooner. The signature operation counting rules are intended to be easy and quick to implement by statically scanning scriptCheck. Bitcoin imposes a maximum-number-of-signature-operations per block to prevent denial-of-service attacks on miners. If there was no limit, a rogue miner might broadcast a block that required hundreds of thousands of ECDSA signature operations to validate, and it might be able to get a head start computing the next block while the rest of the network worked to validate the current one. There is a 1-confirmation attack on old implementations, but it is expensive and difficult in practice. The attack is: # Attacker creates a pay-to-script-hash transaction that is valid when interpreted as scriptPubKey, but contains an invalid scriptCheck, and sends themselves some coins using it. # Attacker also creates a standard transaction that spends the pay-to-script transaction, and pays the victim who is running old software. # Attacker mines a block that contains both transactions. If the victim accepts the 1-confirmation payment, then the attacker wins because both transactions will be invalidated when the rest of the network overwrites the attacker's invalid block. The attack is expensive because it requires the attacker create a block that they know will be invalidated by the rest of the network. It is difficult because creating blocks is difficult and users should not accept 1-confirmation transactions for higher-value transactions. ==Backwards Compatibility== hashScriptCheck transactions are non-standard to old implementations, which will (typically) not relay them nor include them in blocks. Old implementations will validate that scriptCheck's hash value matches when they validate blocks created by software that fully support this BIP, but will do no other validation. Avoiding a block-chain split by malicious pay-to-script transactions requires careful handling of one case: * A pay-to-script-hash transaction that is invalid for new clients/miners but valid for old clients/miners. To gracefully upgrade and ensure no long-lasting block-chain split occurs, more than 50% of miners must support full validation of the new transaction type and must switch from the old validation rules to the new rules at the same time. To judge whether or not more than 50% of hashing power supports this BIP, miners are asked to upgrade their software and put the string "/P2SH/" in the input of the coinbase transaction for blocks that they create. At 00:00:00 UTC on 15 Mar 2012, the block-chain will be examined to determine the number of blocks supporting pay-to-script-hash for the previous 7 days. If 550 or more contain "/P2SH/" in their coinbase, then all blocks with timestamps after 00:00:00 UTC on 1 Apr 2012 shall have their pay-to-script-hash transactions fully validated. Approximately 1,000 blocks are created in a week; 550 should, therefore, be approximately 55% of the network supporting the new feature. If a majority of hashing power does not support the new validation rules, then rollout will be postponed (or rejected if it becomes clear that a majority will never be achieved). ==Forwards Compatibility == The first two bytes of hashScriptCheck specify the hash algorithm and length used to verify scriptCheck. This BIP only allows Bitcoin's Hash160 algorithm, but leaves open the possibility of a future BIP implementing others. ==Reference Implementation== https://github.com/gavinandresen/bitcoin-git/tree/pay_to_script_hash ==See Also== * The [[bip-0013.mediawiki|Address format for Pay to Script Hash BIP]] * [[bip-0016.mediawiki|BIP 16 - Pay to Script Hash (aka "/P2SH/")]] * M-of-N Multisignature Transactions [[bip-0011.mediawiki|BIP 11]] ================================================ FILE: bip-0019.mediawiki ================================================
  BIP: 19
  Layer: Applications
  Title: M-of-N Standard Transactions (Low SigOp)
  Authors: Luke Dashjr 
  Status: Closed
  Type: Specification
  Assigned: 2012-01-30
  License: BSD-2-Clause
==Abstract== This BIP proposes M-of-N-signatures required transactions as a new 'standard' transaction type using the existing scripting system without significant modifications. ==Copyright== This BIP is licensed under the BSD 2-clause license. ==Motivation== Enable secured wallets, escrow transactions, and other use cases where redeeming funds requires more than a single signature. A couple of motivating use cases: * A wallet secured by a "wallet protection service" (WPS). 2-of-2 signatures required transactions will be used, with one signature coming from the (possibly compromised) computer with the wallet and the second signature coming from the WPS. When sending protected bitcoins, the user's bitcoin client will contact the WPS with the proposed transaction and it can then contact the user for confirmation that they initiated the transaction and that the transaction details are correct. Details for how clients and WPS's communicate are outside the scope of this BIP. Side note: customers should insist that their wallet protection service provide them with copies of the private key(s) used to secure their wallets that they can safely store off-line, so that their coins can be spent even if the WPS goes out of business. * Three-party escrow (buyer, seller and trusted dispute agent). 2-of-3 signatures required transactions will be used. The buyer and seller and agent will each provide a public key, and the buyer will then send coins into a 2-of-3 CHECKMULTISIG transaction and send the seller and the agent the transaction id. The seller will fulfill their obligation and then ask the buyer to co-sign a transaction ( already signed by seller ) that sends the tied-up coins to him (seller).
If the buyer and seller cannot agree, then the agent can, with the cooperation of either buyer or seller, decide what happens to the tied-up coins. Details of how buyer, seller, and agent communicate to gather signatures or public keys are outside the scope of this BIP. ==Specification== Two new standard transaction types (scriptPubKey) that are relayed by clients and included in mined blocks. N-of-N (all signatures required): ( {pubkey} OP_CHECKSIGVERIFY )*n N-of-M (some signatures required): {pubkey} OP_CHECKSIG ( OP_SWAP {pubkey} OP_CHECKSIG OP_ADD )*(n-1) n OP_EQUAL But only for n less than or equal to 3. These transactions are redeemed using a standard scriptSig: ...signatures... The current Satoshi bitcoin client does not relay or mine transactions with scriptSigs larger than 200 bytes; to accommodate 3-signature transactions, this will be increased to 500 bytes. ===Templates=== scriptPubKey: {pubkey} OP_CHECKSIGVERIFY {pubkey} OP_CHECKSIGVERIFY {pubkey} OP_CHECKSIGVERIFY {pubkey} OP_CHECKSIGVERIFY {pubkey} OP_CHECKSIGVERIFY {pubkey} OP_CHECKSIG OP_SWAP {pubkey} OP_CHECKSIG OP_ADD {n} OP_EQUAL {pubkey} OP_CHECKSIG OP_SWAP {pubkey} OP_CHECKSIG OP_ADD OP_SWAP {pubkey} OP_CHECKSIG OP_ADD {n} OP_EQUAL scriptSig: ...signatures... up to 500 bytes ==Rationale== OP_CHECKMULTISIG is already an enabled opcode, and is the most straightforward way to support several important use cases. This is already specified in [[bip-0011.mediawiki|BIP 0011]]. However, each OP_CHECKMULTISIG counts toward the block limit as 20 sigops, which only allows 1000 total multisig transactions in a block. Using OP_CHECKSIG only counts as 1 per signature, so can scale better. ==Implementation== All used operations are already supported by old clients and miners as a non-standard transaction type. ================================================ FILE: bip-0020.mediawiki ================================================
  BIP: 20
  Layer: Applications
  Title: URI Scheme
  Authors: Luke Dashjr 
  Status: Closed
  Type: Specification
  Assigned: 2011-01-10
  License: BSD-2-Clause
  Proposed-Replacement: 21
BIP 0020 is based off an earlier document by Nils Schneider. '''And has been replaced by BIP 0021''' ==Abstract== This BIP proposes a URI scheme for making Bitcoin payments. ==Copyright== This BIP is licensed under the BSD 2-clause license. ==Motivation== The purpose of this URI scheme is to enable users to easily make payments by simply clicking links on webpages or scanning QR Codes. ==Specification== === General rules for handling (important!) === Bitcoin clients MUST NOT act on URIs without getting the user's authorization. They SHOULD require the user to manually approve each payment individually, though in some cases they MAY allow the user to automatically make this decision. === Operating system integration === Graphical bitcoin clients SHOULD register themselves as the handler for the "bitcoin:" URI scheme by default, if no other handler is already registered. If there is already a registered handler, they MAY prompt the user to change it once when they first run the client. === BNF grammar === (See also [[#Simpler syntax|a simpler representation of syntax]]) bitcoinurn = "bitcoin:" bitcoinaddress [ ";version=" bitcoinversion ] [ "?" bitcoinparams ] bitcoinaddress = base58 *base58 bitcoinversion = "1.0" bitcoinparams = *bitcoinparam bitcoinparam = amountparam | labelparam | messageparam | sendparam | otherparam amountparam = "amount=" amount amount = amountdecimal | amounthex amountdecimal = *digit [ "." *digit ] [ "X" *digit ] amounthex = "x" *hexdigit [ "." *hexdigit ] [ "X" *hexdigit ] labelparam = "label=" *pchar messageparam = "message=" *pchar sendparam = "send=" *pchar otherparam = pchar *pchar "=" *pchar === Query Keys === *label: Label for that address (e.g. name of receiver) *address: bitcoin address *message: message that is shown to the user after scanning the QR code *size: amount of base bitcoin units ([[#Transfer amount/size|see below]]) *send: used to send bitcoin, rather than to request them *(others): optional, for future extensions ==== Transfer amount/size ==== If an amount is provided, it may be specified either in decimal or, when prefixed with a single "x" character, hexadecimal. The number SHOULD be followed by "X" <digits> to signify an exponent to the base multiplier. Thus, "X8" multiplies your number by 100,000,000. For decimal values, this means the standard BTC unit. For hexadecimal values, this means ᵇTBC units (which are equivalent to 42.94967296 BTC). If exponent is omitted, implementations SHOULD assume X8 for decimal numbers, and X4 for hexadecimal numbers. I.e. amount=50.00 is treated as 50 BTC, and amount=x40 is treated as 40 TBC. When specifying bitcoin base units, "X0" SHOULD be used. Bitcoin clients MAY display the amount in any format that is not intended to deceive the user. They SHOULD choose a format that is foremost least confusing, and only after that most reasonable given the amount requested. For example, so long as the majority of users work in BTC units, values should always be displayed in BTC by default, even if mBTC or TBC would otherwise be a more logical interpretation of the amount. == Rationale == ===Payment identifiers, not person identifiers=== Current best practices are that a unique address should be used for every transaction. Therefore, a URI scheme should not represent an exchange of personal information, but a one-time payment. ===Accessibility (URI scheme name)=== Should someone from the outside happen to see such a URI, the URI scheme name already gives a description. A quick search should then do the rest to help them find the resources needed to make their payment. Other proposed names sound much more cryptic; the chance that someone googles that out of curiosity are much slimmer. Also, very likely, what he will find are mostly technical specifications - not the best introduction to bitcoin. ==Forward compatibility== We want URIs generated in 2011 to still work in 2036: think about extensibility. Of course we can make only educated guesses about the future, but don't act as if there is none. This should be the best we can do, but it should not be seen as set in stone. Make it possible for later generations to improve our work, to mend our errors, without breaking the URIs created now. == Appendix == === Simpler syntax === This section is non-normative and does not cover all possible syntax. Please see the [[#BNF grammar|BNF grammar]] above for the normative syntax. [foo] means optional, <bar> are placeholders
 bitcoin:
[;version=1.0][?amount=][?label=
=== Examples === Just the address: bitcoin:1NS17iag9jJgTHD1VXjvLCEnZuQ3rJED9L Address with name: bitcoin:1NS17iag9jJgTHD1VXjvLCEnZuQ3rJED9L?label=Luke-Jr Request 20.30 BTC to "Luke-Jr": bitcoin:1NS17iag9jJgTHD1VXjvLCEnZuQ3rJED9L?amount=20.3X8&label=Luke-Jr Request 400 TBC: bitcoin:1NS17iag9jJgTHD1VXjvLCEnZuQ3rJED9L?amount=x400X4 Request 4000 TBC: bitcoin:1NS17iag9jJgTHD1VXjvLCEnZuQ3rJED9L?amount=x4X7 Request 5 uBTC: bitcoin:1NS17iag9jJgTHD1VXjvLCEnZuQ3rJED9L?amount=5X2 Request 50 BTC with message: bitcoin:1NS17iag9jJgTHD1VXjvLCEnZuQ3rJED9L?amount=50X8&label=Luke-Jr&message=Donation%20for%20project%20xyz Send 1 BTC: bitcoin:1NS17iag9jJgTHD1VXjvLCEnZuQ3rJED9L?amount=1X8&send=S4b3N3oGqDqR5jNuxEvDwf Characters must be URI encoded properly. ===Sending money via private key=== To send a payment to someone else first construct a new keypair. You may want to use a [[mini private key format]], or you may also use a full private key for more security depending on the amount being sent and how long you expect to pass before a claim. Now create and publish a transaction with an output of the amount you wish to send. Use this script in that output:
  OP_CHECKSIG
Construct an address from the public key. Encode the URI as below:
 bitcoin:
?send=
You may optionally include amount or message fields as well. In a wallet to claim money sent this way search for an incoming transaction with the output script form above, where <address> matches the public key in the script. When you find the transaction create a claim transaction with an input script of this form:
 
This claims the money you were sent. Until your claim transaction has confirmed the sender may take their money back. == Reference Implementations == === Bitcoin clients === * [[Spesmilo]] supports all valid Bitcoin URIs, with Windows and KDE integration === Parsing amount === ==== ECMAScript ====
 reAmount = /^(([\d.]+)(X(\d+))?|x([\da-f]*)(\.([\da-f]*))?(X([\da-f]+))?)$/i;
 function parseAmount(txt) {
    var m = txt.match(reAmount);
    return m[5] ? (
        (
            parseInt(m[5], 16) +
            (m[7] ? (parseInt(m[7], 16) * Math.pow(16, -(m[7].length))) : 0)
        ) * (
            m[9] ? Math.pow(16, parseInt(m[9], 16)) : 0x10000
        )
    ) : (
            m[2]
        *
            (m[4] ? Math.pow(10, m[4]) : 1e8)
    );
 }
==== Python ====
 m = re.match(r'^(([\d.]+)(X(\d+))?|x([\da-f]*)(\.([\da-f]*))?(X([\da-f]+))?)$', amount, re.IGNORECASE)
 if m.group(5):
     amount = float(int(m.group(5), 16))
     if m.group(7):
         amount += float(int(m.group(7), 16)) * pow(16, -(len(m.group(7))))
     if m.group(9):
         amount *= pow(16, int(m.group(9), 16))
     else:
         amount *= 0x10000
 else:
     amount = Decimal(m.group(2))
     if m.group(4):
         amount *= 10 ** int(m.group(4))
     else:
         amount *= 100000000
==== C# ====
 Regex amountExpression = new Regex(@"^(([\d.]+)(X(\d+))?|x([\da-f]*)(\.([\da-f]*))?(X([\da-f]+))?)$", RegexOptions.IgnoreCase);
 Match match = amountExpression.Match(value);
 if (match.Success)
 {
     if (match.Groups[5].Success)
     {
         long hexDecimal = 0;
         if (match.Groups[7].Success)
             hexDecimal = Convert.ToInt64(match.Groups[7].Value, 16) * (long)Math.Pow(16, -match.Groups[7].Length);

         long hexExponent = 0x10000;
         if (match.Groups[9].Success)
             hexExponent = (long)Math.Pow(16, Convert.ToInt32(match.Groups[9].Value, 16));

         Amount = (Convert.ToInt64(match.Groups[5].Value, 16) + hexDecimal) * hexExponent;
     }
     else
     {
         long decimalExponent = 100000000;
         if (match.Groups[4].Success)
             decimalExponent = (long)Math.Pow(10, int.Parse(match.Groups[4].Value));
         Amount = (long)(decimal.Parse(match.Groups[2].Value) * decimalExponent);
     }
 }
================================================ FILE: bip-0021.mediawiki ================================================
  BIP: 21
  Layer: Applications
  Title: URI Scheme
  Authors: Nils Schneider 
           Matt Corallo 
  Status: Closed
  Type: Specification
  Assigned: 2012-01-29
  Replaces: 20
  Proposed-Replacement: 321
=Superseded by BIP 321= This BIP has been superseded and replaced with BIP 321. Please see [[bip-0321.mediawiki|BIP 321]] instead. =Original BIP= This BIP is a modification of an earlier [[bip-0020.mediawiki|BIP 0020]] by Luke Dashjr. BIP 0020 was based off an earlier document by Nils Schneider. The alternative payment amounts in BIP 0020 have been removed. ==Abstract== This BIP proposes a URI scheme for making Bitcoin payments. ==Motivation== The purpose of this URI scheme is to enable users to easily make payments by simply clicking links on webpages or scanning QR Codes. ==Specification== === General rules for handling (important!) === Bitcoin clients MUST NOT act on URIs without getting the user's authorization. They SHOULD require the user to manually approve each payment individually, though in some cases they MAY allow the user to automatically make this decision. === Operating system integration === Graphical bitcoin clients SHOULD register themselves as the handler for the "bitcoin:" URI scheme by default, if no other handler is already registered. If there is already a registered handler, they MAY prompt the user to change it once when they first run the client. === General Format === Bitcoin URIs follow the general format for URIs as set forth in RFC 3986. The path component consists of a bitcoin address, and the query component provides additional payment options. Elements of the query component may contain characters outside the valid range. These must first be encoded according to UTF-8, and then each octet of the corresponding UTF-8 sequence must be percent-encoded as described in RFC 3986. === ABNF grammar === (See also [[#simpler-syntax|a simpler representation of syntax]]) bitcoinurn = "bitcoin:" bitcoinaddress [ "?" bitcoinparams ] bitcoinaddress = *base58 bitcoinparams = bitcoinparam [ "&" bitcoinparams ] bitcoinparam = [ amountparam / labelparam / messageparam / otherparam / reqparam ] amountparam = "amount=" *digit [ "." *digit ] labelparam = "label=" *qchar messageparam = "message=" *qchar otherparam = qchar *qchar [ "=" *qchar ] reqparam = "req-" qchar *qchar [ "=" *qchar ] Here, "qchar" corresponds to valid characters of an RFC 3986 URI query component, excluding the "=" and "&" characters, which this BIP takes as separators. The scheme component ("bitcoin:") is case-insensitive, and implementations must accept any combination of uppercase and lowercase letters. The rest of the URI is case-sensitive, including the query parameter keys. === Query Keys === *label: Label for that address (e.g. name of receiver) *address: bitcoin address *message: message that describes the transaction to the user ([[#Examples|see examples below]]) *(others): optional, for future extensions ==== Transfer amount ==== If an amount is provided, it MUST be specified in decimal BTC. All amounts MUST contain no commas and use a period (.) as the separating character to separate whole numbers and decimal fractions. I.e. amount=50.00 or amount=50 is treated as 50 BTC, and amount=50,000.00 is invalid. Bitcoin clients MAY display the amount in any format that is not intended to deceive the user. They SHOULD choose a format that is foremost least confusing, and only after that most reasonable given the amount requested. For example, so long as the majority of users work in BTC units, values should always be displayed in BTC by default, even if mBTC or TBC would otherwise be a more logical interpretation of the amount. == Rationale == ===Payment identifiers, not person identifiers=== Current best practices are that a unique address should be used for every transaction. Therefore, a URI scheme should not represent an exchange of personal information, but a one-time payment. ===Accessibility (URI scheme name)=== Should someone from the outside happen to see such a URI, the URI scheme name already gives a description. A quick search should then do the rest to help them find the resources needed to make their payment. Other proposed names sound much more cryptic; the chance that someone googles that out of curiosity are much slimmer. Also, very likely, what he will find are mostly technical specifications - not the best introduction to bitcoin. ==Forward compatibility== Variables which are prefixed with a req- are considered required. If a client does not implement any variables which are prefixed with req-, it MUST consider the entire URI invalid. Any other variables which are not implemented, but which are not prefixed with a req-, can be safely ignored. ==Backward compatibility== As this BIP is written, several clients already implement a bitcoin: URI scheme similar to this one, however usually without the additional "req-" prefix requirement. Thus, it is recommended that additional variables prefixed with req- not be used in a mission-critical way until a grace period of 6 months from the finalization of this BIP has passed in order to allow client developers to release new versions, and users of old clients to upgrade. == Appendix == === Simpler syntax === This section is non-normative and does not cover all possible syntax. Please see the BNF grammar above for the normative syntax. [foo] means optional, <bar> are placeholders bitcoin:
[?amount=][?label=Subscript_1. The unused witness item(s) before the Subscript_1 are used as Input Stack to feed to the MASTScript. (Similar to P2WSH in BIP141) The script fails with one of the following conditions: * MAST Script is malformed (i.e. not enough data provided for the last push operation). Individual Subscript might be malformed, as long as they are serialized into a valid MAST Script * Size of MAST Script is larger than 10,000 bytes * Size of any one of the Input Stack item is larger than 520 bytes * Number of non-push operations (nOpCount) is more than 201. nOpCount is the sum of the number of non-push operations in MAST Script (counted in the same way as P2WSH witnessScript), number of Subscript (Y), and Depth of the Merkle tree. The MAST Script is then evaluated with the Input Stack (with some new or redefined opcodes described in BIPXXX). The evaluation must not fail, and result in an exactly empty stack. Counting of SigOpsCost is based on the MAST Script, described in BIPYYY. == Rationale == === MAST Structure === This proposal is a restricted case of more general MAST. In a general MAST design, users may freely assign one or more script branches for execution. In this proposal, only one branch is allowed for execution, and users are required to transform a complicated condition into several mutually exclusive branches. For example, if the desired redeem condition is: (A or B) and (C or D or E) and (F or G) In a general MAST design, the 7 branches (A to G) will form a 3-level Merkle tree, plus an "overall condition" describing the relationship of different branches. In redemption, the "overall condition", executed branches (e.g. B, D, F), and Merkle path data will be provided for validation. In the current proposal, the user has to transform the redeem condition into 12 mutually exclusive branches and form a 4-level Merkle tree, and present only one branch in redemption: A and C and F B and C and F A and D and F . . B and E and G One way to implement the general MAST design is using a combination of OP_EVAL, OP_CAT, and OP_HASH256. However, that will suffer from the problems of OP_EVAL, including risks of indefinite program loop and inability to do static program analysis. A complicated implementation is required to fix these problems and is difficult to review. The advantages of the current proposal are: * Subscript are located at a fixed position in the witness stack. This allows static program analysis, such as static SigOpsCost counting and early termination of scripts with disabled opcodes. * If different parties in a contract do not want to expose their scripts to each other, they may provide only H(Subscript) and keep the Subscript private until redemption. * If they are willing to share the actual scripts, they may combine them into one Subscript for each branch, saving some nOpCount and a few bytes of witness space. There are some disadvantages, but only when the redemption condition is very complicated: * It may require more branches than a general MAST design (as shown in the previous example) and take more witness space in redemption * Creation and storage of the MAST structure may take more time and space. However, such additional costs affect only the related parties in the contract but not any other Bitcoin users. === MAST Version === This proposal allows users to indicate the version of scripting language in the witness, which is cheaper than doing that in scriptPubKey or scriptSig. Undefined versions remain anyone-can-spend and are reserved for future expansions. A new version could be used for relaxing constraints (e.g. the 10,000 bytes size limit of MAST Script), adding or redefining opcodes, or even introducing a completely novel scripting system. === nOpCount limit === In version 0 MAST, the extra hashing operations in calculating the MAST Root are counted towards the 201 nOpCount limit to prevent abusive use. This limitation is not applied to undefined MAST Version for flexibility, but it is constrained by the 255 Subscript and 32 Depth limits. === Script evaluation === This proposal requires script evaluation resulting in an empty stack, instead of a single TRUE value as in P2WSH. This allows each party in a contract to provide its own Subscript, and demonstrate the required Input Stack to clean up its own Subscript. In this case, order of the Subscript is not important since the overall objective is to clean up the stack after evaluation. == Examples == === Calculation of MAST Root === Subscript: SA = 1 EQUALVERIFY (0x5188) SB = 2 EQUALVERIFY (0x5288) SC = 3 EQUALVERIFY (0x5388) SD = 4 EQUALVERIFY (0x5488) SE = 5 EQUALVERIFY (0x5588) SF = 6 EQUALVERIFY (0x5688) SG = 7 EQUALVERIFY (0x5788) SH = 8 EQUALVERIFY (0x5888) M = RETURN "Hello" (0x6a0548656c6c6f) Hash: HA = H(0x01|H(SA)) = H(0x015acb54166e0db370cd1b05a29120373568dacea2abc3748459ec3da2106e4b4e) = 0xd385d7268ad7e1ec51660f833d54787d2d8d79b6b1809d9c1d06c9e71f7be204 HB = H(0x02|H(SB)|H(SC)) = 0x7cbfa08e44ea9f4f996873be95d9bffd97d4b91a5af32cc5f64efb8461727cdd HF = H(0x03|H(SD)|H(SE)|H(SF)) = 0x4611414355945a7c2fcc62a53a0004821b87e68f93048ffba7a55a3cb1e9783b HG = H(0x01|H(SG)) = 0xaa5fbdf58264650eadec33691ba1e7606d0a62f570eea348a465c55bc86ffc10 HC = H(0x01|H(M)) = 0x70426d480d5b28d93c5be54803681f99abf4e8df4eab4dc87aaa543f0d138159 HD = H(0x0x|H(SH)) = 0x8482f6c9c3fe90dd4d533b4efedb6a241b95ec9267d1bd5aaaee36d2ce2dd6da HE = H(HA|HB) = 0x049b9f2f94f0a9bdea624e39cd7d6b27a365c6a0545bf0e9d88d86eff4894210 HH = H(HC|HD) = 0xc709fdc632f370f3367da45378d1cf430c5fda6805e731ad5761c213cf2d276e HI = H(HE|HF) = 0xead5e1a1e7e41b77b794f091df9be3f0e9f41d47304eb43dece90688f69843b7 HJ = H(HG|HH) = 0xd00fc690c4700d0f983f9700740066531ea826b21a4cbc62f80317261723d477 Script Root = H(HI|HJ) = 0x26d5235d20daf1440a15a248f5b5b4f201392128072c55afa64a26ccc6f56bd9 MAST Root = H(MAST Version|Script Root) = H(0x0000000026d5235d20daf1440a15a248f5b5b4f201392128072c55afa64a26ccc6f56bd9) = 0xb4b706e0c02eab9aba58419eb7ea2a286fb1c01d7406105fc12742bf8a3f97c9 The scriptPubKey with native witness program is: 1 <0xb4b706e0c02eab9aba58419eb7ea2a286fb1c01d7406105fc12742bf8a3f97c9> (0x5120b4b706e0c02eab9aba58419eb7ea2a286fb1c01d7406105fc12742bf8a3f97c9) To redeem with the SD|SE|SF branch, the witness is Script_stack_1: 0x06 Script_stack_2: 0x05 Script_stack_3: 0x04 Subscript_1: 0x5488 Subscript_2: 0x5588 Subscript_3: 0x5688 Position: 0x01 (HF is the second hash in its level) Path (HE|HJ): 0x049b9f2f94f0a9bdea624e39cd7d6b27a365c6a0545bf0e9d88d86eff4894210d00fc690c4700d0f983f9700740066531ea826b21a4cbc62f80317261723d477 Metadata: 0x03 (3 Subscript) === Imbalance MAST === When constructing a MAST, if the user believes that some of the branches are more likely to be executed, they may put them closer to the Script Root. It will save some witness space when the preferred branches are actually executed. === Escrow with Timeout === The following is the "Escrow with Timeout" example in [[bip-0112.mediawiki|BIP112]]: IF 2 3 CHECKMULTISIG ELSE "30d" CHECKSEQUENCEVERIFY DROP CHECKSIG ENDIF Using compressed public key, the size of this script is 150 bytes. With MAST, this script could be broken down into 2 mutually exclusive branches:In BIPXXX, it is proposed that CHECKLOCKTIMEVERIFY and CHECKSEQUENCEVERIFY will pop the top stack item 2 3 CHECKMULTISIGVERIFY (105 bytes) "30d" CHECKSEQUENCEVERIFY CHECKSIGVERIFY (42 bytes) Since only one branch will be published, it is more difficult for a blockchain analyst to determine the details of the escrow. === Hashed Time-Lock Contract === The following is the "Hashed TIme-Lock Contract" example in [[bip-0112.mediawiki|BIP112]]: HASH160 DUP EQUAL IF "24h" CHECKSEQUENCEVERIFY 2DROP ELSE EQUAL NOTIF "Timestamp" CHECKLOCKTIMEVERIFY DROP ENDIF ENDIF CHECKSIG To create a MAST Root, it is flattened to 3 mutually exclusive branches: HASH160 EQUALVERIFY "24h" CHECKSEQUENCEVERIFY CHECKSIGVERIFY HASH160 EQUALVERIFY CHECKSIGVERIFY "Timestamp" CHECKLOCKTIMEVERIFY CHECKSIGVERIFY which significantly improves readability and reduces the witness size when it is redeemed. === Large multi-signature constructs === The current CHECKMULTISIG supports up to 20 public keys. Although it is possible to extend it beyond 20 keys by using multiple CHECKSIGs and IF/ELSE conditions, the construction could be very complicated and soon use up the 10,000 bytes and 201 nOpCount limit. With MAST, large and complex multi-signature constructs could be flattened to many simple CHECKMULTISIGVERIFY conditions. For example, a 3-of-2000 multi-signature scheme could be expressed as 1,331,334,000 3-of-3 CHECKMULTISIGVERIFY, which forms a 31-level MAST. The scriptPubKey still maintains a fixed size of 34 bytes, and the redemption witness will be very compact, with less than 1,500 bytes. === Commitment of non-consensus enforced data === Currently, committing non-consensus enforced data in the scriptPubKey requires the use of OP_RETURN which occupies additional block space. With MAST, users may commit such data as a branch. Depends on the number of executable branches, inclusion of such a commitment may incur no extra witness space, or 32 bytes at most. An useful case would be specifying "message-signing keys", which are not valid for spending, but allow users to sign any message without touching the cold storage "funding key". == Backward compatibility == As a soft fork, older software will continue to operate without modification. Non-upgraded nodes, however, will consider MAST programs as anyone-can-spend scripts. Wallets should always be wary of anyone-can-spend scripts and treat them with suspicion. == Deployment == This BIP depends on [[bip-0141.mediawiki|BIP141]] and will be deployed by version-bits [[bip-0009.mediawiki|BIP9]] after BIP141 is enforced. Exact details TBD. == Credits == The idea of MAST originates from Russell O’Connor, Pieter Wuille, and [https://bitcointalk.org/index.php?topic=255145.msg2757327#msg2757327 Peter Todd]. == Reference Implementation == https://github.com/jl2012/bitcoin/tree/bip114v2 (WIP) //New rules apply if version byte is 1 and witness program size is 32 bytes if (witversion == 1 && program.size() == 32 && (flags & SCRIPT_VERIFY_MAST)) { CHashWriter sRoot(SER_GETHASH, 0); CHashWriter sScriptHash(SER_GETHASH, 0); uint32_t nMASTVersion = 0; size_t stacksize = witness.stack.size(); if (stacksize < 4) return set_error(serror, SCRIPT_ERR_INVALID_MAST_STACK); std::vector metadata = witness.stack.back(); // The last witness stack item is metadata if (metadata.size() < 1 || metadata.size() > 5) return set_error(serror, SCRIPT_ERR_INVALID_MAST_STACK); // The first byte of metadata is the number of subscripts (1 to 255) uint32_t nSubscript = static_cast(metadata[0]); if (nSubscript == 0 || stacksize < nSubscript + 3) return set_error(serror, SCRIPT_ERR_INVALID_MAST_STACK); int nOpCount = nSubscript; // Each condition consumes a nOpCount sScriptHash << metadata[0]; // The rest of metadata is MAST version in minimally-coded unsigned little endian int if (metadata.back() == 0) return set_error(serror, SCRIPT_ERR_INVALID_MAST_STACK); if (metadata.size() > 1) { for (size_t i = 1; i != metadata.size(); ++i) nMASTVersion |= static_cast(metadata[i]) << 8 * (i - 1); } // Unknown MAST version is non-standard if (nMASTVersion > 0 && flags & SCRIPT_VERIFY_DISCOURAGE_UPGRADABLE_WITNESS_PROGRAM) return set_error(serror, SCRIPT_ERR_DISCOURAGE_UPGRADABLE_WITNESS_PROGRAM); sRoot << nMASTVersion; // The second last witness stack item is the pathdata // Size of pathdata must be divisible by 32 (0 is allowed) // Depth of the Merkle tree is implied by the size of pathdata, and must not be greater than 32 std::vector pathdata = witness.stack.at(stacksize - 2); if (pathdata.size() & 0x1F) return set_error(serror, SCRIPT_ERR_INVALID_MAST_STACK); unsigned int depth = pathdata.size() >> 5; if (depth > 32) return set_error(serror, SCRIPT_ERR_INVALID_MAST_STACK); // Each level of Merkle tree consumes a nOpCount // Evaluation of version 0 MAST terminates early if there are too many nOpCount // Not enforced in unknown MAST version for upgrade flexibility nOpCount = nOpCount + depth; if (nMASTVersion == 0 && nOpCount > MAX_OPS_PER_SCRIPT) return set_error(serror, SCRIPT_ERR_OP_COUNT); // path is a vector of 32-byte hashes std::vector path; path.resize(depth); for (unsigned int j = 0; j < depth; j++) memcpy(path[j].begin(), &pathdata[32 * j], 32); // The third last witness stack item is the positiondata // Position is in minimally-coded unsigned little endian int std::vector positiondata = witness.stack.at(stacksize - 3); if (positiondata.size() > 4) return set_error(serror, SCRIPT_ERR_INVALID_MAST_STACK); uint32_t position = 0; if (positiondata.size() > 0) { if (positiondata.back() == 0) return set_error(serror, SCRIPT_ERR_INVALID_MAST_STACK); for (size_t k = 0; k != positiondata.size(); ++k) position |= static_cast(positiondata[k]) << 8 * k; } // Position value must not exceed the number of leaves at the depth if (depth < 32) { if (position >= (1U << depth)) return set_error(serror, SCRIPT_ERR_INVALID_MAST_STACK); } // Sub-scripts are located before positiondata for (size_t i = stacksize - nSubscript - 3; i <= stacksize - 4; i++) { CScript subscript(witness.stack.at(i).begin(), witness.stack.at(i).end()); // Evaluation of version 0 MAST terminates early if script is oversize // Not enforced in unknown MAST version for upgrade flexibility if (nMASTVersion == 0 && (scriptPubKey.size() + subscript.size()) > MAX_SCRIPT_SIZE) return set_error(serror, SCRIPT_ERR_SCRIPT_SIZE); uint256 hashSubScript; CHash256().Write(&subscript[0], subscript.size()).Finalize(hashSubScript.begin()); sScriptHash << hashSubScript; scriptPubKey = scriptPubKey + subscript; // Final scriptPubKey is a serialization of subscripts } uint256 hashScript = sScriptHash.GetHash(); // Calculate MAST Root and compare against witness program uint256 rootScript = ComputeMerkleRootFromBranch(hashScript, path, position); sRoot << rootScript; uint256 rootMAST = sRoot.GetHash(); if (memcmp(rootMAST.begin(), &program[0], 32)) return set_error(serror, SCRIPT_ERR_WITNESS_PROGRAM_MISMATCH); if (nMASTVersion == 0) { stack = std::vector >(witness.stack.begin(), witness.stack.end() - 3 - nSubscript); for (unsigned int i = 0; i < stack.size(); i++) { if (stack.at(i).size() > MAX_SCRIPT_ELEMENT_SIZE) return set_error(serror, SCRIPT_ERR_PUSH_SIZE); } // Script evaluation must not fail, and return an empty stack if (!EvalScript(stack, scriptPubKey, flags, checker, SIGVERSION_WITNESS_V1, nOpCount, serror)) return false; if (stack.size() != 0) return set_error(serror, SCRIPT_ERR_EVAL_FALSE); } return set_success(serror); } Copying from src/consensus/merkle.cpp: uint256 ComputeMerkleRootFromBranch(const uint256& leaf, const std::vector& vMerkleBranch, uint32_t nIndex) { uint256 hash = leaf; for (std::vector::const_iterator it = vMerkleBranch.begin(); it != vMerkleBranch.end(); ++it) { if (nIndex & 1) { hash = Hash(BEGIN(*it), END(*it), BEGIN(hash), END(hash)); } else { hash = Hash(BEGIN(hash), END(hash), BEGIN(*it), END(*it)); } nIndex >>= 1; } return hash; } == References == *[[bip-0141.mediawiki|BIP141 Segregated Witness (Consensus layer)]] == Copyright == This document is placed in the public domain. ================================================ FILE: bip-0115.mediawiki ================================================
  BIP: 115
  Layer: Consensus (soft fork)
  Title: Generic anti-replay protection using Script
  Authors: Luke Dashjr 
  Status: Closed
  Type: Specification
  Assigned: 2016-09-23
  License: BSD-2-Clause
==Abstract== This BIP describes a new opcode (OP_CHECKBLOCKATHEIGHT) for the Bitcoin scripting system that allows construction of transactions which are valid only on specific blockchains. ==Copyright== This BIP is licensed under the BSD 2-clause license. ==Specification== OP_CHECKBLOCKATHEIGHT redefines the existing OP_NOP5 opcode. When this opcode is executed: * If the stack has fewer than 2 elements, the script fails. * If the top item on the stack cannot be interpreted as a minimal-length 32-bit CScriptNum, the script fails. * The top item on the stack is interpreted as a block height (ParamHeight). * If the blockchain (in the context of the execution) does not have ParamHeight blocks prior to the one including this transaction, the script fails (this failure must not be cached across blocks; it is equivalent to non-final status). * If ParamHeight specifies a block deeper than 52596 blocks in the chain (including negative values), the opcode completes successfully and script continues as normal. * The second-to-top item on the stack is interpreted as a block hash (ParamBlockHash). * If ParamBlockHash is longer than 28 bytes, the script fails. * If ParamBlockHash does not match the equivalent ending bytes of the block hash specified by ParamHeight, the script fails. Otherwise, script execution will continue as if a NOP had been executed. ===Deployment=== This BIP will be deployed by "version bits" [[bip-0009.mediawiki|BIP9]] with the '''name''' "cbah" and using '''bit''' TBD. For Bitcoin '''mainnet''', the BIP9 '''starttime''' will be TBD (Epoch timestamp TBD) and BIP9 '''timeout''' will be TBD (Epoch timestamp TBD). For Bitcoin '''mainnet''', the BIP9 '''starttime''' will be TBD (Epoch timestamp TBD) and BIP9 '''timeout''' will be TBD (Epoch timestamp TBD). ==Motivation== ===Securely recovering from double spends=== In some circumstances, users may wish to spend received bitcoins before they have confirmed on the blockchain (Tx B1). However, if the transaction sending them those bitcoins (Tx A1) is double-spent, the wallet must re-issue their own transaction spending them (Tx B2). So long as the double-spend of the incoming transaction (Tx A2) also pays the wallet, this can be managed by simply updating the outgoing transaction with the new outpoint and resigning. However, if the double-spend does not pay the wallet, the situation is presently irrecoverable: it must spend different, non-conflicting TXOs in Tx B2, which allows an attacker to then reorganise the chain (reversing the incoming transaction's double-spend) and confirm both of his transactions Tx B1 and Tx B2. By adding OP_CHECKBLOCKATHEIGHT, the wallet can issue Tx B2 with a condition that the block confirming Tx A2 is in the history, thus eliminating this risk. ===Replay protection in the event of a persistent blockchain split=== In the event of a persistent blockchain split, some mechanism is desired by which the UTXOs valid in either chain may be spent without the transaction being validly replayable on the other chain. This can be guaranteed by choosing a block which exists only on either side of the split, and pinning (using OP_CHECKBLOCKATHEIGHT) common UTXOs to be spent only on chains based on that block. ==Best practices for wallets== To avoid unnecessary conflicts when a chain is reorganized, wallets should always avoid specifying the last 100 blocks when practical. Wallets that use recent blocks when unavoidable SHOULD actively monitor the network and re-create transactions that are reorganised out with updated block hashes. Unless it conflicts with local/user security policies, wallets SHOULD retain the private key in memory to re-sign such transactions until the pinned block is at least 100 blocks deep into the chain. For ordinary usage, wallets SHOULD specify the ParamBlockHash as 16 bytes. ==Rationale== How is this different from the transaction's lock-time? * The lock-time specifies a time or block height before a transaction becomes valid. OP_CHECKBLOCKATHEIGHT, on the other hand, specifies a specific block's hash. Why are block heights required to be absolute, rather than relative? * A relative block height would allow for creation of transactions which are valid at block N, but not N+1. This is carefully avoided by Bitcoin to ensure that if any given block is reorganised out, non-malicious transactions can be simply re-confirmed in a later block. Why are blocks older than 52596 deep in the chain not verified? * This is to avoid creating an infinite storage requirement from all full nodes which would be necessary to maintain all the block headers indefinitely. 52596 block headers requires a fixed size of approximately 4 MB. * In any case where you might want to specify a deeper block, you can also just as well specify a more recent one that descends from it. * It is assumed that 1 year is sufficient time to double-spend any common UTXOs on all blockchains of interest. * If a deeper check is needed, it can be softforked in. Making the check more shallow, on the other hand, is a hardfork. Why is ParamBlockHash allowed to match less than the full block hash? * In a chain split, it is sufficient to check only a few bytes to avoid replay. * In all scenarios, it is likely sufficient to check only a minority of the full hash to avoid any realistic chance of replay. * Allowing less than the full hash to be specified saves space in transaction data. * Using a single byte can be combined with other opcodes (such as OP_LESSTHAN) to enable on-chain gambling logic. What if ParamBlockHash has leading zeros? Should this be prevented? * If leading zeros are included, they should be compared to the actual block hash. (If they were truncated, fewer bytes would be compared.) * It is unlikely that the leading zeros will ever be necessary for sufficient precision, so the additional space is not a concern. * Since all block hashes are in principle shorter than 29 bytes, ParamBlockHash may not be larger than 28 bytes. Why is it safe to allow checking blocks as recently as the immediate previous block? * This should only be used when necessary (ie, the deeper block is not sufficient), and when the wallet can actively issue updates should the blockchain reorganise. * While this allows intentionally creating a transaction which may be invalid in a reorganization, the same can already be accomplished by creating double spends. ==Backwards Compatibility== OP_NOP5 ought to be forbidden by policy by all miners for future extensions such as this, so old miners will under no circumstances produce blocks which would now be considered invalid under the new rules. However, miners must still upgrade to avoid accepting and building on top of such a possible invalid block as part of an attack. Old nodes will likely also not relay transactions using this opcode for the same extensibility reasons, but this is not important since the rule cannot be verified deterministically outside the context of a block. ==Reference Implementation== https://github.com/bitcoin/bitcoin/compare/master...luke-jr:cbah ================================================ FILE: bip-0116.mediawiki ================================================
  BIP: 116
  Layer: Consensus (soft fork)
  Title: MERKLEBRANCHVERIFY
  Authors: Mark Friedenbach 
           Kalle Alm 
           BtcDrak 
  Status: Draft
  Type: Specification
  Assigned: 2017-08-25
  License: CC-BY-SA-4.0
  License-Code: MIT
==Abstract== A general approach to bitcoin contracts is to fully enumerate the possible spending conditions and then program verification of these conditions into a single script. At redemption, the spending condition used is explicitly selected, e.g. by pushing a value on the witness stack that cascades through a series of if/else constructs. This approach has significant downsides, such as requiring all program pathways to be visible in the scriptPubKey or redeem script, even those which are not used at validation. This wastes space on the block chain, restricts the size of possible scripts due to push limits, and impacts both privacy and fungibility as details of the contract can often be specific to the user. This BIP proposes a new soft-fork upgradeable opcode, MERKLEBRANCHVERIFY, which allows script writers to commit to a set of data elements and have one or more of these elements be provided at redemption without having to reveal the entire set. As these data elements can be used to encode policy, such as public keys or validation subscripts, the MERKLEBRANCHVERIFY opcode can be used to overcome these limitations of existing bitcoin script. ==Copyright== This BIP is licensed under a Creative Commons Attribution-ShareAlike license. All provided source code is licensed under the MIT license. ==Specification== MERKLEBRANCHVERIFY redefines the existing NOP4 opcode. When executed, if any of the following conditions are true, the script interpreter will terminate with an error: # the stack contains less than three (3) items; # the first item on the stack is more than 2 bytes; # the first item on the stack, interpreted as an integer, N, is negative or not minimally encoded; # the second item on the stack is not exactly 32 bytes; # the third item on the stack is not a serialized Merkle tree inclusion proof as specified by BIP98[1] and requiring exactly floor(N/2) VERIFY hashes; or # the remainder of the stack contains less than floor(N/2) additional items, together referred to as the input stack elements. If the low-order bit of N is clear, N&1 == 0, each input stack element is hashed using double-SHA256. Otherwise, each element must be exactly 32 bytes in length and are interpreted as serialized hashes. These are the VERIFY hashes. If the fast Merkle root computed from the Merkle tree inclusion proof, the third item on the stack, with the VERIFY hashes in the order as presented on the stack, from top to bottom, does not exactly match the second item on the stack, the script interpreter will terminate with an error. Otherwise, script execution will continue as if a NOP had been executed. ==Motivation== Although BIP16 (Pay to Script Hash)[2] and BIP141 (Segregated Witness)[3] both allow the redeem script to be kept out of the scriptPubKey and therefore out of the UTXO set, the entire spending conditions for a coin must nevertheless be revealed when that coin is spent. This includes execution pathways or policy conditions which end up not being needed by the redemption. Not only is it inefficient to require this unnecessary information to be present on the blockchain, albeit in the witness, it also impacts privacy and fungibility as some unused script policies may be identifying. Using a Merkle hash tree to commit to the policy options, and then only forcing revelation of the policy used at redemption minimizes this information leakage. Using Merkle hash trees to commit to policy allows for considerably more complex contracts than would otherwise be possible, due to various built-in script size and runtime limitations. With Merkle commitments to policy these size and runtime limitations constrain the complexity of any one policy that can be used rather than the sum of all possible policies. ==Rationale== The MERKLEBRANCHVERIFY opcode uses fast Merkle hash trees as specified by BIP98[1] rather than the construct used by Satoshi for committing transactions to the block header as the later has a known vulnerability relating to duplicate entries that introduces a source of malleability to downstream protocols[4]. A source of malleability in Merkle proofs could potentially lead to spend vulnerabilities in protocols that use MERKLEBRANCHVERIFY. For example, a compact 2-of-N policy could be written by using MERKLEBRANCHVERIFY to prove that two keys are extracted from the same tree, one at a time, then checking the proofs for bitwise equality to make sure the same entry wasn't used twice. With the vulnerable Merkle tree implementation there are privileged positions in unbalanced Merkle trees that allow multiple proofs to be constructed for the same, single entry. BIP141 (Segregated Witness)[3] provides support for a powerful form of script upgrades called script versioning, which is able to achieve the sort of upgrades which would previously have been hard-forks. If script versioning were used for deployment then MERKLEBRANCHVERIFY could be written to consume its inputs, which would provide a small 2-byte savings for many anticipated use cases. However the more familiar NOP-expansion soft-fork mechanism used by BIP65 (CHECKLOCKTIMEVERIFY)[5] and BIP112 (CHECKSEQUENCEVERIFY)[6] was chosen over script versioning for the following two reasons: # '''Infrastructure compatibility.''' Using soft-fork NOP extensions allows MERKLEBRANCHVERIFY to be used by any existing software able to consume custom scripts, and results in standard P2SH or P2WSH-nested-in-P2SH addresses without the need for BIP143[7] signing code. This allows MERKLEBRANCHVERIFY to be used immediately by services that need it rather than wait on support for script versioning and/or BIP-143[7] signatures in tools and libraries. # '''Delayed decision on script upgrade protocol.''' There are unresolved issues with respect to how script versioning should be used for future script upgrades. There are only 16 available script versions reserved for future use, and so they should be treated as a scarce resource. Additionally, script feature versioning should arguably be specified in the witness and the BIP141 script versioning only be used to specify the structure of the witness, however no such protocol exists as of yet. Using the NOP-expansion space prevents MERKLEBRANCHVERIFY from being stalled due to waiting on script upgrade procedure to be worked out, while making use of expansion space that is already available. The MERKLEBRANCHVERIFY opcode allows for VERIFY hashes to be presented directly, or calculated from the leaf values using double-SHA256. In most cases the latter approach is expected to be used so that the leaf value(s) can be used for both branch validation and other purposes without any explicit preprocessing. However allowing already-calculated hash values as inputs enables using chained MERKLEBRANCHVERIFY opcodes to verify branches of trees with proofs large enough that they would not fit in the 520 byte script push limitation. As specified, a 30-branch path can be verified by proving the path from the leaf to the 15th interior node as the 'root', then proving that node's hash to be a child of the actual Merkle tree root hash. Validation of a 256-branch path (e.g. a binary prefix tree with a hash value as key) would require 18 chained validations, which would fit within current script limitations. ==Applications== ===1-of-N for large N=== Here is a redeem script that allows a coin to be spent by any key from a large set, without linear scaling in script size: redeemScript: 2 MERKLEBRANCHVERIFY 2DROP DROP CHECKSIG witness: The redeem script looks very similar to the standard pay-to-pubkey-hash, except instead of showing that the pubkey's hash is the same as the commitment given, we demonstrate that the pubkey is one of potentially many pubkeys included in the Merkle tree committed to in the redeem script. The low-order bit of the first parameter, 2, is clear, meaning that there is one input ((2>>1) == 1), the serialized pubkey, and its VERIFY hash needs to be calculated by MERKLEBRANCHVERIFY using double-SHA256. ===Honeypots=== As described by Pieter Wuille[8] the 1-of-N scheme is particularly useful for constructing honeypots. The desire is to put a large bounty on a server, larger than the value of the server itself so that if the server is compromised it is highly likely that the hacker will claim the bitcoin, thereby revealing the intrusion. However if there are many servers, e.g. 1,000, it becomes excessively expensive to lock up separate bounties for each server. It would be desirable if the same bounty was shared across multiple servers in such a way that the spend would reveal which server was compromised. This is accomplished by generating 1,000 different keys, building a hash tree of these public keys, and placing each key and associated Merkle path on separate servers. When the honeypot is claimed, the (previous) owner of the coins can tell which server was compromised from the key and path used to claim the funds. ==Implementation== An implementation of this BIP, including both consensus code updates and tests is available at the following Github repository: [https://github.com/maaku/bitcoin/tree/merkle-branch-verify] ==Deployment== This BIP will be deployed by BIP8 (Version bits with lock-in by height)[10] with the name "merklebranchverify" and using bit 2. For Bitcoin mainnet, the BIP8 startheight will be at height M to be determined and BIP8 timeout activation will occur on height M + 50,400 blocks. For Bitcoin testnet, the BIP8 startheight will be at height T to be determined and BIP8 timeout activation will occur on height T + 50,400 blocks. We note that DISCOURAGE_UPGRADABLE_NOPS means that transactions which use this feature are already considered non-standard by the rules of the network, making deployment easier than was the case with, for example, with BIP68 (Relative lock-time using consensus-enforced sequence numbers)[9]. ==Compatibility== Old clients will consider the OP_MERKLEBRANCHVERIFY as a NOP and ignore it. Proof will not be verified, but the transaction will be accepted. ==References== [1] [https://github.com/bitcoin/bips/blob/master/bip-0098.mediawiki BIP98: Fast Merkle Trees (Consensus layer)] [2] [https://github.com/bitcoin/bips/blob/master/bip-0016.mediawiki BIP16: Pay to Script Hash] [3] [https://github.com/bitcoin/bips/blob/master/bip-0141.mediawiki BIP141: Segregated Witness (Consensus layer)] [4] [https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2012-2459 National Vulnerability Database: CVE-2012-2459] [5] [https://github.com/bitcoin/bips/blob/master/bip-0065.mediawiki BIP65: OP_CHECKLOCKTIMEVERIFY] [6] [https://github.com/bitcoin/bips/blob/master/bip-0112.mediawiki BIP112: CHECKSEQUENCEVERIFY] [7] [https://github.com/bitcoin/bips/blob/master/bip-0143.mediawiki BIP143: Transaction Signature Verification for Version 0 Witness Program] [8] [https://blockstream.com/2015/08/24/treesignatures.html Multisig on steroids using tree signatures] [9] [https://github.com/bitcoin/bips/blob/master/bip-0068.mediawiki BIP68: Relative lock-time using consensus-enforced sequence numbers] [10] [https://github.com/bitcoin/bips/blob/master/bip-0008.mediawiki BIP8: Version bits with lock-in by height] ================================================ FILE: bip-0117.mediawiki ================================================
  BIP: 117
  Layer: Consensus (soft fork)
  Title: Tail Call Execution Semantics
  Authors: Mark Friedenbach 
           Kalle Alm 
           BtcDrak 
  Status: Draft
  Type: Specification
  Assigned: 2017-08-25
  License: CC-BY-SA-4.0
  License-Code: MIT
==Abstract== BIP16 (Pay to Script Hash)[1] and BIP141 (Segregated Witness)[2] provide mechanisms by which script policy can be revealed at spend time as part of the execution witness. In both cases only a single script can be committed to by the construct. While useful for achieving the goals of these proposals, they still require that all policies be specified within the confine of a single script, regardless of whether the policies are needed at the time of spend. This BIP, in conjunction with BIP116 (MERKLEBRANCHVERIFY)[3] allows for a script to commit to a practically unbounded number of code pathways, and then reveal the actual code pathway used at spend time. This achieves a form of generalized MAST[4] enabling decomposition of complex branching scripts into a set of non-branching flat execution pathways, committing to the entire set of possible pathways, and then revealing only the path used at spend time. ==Copyright== This BIP is licensed under a Creative Commons Attribution-ShareAlike license. All provided source code is licensed under the MIT license. ==Specification== If, at the end of script execution: * the execution state is non-clean, meaning *# the main stack has more than one item on it, or *# the main stack has exactly one item and the alt-stack is not empty; * the top-most element of the main stack evaluates as true when interpreted as a bool; and * the top-most element is not a single byte or is outside the inclusive range of 0x51 to 0x60, then that top-most element of the main stack is popped and interpreted as a serialized script and executed, while the remaining elements of both stacks remain in place as inputs. If the above conditions hold except for the last one, such that: * the top-most element ''is'' a single byte within the inclusive range of 0x51 (OP_1, meaning N=2) to 0x60 (OP_16, meaning N=17); and * other than this top-most element there are at least N additional elements on the main stack and alt stack combined, then the top-most element of the main stack is dropped, and the N=2 (0x51) to 17 (0x60) further elements are popped from the main stack, continuing from the alt stack if the main stack is exhausted, and concatenated together in reverse order to form a serialized script, which is then executed with the remaining elements of both stacks remaining in place as inputs. The presence of CHECKSIG or CHECKMULTISIG within the subscript do not count towards the global MAX_BLOCK_SIGOPS_COST limit, and the number of non-push opcodes executed in the subscript is not limited by MAX_OPS_PER_SCRIPT. Execution state, other than the above exceptions, carries over into the subscript, and termination of the subscript terminates execution of the script as a whole. This is known as execution with tail-call semantics. Only one such tail-call of a subscript is allowed per script execution context, and only from within a segwit redeem script. Alternatively stated, neither evaluation of witness stack nor execution of the scriptPubKey or scriptSig or P2SH redeem script results in tail-call semantics. ==Motivation== BIP16 (Pay to Script Hash)[1] and BIP141 (Segregated Witness)[2] allow delayed revelation of a script's policy until the time of spend. However these approaches are limited in that only a single policy can be committed to in a given transaction output. It is not possible to commit to multiple policies and then choose, at spend time, which to reveal. BIP116 (MERKLEBRANCHVERIFY)[3] allows multiple data elements to be committed to while only revealing those necessary at the time of spend. The MERKLEBRANCHVERIFY opcode is only able to provide commitments to a preselected set of data values, and does not by itself allow for executing code. This BIP generalizes the approach of these prior methods by allowing the redeem script to perform any type of computation necessary to place the policy script on the stack. The policy script is then executed from the top of the data stack in a way similar to how BIP16 and BIP141 enable redeem scripts to be executed from the top of the witness stack. In particular, using MERKLEBRANCHVERIFY[3] in the scriptPubKey or redeem script allows selection of the policy script that contains only the necessary conditions for validation of the spend. This is a form of generalized MAST[4] where a stage of precomputation splits a syntax tree into possible execution pathways, which are then enumerated and hashed into a Merkle tree of policy scripts. At spend time membership in this tree of the provided policy script is proven before execution recurses into the policy script. ==Rationale== This proposal is a soft-fork change to bitcoin's consensus rules because leaving a script that data-wise evaluates as true from its serialized form on the stack as execution terminates would result in the script validation returning true anyway. Giving the subscript a chance to terminate execution is only further constraining the validation rules. The only scripts which would evaluate as false are the empty script, or a script that does nothing more than push empty/zero values to the stack. None of these scripts have any real-world utility, so excluding them to achieve soft-fork compatibility doesn't come with any downsides. By restricting ourselves to tail-call evaluation instead of a more general EVAL opcode we greatly simplify the implementation. Tail-call semantics means that execution never returns to the calling script's context, and therefore no state needs to be saved or later restored. The implementation is truly as simple as pulling the subscript off the stack, resetting a few state variables, and performing a jump back to the beginning of the script interpreter. The restriction to allow only one layer of tail-call recursion is admittedly limiting, however the technical challenges to supporting multi-layer tail-call recursion are significant. A new metric would have to be developed to track script resource usage, for which transaction data witness size are only two factors. This new weight would have to be relayed with transactions, used as the basis for fee calculation, validated in-line with transaction execution, and policy decided upon for DoS-banning peers that propagate violating transactions. However should these problems be overcome, dropping the single recursion constraint is itself a soft-fork for the same reason, applied inductively. Allowing only one layer of tail-call recursion allows us to receive the primary benefit of multi-policy commitments / generalized MAST, while leaving the door open to future generalized tail-call recursion if and when the necessary changes are made to resource accounting and p2p transaction distribution. The global SIGOP limit and per-script opcode limits do not apply to the policy script because dynamic selection of the policy script makes it not possible for static analysis tools to verify these limits in general, and because performance improvements to libsecp256k1 and Bitcoin Core have made these limits no longer necessary as they once were. The validation costs are still limited by the number of signature operations it is possible to encode within block size limits, and the maximum script size per input is limited to 10,000 + 17*520 = 18,840 bytes. To allow for this drop of global and per-script limits, tail-call evaluation cannot be allowed for direct execution of the scriptPubKey, as such scripts are fetched from the UTXO and do not count towards block size limits of the block being validated. Likewise tail-call from P2SH redeem scripts is not supported due to quadratic blow-up vulnerabilities that are fixed in segwit. ==Generalized MAST== When combined with BIP116 (MERKLEBRANCHVERIFY)[3], tail-call semantics allows for generalized MAST capabilities[4]. The script author starts with a full description of the entire contract they want to validate at the time of spend. The possible execution pathways through the script are then enumerated, with conditional branches replaced by a validation of the condition and the branch taken. The list of possible execution pathways is then put into a Merkle tree, with the flattened policy scripts as the leaves of this tree. The final redeem script which funds are sent to is as follows: redeemScript: 2 MERKLEBRANCHVERIFY 2DROP DROP witness: ... Where policyScript is the flattened execution pathway, proof is the serialized Merkle branch and path that proves the policyScript is drawn from the set used to construct the Merkle tree root, and arg1 through argN are the arguments required by policyScript. The 2 indicates that a single leaf (1 << 1) follows, and the leaf value is not pre-hashed. The 2DROP DROP is necessary to remove the arguments to MERKLEBRANCHVERIFY from the stack. The above example was designed for clarity, but actually violates the CLEANSTACK rule of segwit v0 script execution. Unless the CLEANSTACK rule is dropped or modified in a new segwit output version, this would script would have to be modified to use the alt-stack, as follows: redeemScript: [TOALTSTACK]*N 2 MERKLEBRANCHVERIFY 2DROP DROP witness: ... Where [TOALTSTACK]*N is the TOALTSTACK opcode repeated N times. This moves arg1 through argN to the alt-stack in reverse order, such that arg1 is on the top of the alt-stack when execution of policyScript begins. The policyScript would also have to be modified to fetch its arguments from the alt-stack, of course. If the total set of policy scripts includes scripts that take a varying number of parameters, that too can be supported, within reasonable limits. The following redeem script allows between 1 and 3 witness arguments in addition to the policy script and Merkle proof: witness: ... // N is between 1 and 3 redeemScript: DEPTH TOALTSTACK // Save number of witness elements to alt-stack TOALTSTACK // Save 1st element (required) to alt-stack DEPTH 2 SUB // Calculate number of optional elements, ignoring policyScript and proof DUP IF SWAP TOALTSTACK 1SUB ENDIF // Save 2nd element (optional) to alt-stack, if it is present IF TOALTSTACK ENDIF // Save 3rd element (optional) to alt-stack, if it is present; consume counter 2 MERKLEBRANCHVERIFY 2DROP DROP alt-stack: ... Because the number of witness elements is pushed onto the alt-stack, this enables policy scripts to verify the number of arguments passed, even though the size of the alt-stack is not usually accessible to script. The following policy script for use with the above redeem script will only accept 2 witness elements on the alt-stack, preventing witness malleability: policyScript: FROMALTSTACK ...check arg1... FROMALTSTACK ...check&consume arg2/arg1&2... FROMALTSTACK 4 EQUAL The number 4 is expected as that includes the policyScript and proof. The verbosity of this example can be prevented by using a uniform number of witness elements as parameters for all policy subscripts, eliminating the conditionals and stack size counts. Future script version upgrades should also consider relaxing CLEANSTACK rules to allow direct pass-through of arguments from the witness/redeem script to the policy script on the main stack. ===Comparison with BIP114=== BIP114 (Merkelized Abstract Syntax Tree)[5] specifies an explicit MAST scheme activated by BIP141 script versioning[2]. Unlike BIP114, the scheme proposed by this BIP in conjunction with BIP116 (MERKLEBRANCHVERIFY)[3] implicitly enables MAST constructs using script itself to validate membership of the policy script in the MAST. This has the advantage of requiring vastly fewer consensus code changes, as well as potentially enabling future script-based innovation without requiring any further consensus code changes at all, as the MAST scheme itself is programmable. Furthermore, by adding MERKLEBRANCHVERIFY and tail-call semantics to all script using the NOP-expansion space, BIP141 style script versioning is not required. This removes a potentially significant hurdle to deployment by making this feature not dependent on resolving outstanding issues over address formats, how script version upgrades should be deployed, and consensus over what other features might go into a v1 upgrade. ==Implementation== An implementation of this BIP, including both consensus code changes and tests are available at the following Github repository: [https://github.com/maaku/bitcoin/tree/tail-call-semantics] ==Deployment== This BIP will be deployed by BIP8 (Version bits with lock-in by height)[9] with the name "tailcall" and using bit 3. For Bitcoin mainnet, the BIP8 startheight will be at height M to be determined and BIP8 timeout activation will occur on height M + 50,400 blocks. For Bitcoin testnet, the BIP8 startheight will be at height T to be determined and BIP8 timeout activation will occur on height T + 50,400 blocks. We note that CLEANSTACK means that transactions which use this feature are already considered non-standard by the rules of the network, making deployment easier than was the case with, for example, with BIP68 (Relative lock-time using consensus-enforced sequence numbers)[6]. ==Compatibility== The v0 segwit rules prohibit leaving anything on the stack, so for v0 parameters have to be passed on the alt stack for compatibility reasons. ==References== [1] [https://github.com/bitcoin/bips/blob/master/bip-0016.mediawiki BIP16: Pay to Script Hash] [2] [https://github.com/bitcoin/bips/blob/master/bip-0141.mediawiki BIP141: Segregated Witness (Consensus Layer)] [3] [https://github.com/bitcoin/bips/blob/master/bip-0116.mediawiki BIP116: MERKLEBRANCHVERIFY] [4] "[https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2017-September/015028.html An explanation and justification of the tail-call and MBV approach to MAST]", Mark Friedenbach, Bitcoin Development Mailing List, 20 September 2017. [5] [https://github.com/bitcoin/bips/blob/master/bip-0114.mediawiki BIP114: Merkelized Abstract Syntax Tree] [6] [https://github.com/bitcoin/bips/blob/master/bip-0068.mediawiki BIP68: Relative lock-time using consensus-enforced sequence numbers] [9] [https://github.com/bitcoin/bips/blob/master/bip-0008.mediawiki BIP8: Version bits with lock-in by height] ================================================ FILE: bip-0118.mediawiki ================================================
  BIP: 118
  Layer: Consensus (soft fork)
  Title: SIGHASH_ANYPREVOUT for Taproot Scripts
  Authors: Christian Decker 
           Anthony Towns 
  Comments-Summary: No comments yet.
  Comments-URI: https://github.com/bitcoin/bips/wiki/Comments:BIP-0118
  Status: Draft
  Type: Specification
  Assigned: 2017-02-28
  License: BSD-3-Clause
  Requires: 340, 341, 342
== Introduction == === Abstract === This BIP describes a new type of public key for tapscript ([[bip-0342.mediawiki|BIP 342]]) transactions. It allows signatures for these public keys to not commit to the exact UTXO being spent. This enables dynamic binding of transactions to different UTXOs, provided they have compatible scripts. === Copyright === This document is licensed under the 3-clause BSD license. === Motivation === Off-chain protocols make use of transactions that are not yet broadcast to the Bitcoin network in order to renegotiate the final state that should be settled on-chain. In a number of cases it is desirable to respond to a given transaction being seen on-chain with a predetermined reaction in the form of another transaction. Often the same reaction is desired for a variety of different transactions that may be seen on-chain, but because the input signatures in the response transaction commit to the exact transaction that is being reacted to, this means a new signature must be created for every possible transaction one wishes to be able to react to. This proposal introduces a new public key type'''Why a new public key type?''' New public key types for tapscript can be introduced in a soft fork by specifying new rules for ''unknown public key types'' as specified in [[bip-0342.mediawiki|BIP 342]], as this only requires adding restrictions to the pre-existing signature opcodes. Possible alternative approaches would be to define new script opcodes, to use a different taproot leaf version, or to use a different set of SegWit outputs than those specified by [[bip-0341.mediawiki|BIP 341]]; however all of these approaches are more complicated, and are better reserved for other upgrades where the additional flexibility is actually needed. In this case, we specify a new transaction digest, but retain the same elliptic curve and signature algorithm (ie, secp256k1 and [[bip-0340.mediawiki|BIP 340]]). that modifies the behavior of the transaction digest algorithm used in the signature creation and verification, by excluding the commitment to the previous output (and, optionally, the witness script'''Why (and why not) commit to the witness script?''' The [https://blockstream.com/eltoo.pdf eltoo] paper provides an example of why committing to the witness script is not always appropriate. It uses script and the transaction nLockTime to make signatures asymmetric, so that a transaction with an earlier signature can be spent by a transaction with a later signature, but a transaction with a later signature cannot be spent by a transaction with an earlier signature. As a result, a single signature for a third, even later transaction must be able to spend both the prior transactions, even though they have a different tapscript. On the other hand, these cases also provide a good reason to have the option to commit to the script: because each transaction has a new script, committing to the script allows you to produce a signature that applies to precisely one of these transactions. In the eltoo case, this allows you to have a signature for an update transaction that can be applied to any prior update, and a signature for a settlement transaction that applies only to the corresponding update transaction, while using the same key for both, which in turn allows for a more compact script. and value '''Why (and why not) commit to the input value?''' Committing to the input value may provide additional safety that a signature can't be maliciously reused to claim funds that the signer does not intend to spend, so by default it seems sensible to commit to it. However, doing so prevents being able to use a single signature to consolidate a group of UTXOs with the same spending condition into a single UTXO which may be useful for some protocols, such as the proposal for [https://lists.linuxfoundation.org/pipermail/lightning-dev/2020-January/002448.html layered commitments with eltoo].). Removing this commitment allows dynamic rebinding of a signed transaction to another previous output that requires authorisation by the same key. The dynamic rebinding is opt-in due to using a separate public key type, and the breadth of transactions the signature can be rebound to can be further restricted by using different keys, committing to the script being spent in the signature, using different amounts between UTXOs, using different nSequence values in the spending transaction, or using the codeseparator opcode to commit to the position in the script. == Specification == This BIP modifies the behaviour of the [[bip-0342.mediawiki|BIP 342]] signature opcodes'''What about key path spends?''' This proposal only supports ANYPREVOUT signatures via script path spends, and does not support ANYPREVOUT signatures for key path spends. This is for two reasons: first, not supporting key path spends allows this proposal to be independent of the core changes included in [[bip-0341.mediawiki|BIP 341]] and [[bip-0342.mediawiki|BIP 342]]; second, it allows addresses to opt-in or opt-out of ANYPREVOUT support while remaining indistinguishable prior to being spent. (CHECKSIG, CHECKSIGVERIFY, and CHECKSIGADD) for public keys that have a length of 33 bytes and a first byte of 0x01 or the public key which is precisely the single byte vector 0x01'''Use of 0x01 public key type''' Because OP_0 leaves an empty vector on the stack it would not satisfy [[bip-0342.mediawiki|BIP 342]]'s rules for unknown public key types. As such, it is convenient to use one of OP_1..OP_16 or OP_1NEGATE as a way to reference the taproot internal key. To keep things as simple as possible, we use the first of these, and add the same byte as a prefix to allow ANYPREVOUT signatures for explicitly specified keys. . These keys are termed '''BIP 118 public keys'''. ==== Rules for signature opcodes ==== The [[bip-0342.mediawiki|BIP 342]] rules for signature opcodes are modified by removing keys with the first byte 0x01 and length of either 1-byte or 33-bytes from the list of unknown public key types, and adding the following rule prior to the handling of unknown public key types: * If the public key is the single byte 0x01, or if the public key is 33 bytes and the first byte of the public key is 0x01, it is considered to be a BIP 118 public key: ** If the signature is not the empty vector, the signature is validated according to the [[bip-0341.mediawiki|BIP 341]] signing validation rules with the public key, allowable hash_type values, and transaction digest modified as defined below. ==== Public key ==== To convert the 1-byte BIP 118 public key for use with [[bip-0340.mediawiki|BIP 340]], use the 32-byte taproot internal key, p, as defined in [[bip-0341.mediawiki|BIP 341]]. To convert a 33-byte BIP 118 public key for use with [[bip-0340.mediawiki|BIP 340]], remove the 0x01 prefix and use the remaining 32 bytes. ==== Signature message ==== We define the functions ''Msg118(hash_type)'' and ''Ext118(hash_type)'' which compute the message being signed as a byte array. The parameter ''hash_type'' is an 8-bit unsigned value, reusing values defined in [[bip-0341.mediawiki|BIP 341]], with the addition that the values 0x41, 0x42, 0x43, 0xc1, 0xc2, and 0xc3 are also valid for BIP 118 public keys. We define the following constants using bits 6 and 7 of hash_type: * SIGHASH_ANYPREVOUT = 0x40 * SIGHASH_ANYPREVOUTANYSCRIPT = 0xc0 The following restrictions apply and cause validation failure if violated: * Using any undefined ''hash_type'' (not ''0x00'', ''0x01'', ''0x02'', ''0x03'', ''0x41'', ''0x42'', ''0x43'', ''0x81'', ''0x82'', ''0x83'', ''0xc1'', ''0xc2'', or ''0xc3''). * Using SIGHASH_SINGLE without a "corresponding output" (an output with the same index as the input being verified). If these restrictions are not violated, ''Msg118(hash_type)'' evaluates as follows. If ''hash_type & 0x40 == 0'', then ''Msg118(hash_type) = SigMsg(hash_type, 1)'', where ''SigMsg'' is as defined in [[bip-0341.mediawiki|BIP 341]]. If ''hash_type & 0x40 != 0'', then ''Msg118(hash_type)'' is the concatenation of the following data, in order (with byte size of each item listed in parentheses). Numerical values in 2, 4, or 8-byte items are encoded in little-endian. * Control: ** ''hash_type'' (1). * Transaction data: ** ''nVersion'' (4): the ''nVersion'' of the transaction. ** ''nLockTime'' (4): the ''nLockTime'' of the transaction. ** If ''hash_type & 3'' does not equal SIGHASH_NONE or SIGHASH_SINGLE: *** ''sha_outputs'' (32): the SHA256 of the serialization of all outputs in CTxOut format. * Data about this input: ** ''spend_type'' (1): equal to 2 if no annex is present, or 3 otherwise (the original witness stack has two or more witness elements, and the first byte of the last element is ''0x50'') ** If ''hash_type & 0xc0'' is SIGHASH_ANYPREVOUT: *** ''amount'' (8): value of the previous output spent by this input. *** ''scriptPubKey'' (35): ''scriptPubKey'' of the previous output spent by this input, serialized as script inside CTxOut. Its size is always 35 bytes. ** ''nSequence'' (4): ''nSequence'' of this input. ** If an annex is present (the lowest bit of ''spend_type'' is set): *** ''sha_annex'' (32): the SHA256 of ''(compact_size(size of annex) || annex)'', where ''annex'' includes the mandatory ''0x50'' prefix. * Data about this output: ** If ''hash_type & 3'' equals SIGHASH_SINGLE: *** ''sha_single_output'' (32): the SHA256 of the corresponding output in CTxOut format. Similarly, ''Ext118(hash_type)'' evaluates to the concatenation of the following data, in order: * Extension: ** If ''hash_type & 0xc0'' is not SIGHASH_ANYPREVOUTANYSCRIPT: *** ''tapleaf_hash'' (32): the tapleaf hash as defined in [[bip-0341.mediawiki|BIP 341]] ** ''key_version'' (1): a constant value ''0x01'' representing that this is a signature for a BIP 118 public key. ** ''codesep_pos'' (4): the opcode position of the last executed OP_CODESEPARATOR before the currently executed signature opcode, with the value in little endian (or ''0xffffffff'' if none executed). The first opcode in a script has a position of 0. A multi-byte push opcode is counted as one opcode, regardless of the size of data being pushed. To verify a signature ''sig'' for a BIP 118 public key ''p'': * If the ''sig'' is 64 bytes long, return ''Verify(p, hashTapSigHash(0x00 || Msg118(0x00) || Ext118(0x00)), sig)'' * If the ''sig'' is 65 bytes long, return ''sig[64] ≠ 0x00 and Verify(p, hashTapSighash(0x00 || Msg118(sig[64]) || Ext118(sig[64])), sig[0:64])''. * Otherwise, fail. ''Verify'' is as defined in [[bip-0340.mediawiki|BIP 340]]. The key differences from [[bip-0342.mediawiki|BIP 342]] signature verification are: * In all cases, key_version is set to the constant value 0x01 instead of 0x00.'''Why change key_version?''' Changing key_version ensures that if the same private key is used to generate both a [[bip-0342.mediawiki|BIP 342]] key and a BIP 118 public key, that a signature for the [[bip-0342.mediawiki|BIP 342]] key is not also valid for the BIP 118 public key (and vice-versa). * If SIGHASH_ANYPREVOUT is set, the digest is calculated as if SIGHASH_ANYONECANPAY was set, except outpoint is not included in the digest. * If SIGHASH_ANYPREVOUTANYSCRIPT is set, the digest is calculated as if SIGHASH_ANYONECANPAY was set, except outpoint, amount, scriptPubKey and tapleaf_hash are not included in the digest. == Security == ==== Signature replay ==== By design, SIGHASH_ANYPREVOUT and SIGHASH_ANYPREVOUTANYSCRIPT introduce additional potential for signature replay (that is they allow the same signature to be reused on a different transaction) when compared to SIGHASH_ALL and SIGHASH_ANYONECANPAY signatures. Both SIGHASH_ALL and SIGHASH_ANYONECANPAY signatures prevent signature replay by committing to one or more inputs, so replay of the signature is only possible if the same input can be spent multiple times, which is not possible on the Bitcoin blockchain (due to enforcement of [[bip-0030.mediawiki|BIP 30]]). With SIGHASH_ANYPREVOUT signature replay is possible for different UTXOs with the same scriptPubKey and the same value, while with SIGHASH_ANYPREVOUTANYSCRIPT signature replay is possible for any UTXOs that reuse the same BIP 118 public key in one of their potential scripts. As a consequence, implementers MUST ensure that BIP 118 public keys are only reused when signature replay cannot cause loss of funds (eg due to other features of the protocol or other constraints on the transaction), or when such a loss of funds is acceptable. ==== Malleability ==== Use of SIGHASH_ANYPREVOUT or SIGHASH_ANYPREVOUTANYSCRIPT may introduce additional malleability vectors. In particular, a transaction authenticated using only ANYPREVOUT signatures is malleable to anyone able to provide an alternate input satisfied by the signature -- an input changed in this way would produce a new, valid transaction paying the same recipient, but with a different txid. Depending on the changes to the inputs, this might conflict with the original transaction (if some inputs remain shared) or might result in a double-payment to the recipient (if they do not). Further, for a chain of transactions using the same scriptPubKey and value, and only authenticated via ANYPREVOUT signatures (as envisioned in eltoo for failure cases), it may be possible for any third party to malleate the transactions (and their txids) without having access to any of the private keys, particularly by omitting intermediate transactions. This form of malleation can be dealt with by the child transactions also using ANYPREVOUT signatures -- when a parent transaction is malleated, its children can be adjusted to reference the new txid as the input and the ANYPREVOUT signatures remain valid. However child transactions that are authorised by a SIGHASH_ALL or SIGHASH_ANYONECANPAY signature will need new signatures if their inputs are malleated in this way. This risk may be mitigated somewhat by using [[bip-0068.mediawiki|BIP 68]]/[[bip-0112.mediawiki|BIP 112]] relative time locks before spending a UTXO that had been authorised via an ANYPREVOUT signature with SIGHASH_ALL or SIGHASH_ANYONECANPAY: a relative timelock can ensure that the inputs have enough confirmations that they can only be replaced in the event of a large block reorg. Note that this approach has drawbacks: relative timelocks prevent fee-bumping via child-pays-for-parent, and have the obvious drawback of making the funds temporarily unusable until the timelock expires. ==== Privacy considerations ==== It is expected that ANYPREVOUT signatures will only be rarely used in practice. Protocol and wallet designers should aim to have their transactions use Taproot key path spends whenever possible, both for efficiency reasons due to the lower transaction weight, but also for privacy reasons to avoid third parties being able to distinguish their transactions from those of other protocols. Transactions that do use ANYPREVOUT signatures will therefore reveal information about the transaction, potentially including that cooperation was impossible, or what protocol or software was used (due to the details of the script). In order to maximise privacy, it is therefore recommended that protocol designers only use BIP 118 public keys in scripts that will be spent using at least one ANYPREVOUT signature, and either use key path spends or alternate scripts in the taproot merkle tree for any spends that can be authorised without ANYPREVOUT signatures. Following this recommendation may require additional script branches, which may mean disregarding this recommendation may result in a better tradeoff between cost and privacy in some circumstances. == Rationale == == Deployment == TODO This may be deployed as a soft-fork either concurrent with, or subsequent to the deployment of [[bip-0340.mediawiki|BIP 340]], [[bip-0341.mediawiki|BIP 341]] and [[bip-0342.mediawiki|BIP 342]]. == Backwards compatibility == As a soft fork, older software will continue to operate without modification. Nodes that have not upgraded to support [[bip-0341.mediawiki|BIP 341]] will see all taproot witness programs as anyone-can-spend scripts, and nodes that have upgraded to support [[bip-0341.mediawiki|BIP 341]] and [[bip-0342.mediawiki|BIP 342]] but not BIP 118 will simply treat any non-empty signature against a BIP 118 public key as valid. As such, nodes are strongly encourage to upgrade in order to fully validate signatures for the new public key type. Non-upgraded wallets can receive and send bitcoin from non-upgraded and upgraded wallets using SegWit version 0 programs, traditional pay-to-pubkey-hash, etc. Depending on the implementation, non-upgraded wallets may be able to send to SegWit version 1 programs if they support sending to [[bip-0350.mediawiki|BIP350]] Bech32m addresses and do not prevent the transaction from being broadcast due to considering the outputs non-standard. == Revisions == Apart from being based on Taproot rather than SegWit v0, the main differences to prior revisions of this BIP are: * The sighash flag has been renamed from "NOINPUT" to "ANYPREVOUT" to reflect that while any prevout may potentially be used with the signature, some aspects of the input are still committed to, namely the input nSequence value, and (optionally) the spending conditions and amount. * Previously NOINPUT would have worked for direct public key spends (assuming deployment was fleshed out in a way similar to BIP 141 P2WPKH and P2WSH), however this proposal only applies to signatures via tapscript, and not direct key path spends. This means that addresses must opt-in to the ability to be spent by a SIGHASH_ANYPREVOUT or SIGHASH_ANYPREVOUTANYSCRIPT signature by including an appropriate tapscript path when the address is created. * NOINPUT signatures do not commit to the output's spending conditions either via scriptPubKey or the redeem/witness script. This behaviour is preserved when SIGHASH_ANYPREVOUTANYSCRIPT is used, but when SIGHASH_ANYPREVOUT is used, the signature now commits to scriptPubKey and the tapscript. * NOINPUT signatures did commit to the input's amount. This behaviour is preserved when SIGHASH_ANYPREVOUT is used, but not when SIGHASH_ANYPREVOUTANYSCRIPT is used. * OP_CODESEPARATOR in script will affect both SIGHASH_ANYPREVOUT and SIGHASH_ANYPREVOUTANYSCRIPT signatures, whereas it would not have in the previous draft. == Acknowledgements == The SIGHASH_NOINPUT flag was first proposed by Joseph Poon in [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2016-February/012460.html February 2016], after being mentioned in the original [http://lightning.network/lightning-network-paper.pdf Lightning paper] by Joseph Poon and Thaddeus Dryja. This document is the result of discussions with many people and had direct input from Greg Maxwell, Jonas Nick, Pieter Wuille and others. ================================================ FILE: bip-0119/simulation.py ================================================ #!/usr/bin/python3 import numpy as np import matplotlib.pyplot as plt PHASES = 15 PHASE_LENGTH = 144 SAMPLES = PHASE_LENGTH * PHASES AVG_TX = 235 COMPRESSED_NODE_SIZE = 4 + 1 + 1 + 4 + 32 + 4 + 4 + 8 + 8 + 34 + 34 + 33 + 32 + 34 print(COMPRESSED_NODE_SIZE) MAX_BLOCK_SIZE = 1e6 AVG_INTERVAL = 10*60 TXNS_PER_SEC = 0.5*MAX_BLOCK_SIZE/AVG_TX/AVG_INTERVAL MAX_MEMPOOL = MAX_BLOCK_SIZE * 100 COMPRESSIBLE = 0.05 def get_rate(phase): if phase > PHASES/3: return 1.25**(2*PHASES/3 - phase) *TXNS_PER_SEC else: return 1.25**(phase)*TXNS_PER_SEC def normal(): np.random.seed(0) print("Max Txns Per Sec %f"%TXNS_PER_SEC) backlog = 0 results_unconfirmed = [0]*SAMPLES total_time = [0]*SAMPLES for phase in range(PHASES): for i in range(PHASE_LENGTH*phase, PHASE_LENGTH*(1+phase)): block_time = np.random.exponential(AVG_INTERVAL) total_time[i] = block_time # Equivalent to the sum of one poisson per block time # I.E., \sum_1_n Pois(a) = Pois(a*n) txns = np.random.poisson(get_rate(phase)* block_time) weight = txns*AVG_TX + backlog if weight > MAX_BLOCK_SIZE: backlog = weight - MAX_BLOCK_SIZE else: backlog = 0 results_unconfirmed[i] = backlog/AVG_TX return results_unconfirmed, np.cumsum(total_time)/(60*60*24.0) def compressed(rate_multiplier = 1): np.random.seed(0) print("Max Txns Per Sec %f"%TXNS_PER_SEC) backlog = 0 secondary_backlog = 0 results = [0]*SAMPLES results_lo_priority = [0]*SAMPLES results_confirmed = [0]*SAMPLES results_unconfirmed = [0]*SAMPLES results_yet_to_spend = [0]*SAMPLES total_time = [0]*(SAMPLES) for phase in range(PHASES): for i in range(PHASE_LENGTH*phase, PHASE_LENGTH*(1+phase)): block_time = np.random.exponential(AVG_INTERVAL) total_time[i] = block_time txns = np.random.poisson(rate_multiplier*get_rate(phase)*block_time) postponed = txns * COMPRESSIBLE weight = (txns-postponed)*AVG_TX + backlog secondary_backlog += postponed*133 + postponed*34 # Total extra work if weight > MAX_BLOCK_SIZE: results_confirmed[i] += MAX_BLOCK_SIZE - AVG_TX backlog = weight - MAX_BLOCK_SIZE else: space = MAX_BLOCK_SIZE - weight secondary_backlog = max(secondary_backlog-space, 0) backlog = 0 results_unconfirmed[i] = float(backlog)/AVG_TX results_yet_to_spend[i] = secondary_backlog/2/AVG_TX return results_unconfirmed, results_yet_to_spend, np.cumsum(total_time)/(60*60*24.0) DAYS = np.array(range(SAMPLES))/144 def make_patch_spines_invisible(ax): ax.set_frame_on(True) ax.patch.set_visible(False) for sp in ax.spines.values(): sp.set_visible(False) if __name__ == "__main__": normal_txs, blocktimes_n = normal() compressed_txs, unspendable, blocktimes_c1 = compressed() compressed_txs2, unspendable2, blocktimes_c2 = compressed(2) fig, host = plt.subplots() host.set_title("Transaction Compression Performance with %d%% Adoption During Spike"%(100*COMPRESSIBLE)) fig.subplots_adjust(right=0.75) par1 = host.twinx() par2 = host.twinx() par3 = host.twinx() par2.spines["right"].set_position(("axes", 1.2)) make_patch_spines_invisible(par2) par2.spines["right"].set_visible(True) par3.spines["right"].set_position(("axes", 1.4)) make_patch_spines_invisible(par3) par3.spines["right"].set_visible(True) host.set_xlabel("Block Days") host.set_ylabel("Transactions per Second") p5, = host.plot(range(PHASES), [get_rate(p) for p in range(PHASES)], "k-", label="Transactions Per Second (1x Rate)") p6, = host.plot(range(PHASES), [2*get_rate(p) for p in range(PHASES)], "k:", label="Transactions Per Second (2x Rate)") host.yaxis.label.set_color(p5.get_color()) par2.set_ylabel("Unconfirmed Transactions") #p1, = par2.plot(DAYS, (-np.array(compressed_txs) + np.array(normal_txs)), "b-.", label = "Mempool Delta") p1, = par2.plot(blocktimes_n, normal_txs, "g", label="Mempool without Congestion Control") p2, = par2.plot(blocktimes_c1, compressed_txs,"y", label="Mempool with Congestion Control (1x Rate)") p3, = par2.plot(blocktimes_c2, compressed_txs2,"m", label="Mempool with Congestion Control (2x Rate)") p_full_block, = par2.plot([DAYS[0], DAYS[-1]], [MAX_BLOCK_SIZE/AVG_TX]*2, "b.-", label="Maximum Average Transactions Per Block") par2.yaxis.label.set_color(p2.get_color()) par1.set_ylabel("Confirmed but Pending Transactions") p4, = par1.plot(blocktimes_c1, unspendable2, "c", label="Congestion Control Pending (2x Rate)") p4, = par1.plot(blocktimes_c2, unspendable, "r", label="Congestion Control Pending (1x Rate)") par1.yaxis.label.set_color(p4.get_color()) lines = [p1, p2, p3, p4, p5, p6, p_full_block] host.legend(lines, [l.get_label() for l in lines]) plt.show() ================================================ FILE: bip-0119/vectors/ctvhash.json ================================================ [ "{\"hex_tx\":string (hex tx), \"spend_index\":[number], \"result\": [string (hex hash)]}", { "desc": { "Inputs": 3, "Outputs": 1, "Witness": true, "Version": -2079506940, "scriptSigs": true }, "hex_tx": "043e0d840001034f8f827b00000000000000000000000000000000000000000000000000000000f54c98ade5a10d6c8a3013fd077ed18e1d7eba9119ee318b83220c2521e1d55ff06a494bb210a1c73ef3df958da16481cec61f80281e9ab392ee6701ffc205db6393497681d92282aa2f55ec5f9dba411b5787353b36c1b33afc884249038954c7d6dcc55baf885767d4800c62314f6021cf59d4f88845d960aeebd5fb84cfe393939893a847b13753d9f3ecb8dbc264b24b64020f4897efebfeac68dd6e13b127b132859d792d2b293223fd7b591d03cb9b20735f18c0085542f1a4d769c1c874e9eac2d2e280fa3d9e7b03dc62e64c9fc80f0b09506b19166e84ab7600744cdfa6bf25f5df671725adb23887aa3e8e6d9200000000000000000000000000000000000000000000000000000000119ccb06e028dc54e45a5bb28199c854b8fd1b1797c2d7aefdb5823fc1b316a2a88e9b670ff7f282cb22d26adc79c464a50e3ce287739ec14d011a999dd66553d08d51fc9eba2ab0f8525bc6cf98cc64f09e7d7415ba7dc98701e3b6cd94342d872bea86dcfec4d14ada25febd8d2387ccef203bc6fc202c5b38c09b3525c6e68b1fb9e2284ffa3374777d686ad6c68c6ec25560645b739e8d338a3b6ff314e80698e180b836a315f90a0ed2e30260bea7e540f8a00f4d051e95f27c7cfef998002ba0cba0a725ad33f6d54aff13be272441af523dc5959980ca6c8caaeb518c46d07b0997c33d24827f9af222000000000000000000000000000000000000000000000000000000007263de59fd7c0115337ebfb53cb1dcc1e5ae6f5303ef40c4a9e71e3c819346ad09bf2ab51de119d11f878134d7715b880ec54dd5c7c5cbf2bc3b9db9a980432807aa4de4072064e0b8315010bb61cb85cf2836cd649d86f88170d747ecfc3bfbc4051aeaa453de0f9d90f33932588a03c920d523fbcdea58340733e207817a8a500d642e759a7181a666e8099592548ece7535fb14d11f8a6e4dba55780773387c464502794bbdf1bbaaa79efda2e024002357f2a50ef2a31120c4382be745debf40e0fc0894172a9d51ede424561b88615518c9c9c7b1bc7b8085cd0907e19d6fbcb85e3569c9349d95dca881100d390c321721809e8bbfabcb4c25b29bc4777c4d79c39aa9849c53b318894ad875708d8e6689dd6bc2f2aef433003ab8d0755387f56bf73f1e74980ff2d4eccddd0a00bb9a71b343137b69f7c51cb66d8e33cd70573f65f9157043f5267b60e64370e0cf33ab8d40e6968192cf3da58790dda9824def3b8d56d7385068ac8bfafc76f06e46cccb80852a59439a5f0ed8ffb02aaff01e4556ea01ba56592ae4e4ec33c86d2dbea9c83550cb9357d7b1aa67a1067b4c163e39202438ec52087f4195c1fc90f543fe41c630bf25ec79d6084a954ac70c9558443ded85901746e35226564b22ecde4e23da0905e38dddc4b34186e895fa5b743eef69ecee8513ebd2f821bb89c2f9ee7f0b82bd0d42f40bd9671dc163a5eb53a403831f9df6ca6245cf0ef03708fb889e4362dc5ee3b504a8e01136cfc3d3bbc44eede5e4abd18fca8315d27a746a749f5fec46254cea659c53ea71f99ed1e9744192d1743cdf24d99c59a671006a4474077ad6020db169be53eec1511c5157517253fdc901257a6f391c70dfed3d0a26bf3155ead063468639825752a4f386f43cc94223db499358afa7fb21d27ef72bbd73be1c9eb528962c4697ec9cbffd44ca6d2879dbf84de9dae29261c37a2ce87813ce34a5de387afd740d29727b1cbf0cbdebf4cacec0cc0c73c28d9f120bc31b243629fc850b55cbc704f16d7505c9b83aa079cb644c69cf6ea01b9c92dea2a624315471922626e10c290976a26247c0f733d49225b91e38074075bea6b2cfe14ba60a608c15351701b71c81bca089f2da62c5fb07ebb261682f2be982b2f699aa27df152d8fd260287e9bedd5b848186e38c3fd1895cc1e53d907bb75ab3fda26202fab8c7a8d0fb3d4445fc3b6f90b2a80010cd3c2ae18e55736e460278b9ed477e209939b096a2cb3225535666616c773e07293c100afb5ce982e933fd2d95a607968e1dec26a4b2e5e8e3e2b40cbec9b15c16da81f72d6bd4569e8e223a4351ec112d52cfe0a6e51e8ab660552195b507a648a42ce70e635437d52c8bda21d914d7fc0f2875f08af1f8803fa0a9a48484ae311361d2fa5bda2b3f689559bc2fb1c577f5acbfa7effed855ae0bf908a7e9269dff51070aa8a97e4954505abcdcebfc6ae1c1bc68dd593021777e9ea573fd79334e85c582ea900e1570337f091bdbb555c19b89262aba2b7429e24ca04c177059ba8dd468375f2a12e99937a22cb131ebb508e81ede4b807789c4318b8229b90a01a4443d74e6fc4ae30d04f7ea1c2bdbb98c2a83b316d56a093c790af9ff25ee6be833448dd05e96ed38e7b3fbfc7c2409c99f36d81e40196180e2360ad3a0ef439a0a6bed0b92e93cca398ca4f95906ba6d30b33e81faeb3c405a3247f488dbc86eca14e25ddcc4367f4170044fbc5e329f49a91410185475164afb2bc537500970cf1041b09d590f12613630bba8efacde59e3c8aaecd5bc5626a7bf0b5abf4b507b3659b6df2bad43d7a2ecdc2500b375c155aae9c62a8d8af503a927d859a6dc2ffdca19cbe8872c63b1083cf5b11fb957da72f631694d0dccf21820247943a90b18eb2258af5c6aed6d19bf82542f524c8066501698f5709473824d07f61", "spend_index": [ 0, 1, 3116999548, 4294967295 ], "result": [ "2d28d0672f1d46cb3e86abd7e682d2d3e9961e6c9237157f47d39f0a694bb694", "12f7ab0a282fb9e29c9fd2ada21f950f492bfd5778a94202398c13ae6e97f0b4", "0ee9cc212182845d4c32ba6b3ba8859800d5cf423c58fb1444feaf21aa9cf81c", "da78ece7c0888725532355018961f58ad471f242e29a60adf84c55007fad608f" ] }, { "desc": { "Inputs": 10, "Outputs": 4, "Witness": true, "Version": -1368569235, "scriptSigs": false }, "hex_tx": "6d4a6dae00010a916a4b8200000000000000000000000000000000000000000000000000000000678ccb660063c1aa74901ac96e00000000000000000000000000000000000000000000000000000000333575f100deed4cd21c61531e000000000000000000000000000000000000000000000000000000002ca78054001064ed3dec34dfc70000000000000000000000000000000000000000000000000000000069eb33a500b63bd6b3a8649f6e00000000000000000000000000000000000000000000000000000000bdef058800d2e45813892f854400000000000000000000000000000000000000000000000000000000dfa70a4b0090fdb4507528cb0a00000000000000000000000000000000000000000000000000000000265a129d009caebc792f12408d00000000000000000000000000000000000000000000000000000000a163d9dd0096eb42406cc5468600000000000000000000000000000000000000000000000000000000980b4ad1008b6e087dfd46e3e60000000000000000000000000000000000000000000000000000000008d612a30061f404f0047d5a85efcd513431c8fdc3e16e04bbda3ed597cba1417cd04394a876b5d008a88e54f7b6aa91ff086ba4ba2fc76e3cb8ff373f737bba9581678944d574c399a6627e2cb10a01bb88baeb4cafb52ca8f14c1c5355497520916ff57f78e173271ed1d731e5ae17e4776481955881d03c183e0737dba812521364159af700d062aa092436e38f6e6994a8b50535a2c1c0513b690c0f1bfa14612aedb1b7b4d90f1b4d4f2909633a36e4a245f6cfba0e64fbf262a96d2721e1d4417b4028b06c200887bba784d6f410880e64c1819432f44256d93e4198b7d62b6cc80fda87347ebba272e3d2267f39efa7268ac3e4f0cd8b077bf9d4831072b9cf1fd6191e6c430422c3225ce247ec07f94fb58d365ff4e59ac353c5cc9ca9be7c01475c6e6509298134e3fcded875ec17bc35c40c6e8b5c6f1ebda9bad1d752b655d9f9238312e5c01f59cf14f45bdfed18c3ae2254635a91405cc42d68f1d7ca68b97ec93d96ed1277baff57951af33a79edd01ac23f47400fa49ea85507bec9a45bf6022e3873d90890eecd1582e17fdf5160ce30eb87baafd169dd4d0f6ea2f9e1b45406620f9c0430a2a513a6011e7cc88557ebc7b2057b4b1dcc55b6edd7a203bb9d8cd9f8019f79b2df2c64410ceefd1a819668d915c1fcc46679dffb772dc3eb55205524f495b6642d311f1bf58024df8400567f61f1debeaeb6b95b612f7e6687e7ae4dc0c3e0df045bd018434ffa4a179bc23c95562daf3e293cdf682381f920d333e61143392021beacb2935789b8d4e86ab2b16d46e0c79c05166ddf0461614204fb01265a5e9cc552812085c68129f7e0663e511f1112588886b30d5b736d3414ea8b7280e5a017473ffa0e6ff88c36902de8672353a8cd464a1b2d67c8d0691d4368b6f5c78a23b8acd08e338a8e73e7f9bfc0f7418f5efcd8bdd924fae94f9f4ef68612144ac53ad0759e0f0d366fb6994d0a8f237236eba419c3afe1176e569bfac7384c03ff056b17702d440a1b0965a753193df5b28f550244e4652bd8f6d9209a3ff027f54c493302dee347e70d3eec95621a223823b5d33f9d59f6fdf66c15ae2ebeb26d26fa265ef3485dc6db2ae40d41da19de962a154baf84962547099ff17ca2e32fd831f65be2c59136394d33d64e75ef4828c7059c0f670769a46a9dfa38bb03f27b15eea1567e1241ac5bfacb5c7737109e1b7dd6f6409b982d2da48a7883ed01601869ae39528755419487c8035b54e66ec9078fa8d655effbd5afbfc067dcab5270ef42a049d32d9af1ef63abde30321a5b56a4e38676ae9a7d02ba11487545ad6829ac5fee5a4c15db77faf50ca1731e85399d4edf189343fec7f0b7549ff6cd94c2df1f048ea84237a5febe51908922d8d5ed87605236e88097fb3e6f5b61735a7a1d899fdff4e4bba1301b0c8008fc550123262c28064e8974ee9ce18f20591c0b5cc9f82481c9e558f44b2b1707ce53ced8cf132686b50bfbe0f3a501f06b37b21c9cd210da0515d73f0d569b610db7fd2e016b6fa063c83c771b81414585f112106d1cbff1c15bbf4f5d01468b9f152a7b04948881699ccfe8b71df6c8841848462f2ba63574b4b82233adb84101a027071d337b73f408f21c333cf80619d033adb11f67c81b4c8364e03072b9cdd06f20fd14e38dc0d5f73ac880ba5f06f0215f67f23c2253dc5d461a438383eee398996d97f1916b0ef6d8ecf027e1aa21827fa0bd8fb04eb0010c98bf673bfacb8a2619b55899f0c86e363e1ed26e43a38ac0941934cd79a0b5521b1338269083b951025b92562b057e738d0c57e6b47cbb120d482bc3b34f1ee93c3de86ea4bf6a01f24f47b7ebac399d4bf3228606dc23695f55a3d99d78e032ee4854e5c3a7d1574c5b56a476ba88a6bbc8263418b5ee790c88da6de6400225763b02f3164c3655ca0c33d5ec1ade6dea61c64a1e40e38d219e870f064c993d806747642572ad2bc5f37ab58edceac35460c7bf50afa9ca8e62c9e8c506635c3301aa9ab70d8c73a955768a56af4e36862d2e908d18057440ea4e9fa7edb1b662a2ccc10b737e59ed3f1f4b8d9445243a685f167ba068153e1d6b865ab827fc01b28cc9b08090dc0f413ad1071760e7740d2251986eccf29c12246dd98171e67b27902a3d02fd58010b63aac9d24630fec45752a1adf2e280c4f7a0697192f128e1ef02f0c546db67f8c45cf55a39a7d103ebdac927574b043a7bb95942267e1a488d60b22f08b32102a7aab4dede478d19cd95a4b5ce911aee03728cbbd9c7666967a86c500ac7c6ff63ff4849e5432bf8de5a695e7ca4d5f1ab2ac09d1cd7c26227194287e0f8f3673cdb852b6d03005c85afcb181fc83a8ec0ed95499be06415c79d69429888a90187e7789f5a860b873abb0f7fef8c47b99e362891451e02eb31a4048ed4aeeebf49603ea7fac87d8134ae718dca06460536a011715ed4b83ae9724aebef0c46bbfdf02ca85ebe1bbdf5f45e58a2e96d514d98ce425726904607e613b16aa3025e1f671f1dd913e60995523035718e7f898bcbb46ee3e90e76b03ad99b61737f1ee2d4c3cf23d5614f767d8a03e4921839f59eabb29ea260684783a2842e6b0d6056429d2b390a697aef776fe8021492db57fcc045e68997524407d6e9b963f8970b5c80cd43a1d0ffc4514da60b26a750639778c902d10e00d8a569c4a8c7008d1388e8b8714c7f827a951dbd9c5a466174f9838651e86cdaa19402c8dc6427d84e73fe41596d6a1d2bba03fd4801e784079ec830a58842a8cb33d32cc56cce22b89ea5dcae7b2e659cdc6c87f6567ebae46e81a5f75ec4495110482b84ce0bdf824dc625c5cf32cc6b28075600d03d48982d75c4755ca3b7fcf9a90f7d8832197e8b96c64158eb3b568bbd48995c7820940e4488f882a8ee842024e91221072dc32917c6da4c03b86bed15fdf2889697ed349649be9b287a1b1e6d5655e7110fb3c98bc417f89eca4c3ca9f3a8891162873298e85ac83ff64adcb9622bbaeddba3bce44855b84c5acd7f72d6be9bc58bd7e9e273385a555019be50dcca5d555170fa041b472af4e9bf7b322178a3e4166b1dd6d81c7cea97788af5615323c128ca9d15dc267dcc41f6db00c8c04c6cfff3f3e8cec109ce77151b206910df0d393671685ea4dd66ca4e20e1b06ae442dc4d4c4c80dd34c3ce214bd4a3e138c82287311366cff1113b9b87f653e00b7757f57dfc011669d691591c3f04c90c9e9757ff568449b89bcce976aeb19b7d0ec42e0c0ff7414910f63f150aaad4de779604069eb6be22287e2dc2161f540608fa3b31728a1220211d253496c399bf61df8691c36728c486e5e867f6cd43262044bdbebababdb8caf50afa7f595ff07b83595de7afeba51fd2a475a419d154e312e5233d5941b45f46fc2dd3df5bc2212cc33c51e2468f5e17d17dfaff014b60024983705b5f9f263055b5ad52fb27b818ec1fbbc1de9d06636eccba8614fd2860250561d19a406b9d3a67ef125cfb6a22c9fb0e61ed3e65a93fefa8edd2fd5801586591b2f2ab61e013400acf71f0e023d17300cc90c1f9259bc8524b2319e77bbba8c4d286a0ffe799c57061f3a36f831e2cd4c5480a5dafa9c209c93d7cb54a56f1b3670ec1eef3de8494c496061c14853566c11e9fa4e77dc3aa029be7a120644ef0394f6cbd581a323b56187769669cb1a5d99bbe08781c95d6eab57a3c6e1d1ca3484b20bf3f67f2b6ef9c6bdba800e3275a469f8e39630366581f2b275b65a2a3643e02142c7a58bc00e60e350f930fe441f443454c5b7da4159195ecc9ea9d90929a74186312877f3b3f8a0eb61037c73f24d7f13fbe2304affcebedc366318b6c1a53f470efdb7cb16c833abf27ba330290ff43209af9eee39081bc576e1715d953ad728297c3c939dab1848763e6df0c72198c8571541b81e4dfea8196bb8f8cd319f80e10e64b61d1541bcd89ca33a6e67517052512906159506f3b012b76d5b4280faa87e5605a175c1b05ab70f91d98eea78f01fdd401e032ea5ebfebe20e81bfd4a6fc2e8f99017f50b310f1310b3b71c70c2537d132a2f6c588db5af8d24ba648ee89fc0553b305f1664f9e480ac4c103665ab51d13f94bcea38d9faebbbd6fa6298a8374448f1e99802499fe7b64d5a0e607ebec52ce1339d073130bc7d68cc0f74c29a8d313ee17d38c467fdb225a1287f9e2c328c8da19a8834809db2ec5438d30df24ba3c3b264858998ba973f016016f117db6982ef3d43d31236ae3bce49a938d43d8cc46e4de548c85cb2bfb33669fd7a9492e62e761861693a7a3aa14cfa3243521f8ca7ae6add2d20be4bef6ce40bb25795b7f53009135a992ebf8563654463e35585fc9c380940f324f9b07f638c54d6d5da77ced9814456adca7fd15665797381580f2aed4bd800942faa64a2a086ea01aca5cc4a139b234ef3837f789d406481f17798521571d5cbf83336d03a4fb054c2556bb423602364006f6f8d59eea0689fd280e29429b7052b4614aaf785e22c70596cdd11403d9a9e9a60f45395c7e4085a515689e37ca942d5a65f872fd3223adf2f7bfd47fce21f280ef44ea71c755dda9f41e730b306b90a1432ead90f9f788177cbdf41db86135171d2b6d8baf8e0a3f019900e19dc9d9668111e3300e1a73aed0a68a25e6d670cba7e1fc6c18e8da346402b732446a381a75c65a0959b1b4fe2d116b801688880a9cc014e0e7b5851610bc49fddca01aea179977b87863ab3ba9004a05a08609278c5bfbfdbe9f6844b439343d46a0cd38b40b4ded6fee8b563a20c25637f7068810e379bd65b704f6e74480d129482f88ce63d9eec54d1f19dd113afd36357ff3d1d989a4992ee5d8c4a25946e8f79b1a80ab76685c568280eed7b6902f66d3e29116ad75c547e8ffe4c5ad03622befb7ead7bf02b5c0f44765d577148fcce0354f60c939aaf4552f352a2981026208ee74c730ea5e03b78756b09aa68e02f60931a2ae5176a0e6eb02726be51b3f286192c11a98617138710d27ce6923bd49e099f18feffc0bed3f1d38474baa4c69bd92561aa4827cfe9796a1f3aad098b4eb8006b02db2ed8fa6dc84eb78a4857cc9f027908d90578eaf1ebda3989c9501c7c098b9ded18ab12fced3473205cc5d1c2b8608bab400423402dd10eacb71e6ce96a0990b34d94a0e035b3fa84b62fc21323a3ff4bbdd6602b694ef45572d4650fd80771eb1bf8621654fc43403fd3a018f67c2e675cf14d60e6276425b877f4c0bb9c057d6004f07431a0e641cbc41b2d77a5304c06ddc39cc995248b366cb79f3c38322b4074ec9bf147d6d1663deb54acf30d9568085f910ac91575901834fb234cb0d8b1579eab248cc5b1172dd8b1872dc8665b07c17f88c37df4f8f67bfe1e4e3c5a0a7259a7a2687319e458de79b8bc377a573b760fdea26b82b1a7ff7e2e89c756d9c7fb29a75367c4c44b8e6444a6ce2f81902a1bf7e2485039d1b2b3810e680e22770953abec970c1ea3eb8244f8b5cf19d23d637b8749c61dd653b34e7e8c7064b5c2d67793c867adf8691543df88c2e96ea08e06fb29a40575ac4b18c8506b08c9608e9e9512e132f093fd12df8910ebced42aae6e768977d7195dc4728b533f35852926671d08b1a68bc6c8abea8b4dd82811bb3d4959363dfa923a5a40c656b0b557afefde201ddfeb04901dd91fa610e4be576555cd592998b4d2e16e64c48acd3ac6db3473ac77625de377c2e1bfb8dcbf8b7b111c13287a84b6b7bf35e2c54b37064fa8c4e03a19beeea55ea95caec8e02a4c73c0344c83664deda81e64b20fb00a602a174031cdd5248db1abbd543ea2240f4e4a4df8c7648cbe45c639ecefbe7c4bb2df223577e63922a7a6bdbd3a6d3908f5cdc412fb455516341d66dca4b4523f82e7f9d3be73ae24b97985e482d6d4e6cb82dcbb362ce064c0dd54a26c42e843625f155f9152f94aa6ba04839323ee78828dbf5e0dfa4d628656c736634f9122c4fad047d0513f7118ce77c959f9eba47b57ccbf2671c6250665f83e915d74ccb7cb6faa028eaecebc21b6bcda7193695592b98abb6ee95e47547da6dca4b9b740d0f4a6a6c95ec7ff2ba481133efd7e2b9b93376f08ec97f40a4045a167695ae1114150cdbff9d3081a08d03f2f0ca0b25435ca28b53266cf94faaf656b4e7fb7db882185c973186743c45064ccda60163e73a8c19aab9ae7d2f9e563ac8fffca64ed9c6277f342a99bdda91efe01c2cb24e6149428b56d322f2f7b31e1c61e581b57afb7acb216627ce137fc8fcd14ec5c8d4be39beeb9dcdcc5087422e0255c29f10870ad9bc8931922a21e5b57e085d3d7f20bed100cdaa22a6af6196892702a6eefcfdd601649dcbca53afb0665b25658b57f988e3fd743ce52ee421f4973ee95becda180c7bf41f7f1b3a0c7a5cfd184478575f7aabb059cbb94a42fbdd5b1b11061b8a442a2f29d1096ea85439d89fc031e3b22d85ed29423632ae4f2b6fa98ac4e4f601d91c487f6c84ca2d660aa157dab73ff31f441e6653e9be98e6c08fd6009a5c7e82f4de916ef3650b7a9456dbb77889763448205f42a7d776c871123b1db50bd73f3d60291b1ef225372e5ef434e256e97b4caf64eef889af73818c30d3b24d5ae5aa15353b4e22de089ea4b560891bc329e12e0aac9e7e2f8fa83971eced1115f4b664f5e80700193c60ed15c07f6267f61e1a07b37ec3072e2282133ced8ddf25e8f865580b9cffa49089014a601bf000adebb5ceb5bcd539f3ad20f9c7ce5b3b1d863d4bd60a5fda1f566c9da7c2196abae8b806d62a01ae6840cfb864487c9f3e58b2c22d21ed292a56fcad7a2c53487fff3faa84ad7d58ffc6b00c60aa50e637d4ea74501aa568b1b2a349eda1d04bff81bb052e1d927bccc3daab9ad18fa77740e936c6575fdf6babdaf7a241114ed4f3d65bfb4fdea7a4f57553963df5a5e066b06e82663e54b58a2e5c8f0ce57e2ba4832139ebfbc70671646332a86e971aa9a9d25dfc89243f41cbdec196b279e1bd669be402c94134a56bece2d3d5e733cbb693ce523ee2ab7207feaee1023c4a11758a2c9a1f901623002b9ffa27b642dc9b6c7ac02c2bda113112e597bef8082c3cf95ea4689d29f1f9e666d75aeadd181f92b6e68119c31bf71310ab8628c5f5cecc32e1f2d760231e1e99660a6ad7b3a8ce6d677ef61161fb9979c3897a21871cb431a7aae519cac807259780068e48917d8f2d2b70b3737311db2333d32ace68822d2bd852cfc81eb5dc356fe2e749fa6635228fd6813997372dfc4cce81c9b847615bf132c3f5d1fcf341128dfd4501c98fa3cbc2537cd4185b53bdf095a83bc17acd63119b6195490014a772c4b1787873696ca6087052284db67c5ec38b9243f7a476acd2f10374724c57c15f193a6cc0ce635d59989ac56172b7bb8efc2d6aa17dca85b2a5690a9f409294b33579ae8ffb506152f3f2f3e7c00955005e4fbfbea1827b6678306cffd56cf3f43ceb0afdeaffc891e5bb7ec6eafe24e2aa5066185820d20cab677bc9b83c5a8f2307d4fbd3ff3a282e457d1c3d6ff041763044318b7721dabd51e43337d37fa3064ac7f564d7ebd23930ad11b38d0d7312a62862f7fc9e0664eaf0f0ab5cea30e55ed52078edb0c722ee7f6d5ec4f3c17503f2a97a498660bb7ea1a0e305fe25492944af4b7d4f7bcef715e714b840b440209650e24ae1302c4a658fa7dea6ca6153ad886444ff54eea7672e9b32a1196e593f0532def46e64f04ba46cacdffb7aa1f27f22a4f30001cbc6c09ac7c4450194df9fa302996d8af546361730744ec2264b884d8b92c8ce254289a2082e182f5199f9e22fc37a23459cf97802ff48448c3c66eda84d4d4583db8946f1d2dca19a5e3177769190174e056a0bef4a3695d4c5a47defcdddf1ba513966b59824d9cc996d123422ffb527eea355cd8be64d0400838229f29f263ed5f31d158b3000e0ea1a41d9d0bb1c83fb36fb3aa3087f3320bda1e78620bc4cd4e7bbadb5a1a79ceed8458b97067be123a9a3545ab4593c9f8a341b0c2cae3c3ce7cf2e451185c45c576203eb157f6f0942a6d18343e0cdf7e99305720026ca36a9f2a4b29246cfc7917bcaf41981b2e6cadf1401c062ef1b4f1f98a9e480a6ce1224cf49181eaeb876726315c2c0cdba03bfc11d091042d47dc2ef5e2fb49c4ab4597ccb65cbf0caaaa6015428f7c223733f2cb7cd7aa8b4c7807341f74e83d796b08a5ba9f2c7e56b51665c452a96f1ba0f7490cdcb248b5e5c85c687b6c5710be23019a8bbbdbb9f451e42b79423657f7669e1e55fcac0ca6ef554d7df76e9ff5429b20dae46ed08b9597daeb049c16b03f095c036b7eae7af530281132a2a3ec12c262ff2f66a261b61cf6400d97bfb413de51aa7bc650840ff0853fef3bbb3fa0aa2481275b7d23e369b3e17263f97d49f7a33caf484ab9629345ddee07c9da56a542ada207d98bd7e7da0f38e9327554ecb0d97fe8eb2d2e6e03047e6a05a5bf9f2ef5fe92a9e086e921f117d2bcc37cd3b3e6e4951f19137d96efd9401a1b86a4c70d612a6e96f2516c5da067c58d0431657cf86213766a7ff003cc932ab129772382f6f6ef8d7191a25ebacbb167a31d229618484276f63069f9f837e910829153d31412bb74be44a246f67cd9054e2725baa93cd362a180da0170b726f7698dcba636acaa61817675444aecedda4bac9cc814cc160ab382768d1a4907c41f632178086bcd42da9f7b59d66aca71fd27ec3badf64355c971cef6f9266d200b054ab5e6c8442d158050a0445562d66d9bade327d990428d3be4098a8a1532113ccb8b973aa3f87c07ac87bd8085dbc19fe2fddfcc626c476a7b39cb83e95f62ff1500af385d97e9abd08e6096e64f1569ba5559f0ca9a7c368938cccd5ebec3fa36843ce3fd4bf8a09310a6fe96dd320ca684ce4839b938fde5b11e7b81aad3d2053c698e8ff1bcc5b90833358eaa7b60b006bdf825a062fe01cd4818cf83c1330906298f7acca65188b51fce45a5a9fd64a94bc180267e1f33c8f052ffe457016bd061572f92c784e245581dfbf378f108880202b1089656514daecc405f5ed23a231f72524c81112662997f371474c3b5dbac649", "spend_index": [ 0, 1, 1311624179, 4294967295 ], "result": [ "e01a5d102bb5f8ba7986e7e4ab0fe8c4922bddd005adf740122684a91afad1a4", "0980b070c9b5fea0a87b3b4a148876079cb54dc3db9ca560411c1c8cc3a7f5d9", "3871f92f02152b4846c1f00e3100be52b8ec53cff9f496061dcd3ad3f2f48a2a", "10b88c130695168a2fc2548e4a6f4fed11388a25f3da39a478ebbce6ac2c8299" ] }, { "desc": { "Inputs": 1, "Outputs": 2, "Witness": true, "Version": -1051347441, "scriptSigs": true }, "hex_tx": "0fb655c1000101e3bfa656000000000000000000000000000000000000000000000000000000005296f6a3fdad01023648cde2159aabc319afec69ddaa111fde9d94585b4610fb3586e295e25fe73989f10e0991620403eb13fc9861f45021df9966228eb44d474d174823ff8ee86a2ecc631b1267fdb545612f78b4b1d300863e675d47dda8c600d68015b7688d4446625ce245ffc43445d0e95ccfb3275948ef8c21eb59887ab32de1e540d20b62182d442f5c82e41e74b1faaaf84075d88f883fc2e5ae237f3e6ba115b0b2d803fba0d28472c1d0db5e4128b2bce7fa1c1bcaa8823b66151940bc37b9e81cfb2b31f1928a6d1d8716925e91f02de1bfc8b54de0f606b950747063444149f406b003e3e954f89769626083128540ceefd85546537fa7d6541b605cac7c76feb9eba6db727892bccc686f5003758c1c36e7e5f56a49e3736dd9e4e85d12d242315fb52cbcfa19fdb6f794e99bc9a4c7504b76e4288bbce908e1147e1ffa2b25147229b464e03c9a196e5e660fcf43c0a824497e5c246cdd3c79585c43069e54206c06c60a00123f4a3f4927166f290354c512ef7e42b5930c8af1e224a052a0ea1005ea96f19e368509611b183415810e1f399dc3afda846235ceba7224fb53bc8434a2ee37e4d494dbd0742ca294cc04910281d342e9ff46eb40c8747ca18aeaff3d1c00fec1600b4642a520fefaec35d3df74aa13c1d9e37e6405e748512e67399ffa9f7fba8d3244e2e1d6a9efb716a78e4cd947a577a193282d407ba748f3311e7f8880852074a47bbc74994e75fac4aba473c99b97e7ea245e8c56dca37ba1bd4d64522f9eb474cc29018d35da3a1a8abb02032bf0577c681703c4e88ac2c5a57ae0f678dc5834639833fbe1f0e1b9fa817582c30fb07b51641cc4d75e3be4989c25f4b339e3194ff91a0e08916c0410a407fad131b0d15958ed8439f6dcd806554121260a62c36b32c82e0a153e93983ea7152eac373761dba154518e7da0a6d90cb60e306a110886b01353f1dc76ec082130f8176ed80444d9bba60cdff3ccdf31b370e837d94055ba6cc5d5bb8fe396c6d1bbe92c6a19cbd371db892203e7f17e91aa33f093e886601473319154b8fb4db0b0e68e7872e7002fdbab5d6f93dcb61500e4447e4c819fdb590bc7803f8068a008e3f9f1e250a6730a76881fed07d6895690f0444f49019b6e11939cc836fd5b8e4a01f1007c029250412d8e7fd8ac89476849b2c020aac27da1ff8618166303eec688936e28f0a31adb1263dcb48d0d060172ab1d0f0e15102d2815dca08a19d9c2d872224623dabed1880912485e54d3331ec9052a778786498ee0a57271b243e3c854701b2284cfc5d9e5997107cb389df6e58691180bc4ecd0ebfa266a2379d23c561c7fc3b29c393820be0534237fecf93fd33e5cd775e3e17a5db3b35e1d3dff99ccc3263796227526b62c1836704cd13bb50aced16eb449e5511dab9544d1ef4eddd839ac1f73de9bb6a5ca714fd0362301489ffada6154f9aa55fa3bae31eae4f7a9fc02d9aa6dc431cac4f657a47d75defe00ed7ace6e2aa0bfbf06a6f95ab872fc7fc084668b35991e18eecc9a5eb8eede635a619ff7bb40cd1e9f36da0c1fbb9ba88667b8a33d28ef266c270a8e258a933903e8658f71b4c104b34a90a685465490b82483a231d1f5193b58a356b8aa509783964c6aec4f480e6d37a82882449e9f0cad78df21cc73ab71f8253bf236fb67e3807e1f7511da8d4ecf17df6794595d2ce4981e6e7639cbd7dbbab6b18a4ccfff9f404449d82f8c9dd5ea718deb2c5cf373788d8dfd02d375b6d52c8c12d6bfbb5b2ee6a7fe45d705a28df3a0097e90bc4b19ed940530d3244da84a86a9c241bbb2e2048ce0510fdff6c9474f0ac33423b93fe6c07d9c24712761f57ed7c19cd311b1af416544443a6f7f61385ed927d13921bc9ea8a44cc065e6b17db35451b439e1954a040305b2b355160426868746819ccdab1023e30f326926c850ff52a06e8c7852dafa114863f65b25ab7495", "spend_index": [ 0, 1, 2574543262, 4294967295 ], "result": [ "f995d871d35aeeef5d42fbe5c6e8428616d2888db157697579c17add7d2408a1", "029adfd50489e1921d57b997e609451fc71b9eebd5ab79a068d96beb221bf3eb", "e1a58a099f934e0ec776d858c811fe485ebace34a67d0ca3ca23f5b00021a262", "73591132765c175ff83226808b2efd2f13be8e3acf422ef43f728bee7a112444" ] }, { "desc": { "Inputs": 5, "Outputs": 3, "Witness": true, "Version": 814707723, "scriptSigs": false }, "hex_tx": "0b748f300001053c73ddd9000000000000000000000000000000000000000000000000000000006d37f59d00ee34fd4b498f005700000000000000000000000000000000000000000000000000000000f66f9bc300059000915d417d6c000000000000000000000000000000000000000000000000000000005fda9bba002da98aa5f81966170000000000000000000000000000000000000000000000000000000049bf1a56004d5d2468ac523d8f00000000000000000000000000000000000000000000000000000000276b4b5500fe26001d03fbecd947d802ea49c8a61d48f577a041311daa647870c8166b0accbf1b2d5e050ffddaa2b08d3e1b2f5392bfcdda9e4a1c19c2b1d9f6185d8d3112d09a983c02db4ce36d9eddbe2daabdccd2dab45985eb37b6349bc81c871bb26ab409211a4513ac4666324e7f44c608fdf5bf073fb64499471f81e6f7950c50f952ec14506ab7985656e5a78446b10a59439d98522177037401faf445734aafce951ba24f0cc68bc0b59a75614d7717265797a683485ac416b4f0be3f9230747f5b6c63ca3e3b8650a68e2fe9346b8fd17c9f29d8c6c4012bb9ab0f970578c8e10acd035ab33642af34daac3882805910b8312bb512d9126d4b465a8260f27ab99c2cdc0936c43fbd2bdbdeb2c35308ab9ead119b767ef01afb943dd9e2b5e053ea99d639fa3b897afeb812d315a80396bc60d59b61fa3e6f461dd718b76c057fc998d3344da47b9da5d024dc4557f05d2a270a9dfc48f297b15c0c37ce68da274afda61593aeec9143b85c060e90ff86650e4fa4e9fee59d4a0c3a3d18351eca4e7cb94fe3f3b156e07217638cdcfb6bf8d512f86bb38bd610832cc7c75c4a94e9a90153ecfdc8b85429d2968cdb48c8296777133ff16197f773b3536a0a1a2d598e6776257685c969d43044173724d8cbeece0e7053234712880a031d12e84ceea423a95efbecc0a5abaabd5a5647fbc6b606116e10532fd7a31d8738d37cfc201b726bf6030f25c3961125dc510417601ffa52cbddddf2c185f4cc17bc7b0d510247b575562306e64cb4e5359d7d70d09e3cd89dac10d82fff19c2255a3ca6a992fbac4b414f23fa1971e838de2e393b2c20c444c238b78e0678cca3901cf29417ab0aeeca9626fcb7be5e777da3648ed088ff4d4154b701f38dbf127fee38897a5ee7d7d357a672031a3085600ae3ad2384696bbdedaaec8a86e008f064c6ad5950eae848772bfb597cdb9b9af7baefff97e52965fd8cb2c8e3561617582942eeb827bce577ffae69ac948a6409c69691c61e0cc55cc11320df3ac90ad2917913e701d69402016a4d88b84915eb546ccf34a37a8b33135dd10306ab10e73bb2ab3fef965423557ab11dcf6c8135660b07a90881b876e06047827fa3e1ae98798604a0dc1d11d9e715102edb2ccaaae863d10ea8c2147b8ca3e8b3f10f082140222d914e15599706465da455f6d5f5b9f14829b4a2611476b5d5ddeaa32037e69098658ccf4790671e2bc206020e9e06c13bc00ce2d4ba17cc6689bcfdd4018fc919d232d5f5021c3d689a4625593fc68aeaacdec4e408bade148365996b6da85c4e9fa11220dfe94615e2ff5356b97874059aafbcac2b0dc90792c3ec08ef4a2bd135ed059c52a42b1d1c168558cd4a758a54752b433d624ab4e7971e51cd39a18aa1229acce968579641aba00662976e6732994b8c3f1683bacfbd510b345391cd438f171898612236705e51c6d603f4c95f5739f80d50abf2133c168af58450f26cdd571ec8d0c6ce4dadb2cef510cb424e75e984f9176e448683c08b3e11419f34f8eb11e1ce4914ae35188fccfece3372e502951df6715ebc5ddad5c13dbf70835c1141cdf2ecf81ed0ecd8d5cf5ca8c57203440f2beaf3f91ef4bd5ad27f53de363c5116de666c5ae832cf9216cc8817091355e22e9dc7ce4f652783b2b523032b7b346c25621b65f4a505b220fde444c57a9a80088bddb5726362ba8a8207834b566c2f9bf9272883aaa62b4553d82010d4081f3bc8a2f7c4878ad4adf0c8c11adc04c41c39ba49dd764bdcb7531b23837ede7d615ce76dd8b68323df8835479ee40688172c881b81cec1074456b53ddd50ba6d96b113ea8a04d5f0466f8ca98b6246d8c84c54d8e9362a6b93481fc2b2c5109c7a6649078c8b38ebffb1adeb396aea039c0b6354d17d5077bcfa3b1103de56a85d7f7fe6d244e4689e03b33515e1674724291c138027e4f0eb953286f4f9e5d790351b538ad17a6a2b0dd3758d06d84413c0bb851daec68775eaf4281010ad67dcfb377b834b3adaf308368fc9b105c16e62e76a629b8af41c7de29a54a974115541e037d5f0f94029dd551d72a3b43e5c39c111a8ce30ab87a0e2e21770e924be91b8e9644c8bb37568bef66a355530e2ccc596bc553ed10fb9973c1c83b6d6f088baf33312637a3d7b47aba022d6e74eecb728f18c22e94fd022e73e7f3e573c8306926459669e80b64eb755ff25df4d2ce78a44c6072729834ef9fdac017c197d8b0e8f91205b0f689ecbe2ea97aa26b6d60d3f72923185f561d7ecc627b96ad0744f69d0cdcac6c30bbf45e9d208f69c6ab1ebc3d83e39da96863525050a37d1d2002733a6fc1581e8e9d16f4a64f2455d7541646d5026ee34cbae5f559d822a99086c75408e376e8d932f87a773b7177f54675a77fc34b935aba64a6fc836b7be488764f4644e68c09cdad418b438a15f02a6cc148bb5e716af5cbacacd4a2be4a5c34e7c0a9f534c19442bb1c4c19fc18567685ec0a6cc79f997061ba073169873b538814d6204b0f0677e9904575bd8d4dafd93410e89065d32ba5fb2a912605368bda85f0e507b68b504baf5003b6308b0bcb094d822ebe2369f0a1caef770051c5a658ed4bc909405c7d30fcf6fe5f52a560e3189e308ea401beb3ab31c1c9a274f4daaef6fa6ddffe0d0accb622d782ccc2d8a581db691c011ec745f8a1c1c4bcb2f52efe1c2856e9a77295e8ef14b935820641d952aa895b1c6bc46a821a85d024b39e734838d007c62ede95bb4c14c6e35d1abf959dae66148b358575f52d9f79fcd81a3d6a4bc7bc62f2499d85ff5833bb2a61a12e28b2b70e8433105ac084998ef7982179ed17df120050b9408a074b8c88beb21ca3ea9359a0bd842c8124e1b3e12bb2f6f68f3887f76ea02824bee5f60ef7d6a438f538ecf4cbbd71c0bc5a41acb03c8c46e6b4ecdd47d16a00e4dcebbbb36e88c82e94c5046081dfdf34fa334eff1d2582e72e39da5a3a0966fce036748b2fa55adf9c96e7b995cc10e3ef11b34a9f6f4eb2556553e6572d11013ef39c033c40232aecba0e36b34daa35f6d9df38b01fd6101cba60d0c4fea9019e3333c4dea24bba24bd906ec319da74809533cebce37ded637c6a21c5fb63096809715971f23ca63b613fe45722cff3c8536d2d2ac71a16476d78dd29bfc013157f0c74da2d05a4bae9bf8145b2c2e5d5b98a1ce1bce0da674490d607e67cfac4fa2832088d237482e3184722b67747658e6c2c94c65e3217bb4e5e9d6c02d74dd45829aca17d9aafa2987b05ac2d6aceb51c824f3d9164a38166d85ed09069399a5d76169bab088258ff89a49451999eed3a2de860e81c6a69e2fb6c77921a018cd29ff1f368f5c5ecf1f831b175fd2f40548adff6425596a10e4d857f3eecf29e00c0e401ed85400d0f22cca0cdc3f8bd566409a5f50ca75adca2de1659698608fe19f5d7ce08ce7d8dd5df9d46146364b4487288290a6d88f52a9c8f525512a6fadde91329d86198bd49642a6f75523e0d0fa10ba996429652c173b04c94f182d6f24d0bde2db590da98c9370d25a6f08978e5183cee41201fd2201d9c1cc04c01b43d94b86a20f89e498560be4361aa120763798da9a303337116095fd5e8d368f0f492c79f120d532020a9f5b8066ab8f7f97f02f0165ab1eb352aa651fff9d70afbf497fb82d2bfa7b95c8b7913d9c63756892e3d8a4defd7c63e366e5e051de0657777d06b6d047a065d34129e6c61406bf004884bfe21d27e840fdce1446a47b0bc55bc6565aaa599262e66102b42e7d410ced19a14e9032c0b52cb73bea41cd6ce76b7430eb2f7442f9fd2236b2c37d9f6a01e522c28b5ccd27d7a0b728cf99f86c06460d67c9521cc5cb95e4116fec8b4fa42dab258c3bd4ade03cc6690e5ae0622be12ce57fbe86411c8c42e77ed684bb719655ff5b47b6b111868e1768b36a31fc09f43017e413f9439969f492fa4ed622e8a6751fb94c3f9908e91981", "spend_index": [ 0, 1, 2609405748, 4294967295 ], "result": [ "5f3bc9fd7fc449341f79d74af750943ba58ed43366d610bf9c85832e15b8f4f0", "564800f51e04ca3288dd040816b60cc9fe4647833a750a98afc943ea22807d8e", "408c08e764904e02780f3e79cc5e12c06cf7acd222e71bc22ba05735d98f2d4a", "aded80f68468d06eda4dca4c1b0685c8cd5563e81b900cf29c82f28d3ad77bee" ] }, { "desc": { "Inputs": 6, "Outputs": 1, "Witness": true, "Version": 21403141, "scriptSigs": true }, "hex_tx": "0596460100010601d21b5000000000000000000000000000000000000000000000000000000000cc926fb500674bbca5336071b70000000000000000000000000000000000000000000000000000000087fe629e00cae822a64fe86aca000000000000000000000000000000000000000000000000000000003ab379d5db80aa6ac750bff88788ab62704b6d28b5d41262af3c738792a963e95fb02fd0169a194a7accdec7ead5fd40d86f6d043f58d81217ed028c8af11ce797fd503aae366f79cfdc5e77f8c77fbdf3b59629e5262f6a88d8abac1ec5a9e3be9c9742e18083573bc5a90f812a63dcdede3e3d444a964533b6ec75ccde595c389e7c8de759530a578b7af5c6bd6de3c88444ff202514f5e22599ef86bf96b2331e7db56f85eb538358598fed5cc77eadee5055f22969d408d32515a674702788e830a3eea9a7c4d35ed430d475263052ab5f774fc0e6425bb466b123ed43254eeaff351b74ed8c000000000000000000000000000000000000000000000000000000002360f547fdb401292a6b1ce12bea1b921383a0da232c9999f28d1a6cb8c3e48a3c8bb493daffa7359575055c7c327d3fd5d620847a9bcf92ca4dad7632727c8f62623029daecba1f94cf734c843c1d52003510c56b9a01d3bc8a56b9371ec83b3f1b89b3e7f9a8d87182d13a9b5b829c29805a4f09859cf5f67bb8eb9c6c620569b2d2e91dc103de7d69ded829cf2c193892dfbab165aab1643e80b9d48d64e971e40d39cc9442a3c498f77953c6ee5e361b47a849fff0648fd9b608533951bdab1568e0e8f1c2590c4019623034afa5ab96d93bb9aec122bcc329e756205e63fab1349f1765c680660910d7303029091fc2fc3539e7a6996db24734297c97e766073d89d27c67e5a2064fc312760099dd2c60674d4332b620573dda5bd72b444eda33174c18c05f721b860f4eb2819a9384d57df40a598f2aad3909041295d59f0a8d30aad1a8c100f779607f4aae77feeaae5d8f597d8f270e115b66883ea05e9c9d3b273ea0f013bab65059bab42f6b2e154b54666f20bac42bd482481e1a084c06c700726efca97927fe005727c2ee470bd97bea94a717f18dd56d52a5fc26c98f06e32b1173d3b1dca7406ee3dd554e8e3280fec79939986e71c8bfcdff78bb9c000000000000000000000000000000000000000000000000000000007fc3fbfffd01016f8315760178a4ae021929732cbfe8fb92ca4e495562d3d38d7e747e070fe5918c42937d71be004c8f3987fb5507a23cc15a92fd5c864eae227e41798af6c61f6e3314b931a10aae0d4f6da2d4c519417ee5302f3f844a32ac914429c25cf553d8fda38bf1b3a107ab3891b66195999701021e07c0dbf0ecb04df0389ba8ee241da0fcc470886d086fa47861c165dbbdc5a46dbaa5c731d8838bee0e00d9d041d8c073ec35d0bb684cdc2890caf837356d45133eb62c103d33450a531d3da116d8265017597b58e61d9e81f64015c97c6689315f1b3bcae6543ef8b14995497b4565c4afb9e9adfd7ee1555306da7d854ea094fffc926fa6d9db0913c9d3030138af91cf26b6dfd6330000000000000000000000000000000000000000000000000000000000fc550a00d67beead01b3eb058f1e5d1b6bc89326504bd91cdeb1d12524c41f4bad8737a0742c673bac363e3c1159cdebcb11b8a7825f24012ba87c660db47a6736d0b92a8515f8ad66a5c926da385e17d0bdfd26b546f9b86e4229a673269c0500ab7aa65f316c2abd00e4d3b5e68303a7c3e233c286d47e81664a421e556a6531998c232ec00e093ed1f3773a4287377c203026efbb1a04a54212b8234ca8556f0b5e6a6111e161326c9c626eb78e9042b5d197abc092ef7574a11bbedee547d0f576805e7dc8ca1b1330bde8ac2f427b239c8a81c902a0bdba04fd39014abab272ab3ea33bb5946fe9a18786ca2ab5d0bdb07a3a9f38130c8b3be1dd13a7c4881b1720791cbdebf2116ba09412cc9d4b4ef081c702c88cc3cb84e22fd7b48d21ffdb250fcf9a27a51b0a4e5ea4d5c0c2b3aba3dc55d37db1f0f88c54ee1dddcb7e38962cce4b4db92bd036079d1fc62ebf6ed94482ff5fa1c567a5c938c130dbc58ffbdcbdea5bae09c0600717af56042976d15d8a38fe5ffc144cf4b8391c4950e3199ab2a5f2c5fed16d8d137be7ce5c0f3aca1ea8cdba22aa4bfb24a08f47d1059b7836364b52d0d4c4c3e0220087a76b7a6eb5680f407f3018d5b0fe017732f5373be87f713b4cbfc5cfdc4bf4fcea60d08ba50c0f71a4f1c01acb685131b12cd5a745ccd09a4ee694bf6ae2e16d5c456bab6c476cca8f3e9e6b2302a578a7acc6a5daec6ffa7153c622b08df87f79a0a25457650a3d6099a243b7b754d1bffdde01a755b0cfa2547b687e47612cd8808970be6da73699a66936a65dc05ec720e21d757ec8e5c578893f42cdf84c91c6bb89eecac05c29aa67f78b2320f20c52bbba11d18a70e6e32187766780d0c1455805de1c921be4bb952da6f67e9016c0de75e96880f22aa24930c27f61f2cfb42f0fda45dea3f8dd77510d2422172db478415c069541d055e210c16614de7c40001b2be4456b77eaccccd6689457793a29c6a3fc8430f447661088fdf3da0a931a68cd4d9a9264006c218fc11fe41c19312479fec30795b9bf1606b2d8278cebf6243fb15834c2f47460ae1137580fd39f52c6740d9e7a9b0b72c91673333101d1ec4deed2dea4cade9779c9caf41f044ccc3db08c270a5ad8fbf16413d3b657595b8148a3ddcdecd142efb3ad3be784026e9ff3ba15bb3e9902d19dd1db39e8cbc9a9e49d679122c3784bade4640cc7ba9a396c61890311dc587129d6e65331a5a041688f8bf377c7534e2b04a93b42c5315d43696dbf7d26fb1c4f16e31a0411aa90f3cdf93badd0a30d92b3aca8ab0c0b2d1b07e3c99f85396c5f2377646180e8880b22a3ccea23acdc1819f6f6f4637e4f16eec41fe53dc7d8391ee9b60f88853e06b6268b4e3376bc564d9400c0f3e9b30d1a268391dd6c69a6ab5110b4545284aca27b56cd2cb7ba24f37b9022fd7d018a529a69011930c421fa1c8298e8a2ea0f853819c1de239c0e04d8fbb55fe0a36fcff19927e1c8ee08b0051aa9e4241b52c35505527c7cb49b5ba85f6742235a0efb6699b59c18ee90b88d014aa7439cb6da9dfe7b8069658df473d86f77de8e3abe9702c7cb57755b2a07029a67346e4f0155e33793e9ea17e230c7f6679bd870d936ff4813220662753b7567549a65d259d3b0d4f76f8a2dfc9dce0589bc8976818fd7b7bbc1b138c4fd913b1c05346505052b691c2781b89eaf7014d86146a928e2deb36e162f1b5111a9140e030a3e3e02fab012320cffc361155e3d54780bc31d9886e742a9eaecfee7226d9090a61cd9887ac47c2b5ead34f254e8956a77250eb620da3d7b35511591e42cf2e9208fcd075eba22472d7552d16d4f6f3d95dd98d22fa5df590ab33129f8404f1cbb37da8a154f3823354ae0831d545ac5807e64113c93052f2ea6e8b42d6cb23a8164d7f5ea186a03ce09d2b27fba5c1ab1306443d899c09192faa6d3583f411f62eef8a9f20f05d16d9166526502a002bea82178876bec3f29b4d6b14ab55c554a82006fdf29fdc41b52f8f5290e0677ade64afddfe9c91e0a70c18cb77df26a15d1fb9b00a2728fe1ac5b64963e8b1a7cf4f41a2b0e359f81d9dabd1c03d78c963d6e9b30796a1233ed4f78979818bff3209d348502db99e877c2837c19f56ac5c30c9d9fe3b111536015603d7af43acd4a5a09789ffe18ddf91c5cbd5bf934ca7774d046e87cd5fe5180d683d2b0fce914ad495295cefa281c10c1fa286130add4909e664c9cd82b318cb8f88576f7d1c1e968ba054257fc04251fdb19d179d425f261f259ca49a700b648c52fd2b82dfcc746074ca87f899382a76fc980e5d0d53ef1382d77b308fd56fcb64a91585c240b7203d31de0dd534421e5f6705ac224679582751664dacb38161331e8e7b03080a6fe6327d2bb80d867f8efd92f35b8391903551078fd8facde46693bc4d05dc7dd08353a3d14c4eecdda0c509f8a225a8bee815916c9e6b782c4cb2a0f9d724c593e849869c8fffc84ce768b19bf5fdaa9a88ca4e9ab3e2aa7c1a8b41063460e5c649172c80a65352c8b50cb3b8da5c092d3d29786ef536b9004a045fda1edef145f7f81cf947f8a582c1b09f8cd4ac04a531912c8ba673af7f4479844797041b2677d312dfff9922bf974d2843e907977185be663522df8da46ca5b860f49820ea46388044a366a90727886af05e4419a9471ed6fff9dd5e6baa2f5c40f9db17ab70d207d359d573eb435195cd1e69bc63e6fa5b3110d57b47e8e1a472fd76b40756bd2093d49215eee347f2e2fd98d017ff1fc8b3d5df71344f8dae329b49bc9fa1769378b2697f6f0aea609848f5f40446ab77ceaae87d37088cf5b4ce90b58896a91d9bde4a2703e0edde875bc768836eae0e26097a3ec206a2b0a44e874424ab70ae596318e2e3e1ff9d0ac5f749c6854909e8a7cb58359377f6981000a31ee769d18fe9ebff7f291ff0d525c264abf29b3d52611fa85f9600173ced565fd2ce8651a9745f967b883c234335d3222484ab5f4592427863242805337424517b1b391193e462419c78f7e457eec1ba9f6571e9b939b2fae357f3bc73ce8f80a205e10d48b7bc11e1bc77cc10b5c0473773a0c023a4967e63e41159059b18e51d972f878a9f3dcc2aaa355aa94c0358631bac7ac90e279dd8577b025bb396c260bbff4c5e3bfb3b512b34f6c6283bdddd1fec44b0a60fe3368cef33841d604fdda017a6d1cc3191ca5b81377b679801e62f4d0890cbb8223802df810a9d1354438049b3d7a0e9c8ab61a4656d6dc2629a9fb4e25fa54a9139d6646a6a147f9577dc1a7f32f8da8d56fc06b4379aa064380cc8802ef69aae0a2e962ebb8308fdc13468aa5935cb388f9d8efd3998dfd05423540194c4e53c7a0066161e8c285e79a4649f0e66c3646607a915e1c88f59e81b8affce0fc807adeb916889f48b94e5ca31cec3b2528ea318e7b0d424d6c5ecaba319d388641235cfa3514010fd4c0c54e7172ce0505526a885de8f353532af79159562979839a5a90f08ccda684a8867be69036f0d6598a4c992f3a43c3ad1fc1d7c09fbca86e3782a49c3df7e05bb5a17d50632b577903fc5c9c3ccfdb2c7f9c94bbbdad2513eac76696b29ae2e53abb1bc2f4b6f8fdcaf239380a51c7ca7958c6b31b7422551e9fda7e6eef57bcb35e331fc1e5a375b29b481b4f400f880f9c786a11f002d97972cc1c5a626bf86b8303b6603eb343b69c1fe3f063e9e5c6b7f1ff2fb393535dae2409100ec0903a76922c978ef7420c6145c5f4782691ead4734deb53acc9eba6de9e9cee2294c9767ec2f9a17cb8f32b3ea0bae12faf5ea9c1041528fe5d81d620aba24b199b6eec08f630e216c830f53c3264ed031d66c8f8a560d5594fc7dba25a01f8614036ca1c29b5453b4b7ebb1d524d561fae087d71e71d4028f2a6f60a55385b47d7e6d16c50a59b877c5f95bd473a02134697df794991bf42b51504c269345f0621009d4ecb25c61260b9af0576ed74ba0acfb87ca7d0d2afa0c3f4755eb93494f22b76611518fcc01c69302a816d90e0b443f89623e4b97917c78966c2e5285a71945e332609d793615693a9d8f4a351ebf2eb036bf2a7946ba702d55efb77dd61584faafa55f842066b11d250bc53905dae083fd1de527f9180171f486a6044a96eecdda76a42e975f7e7689285b9e5af32b9049beb95341541e915345a38909b8c5c9927c932af502e0726d84864c3f2a8866728fb5b04bd3f73cfcef203134b06f08301158bc85b49fbc4d915712e0f031da2533825548c87f3a0d213e204effa84bf31567a358d01826246e224a3e67d374307fe3eb66990c4052678f415c938f20a502779808ac8d37c7137dc2563e3bc05470a16b573abf62a8a58464bc83688e5466fac402bde107e940feece935197f0c2b8b3c0f9314be42a3c1165cd9fdd3074b76aa0ec8455bc366e4b1bea4de34c2b278d854299428d1e59f76c169c747387c04f2f6defa126cd32abd2a83edcec1198fdc301671e12f96e0fb407c506fea811286696d25f6363fdbd40481070b4998ae9e05fbf5399eeeb086d5453e487278d20934d5bb48a3c549082e4026e81832925c92aa7f50f94ac0df136ea6102ddc25209769ded90c67eea3a4622141167b9836689f11aee4c81471d00e379c025f9c0cdd61c3ecc293e54fc78486d8b5f053c88534dcd1dad1f33eba8bb3f242d84c4ed4676c4a595aaa1ff6fb5d3d9d49c1cb4a606d628c8a6d6fba32614b3c75c59476cd8a854e07a5a73e30cbad512302291f090bc97e739f5993c4ce65cc16966f6832c18513900b6de7059e205b333de39dba7548ce5ceef1244e43701ebf5a1ef73e134d5efdca291a95cba7d4718a03e49ec1b48ff1b2529dc17616e788e1b4a5bb94c4fcbc3b0d63d4814dce04806f2a2fa33e29ae146d03516cb9d567b8f0e52739ef42685e4559f54aa914f1d685e0ccffe8d971d84f3e3dc78b55ef3825fe1d4f93b5dde4d7483f272d08d5e69c090172f75b1b570cd1d2f15419de9580433df9358395ef41b42a87814c8b5597afd92dfba262ad1784c4a56b43b3960db6bc391f576285093a9a59e681b46ebc8f7bfa4c668592a8759c81dd5400dc5dfd4c54c292c7b1e715367be922e592cc7a851d7ecfd0401ac846196be62de8be7ab31884d3a40ed6fb97d2dc08e3fab6cc056b35516929a09dbc81ed0adaa8694e46a6973566974524149d085532d5ee08e77963f2bbfcd59d4dd97d7b20c099bbc71c3cf9a2d9381114a3bc402e558cd9f20b68b89fec071ddda09fc29a9f61bb7b339b26c146e3071406092b1204d570a4f2f046a1ccfa9ad2780356fddf70f549e3aec3190c764d771dc69c1c0edd6a01cafb695f248655a2929e2c153bf92bbb97c75ed8a677bec3a487bd8fec11586ad1659eed9a99aac10705d979a57a3abf42d17db324a6ac56d52f33edcd523d906587792dd3f4537db5b11ff1190b218d15db8827f2c04961ec9190e72a8f9e8838db13bb4b74a264d7f597dd596d169875cdf219c6360ac9d436713e0b38a361659eaa57941ba50449e765e00bce31185741feacb5f258c0cc8f574502beb1220b39f0341bc22fcaf8c1f4603fa96d310f8bb1720d08fe5f88d08c021fad3f6c4b8a65c04cb34bdb23d8ed3ab86d48f2cfa9355d334562adcbf470bc2dbc7baa9d7a9ba48ea72433d08c2ed9aae3a4e8ff3ccf19e9a09799497653481bf686ec1aba8add6f67b2f8f59a2ad1753133baebf551f489aa9deec98a2dd9fffb57d0e4fb145344d95b459287b9a21101a9a8abd022962468a7c5c79a9b1b391502d1e5be56330f6199fe691be0ef34f3446fa1cee5af1bfdd10cdaede2fb367d36922bbdd925462f0f532f25d295d2380e947e252650a861ad08f0d395f2255964ab2c089daf5bdbe7ba1bfa42d03524f9b4ffdce01ac8d4e394e74da1ea643ac7294d4482a24f9e5def87c8bc44b2d8ea7039580e6b88f1840f77ff4dad00c862bfe937ac8c5f2ebe7325c13338b286bbf066f2dc113a1f8d34948c29119814e09a57f6e2b22e6d3fc68faab24444ac83fa627cb5e251940735dff350debde2ae483f363e3483c5569cae870cd8969c3bd942c4c00a29142a8c97e427064779e080cce75a46f19dc4a0bd89dcab0fd7fe9bf211cbc0a945b1e8fe80a26f9486bdaf92682a027577f76915183184f5491c5497955c0de539a4374bf4aedb27afe226ac37114f5aa4c2793bf60baf4eb44a04e4f4bde01a2d5260a62ad7a99c9bc3b1e15b3c422dfd1b1292efb1a4729b6d030d67892882272a1ab255c83acedbb3bc2ce789a5cdb74586787a4deb1d726b5c3fbc45ca712e84e71dfe84e321566ff45504659aee25d65ebe46b8961036329267d08ff62b7188f88eb633699bc0b8cf8ed36f1977df3e46f8d965a65964d0e27f35cab715210207da86781ec5a78a06d290b66fce6bdb95fed09e5b18ce6dc38d50bf1baac4c7136bc9421dfea53ba199782b50dc93d0fa94b04dd9b19f7c26b3f1ca5176930334ae449b1ee7498ed54ecbb57162da15b4a4464d4aec222062ec8a025ae87fcee521e54a7980e76f79a53bea72f94d0d05dbaf56fdb26360412eac08d782ec2e004d3b4825ba736e4314b15dfeefa6a688c6a2fbad552420f9e34260c353de6bd8cdbe20f25d9b925be17416ca6f40a120a9b51335f8253c85a996eb814381059942df7f2fd2b2ad6a3dc72701d26dcc70b9b9272c98ff35b506f362137826ff1c01cb6e94fc45be8d4566e564280a4d459de12e7a4bb7e40c01162d9e0bf26005ab49620f3e9ec6edb2971892b01892fd6198a3f281fbd32eb2fa6286ee81ca124b5723a5a87669763fcd76e635150248cb644d6ba9cb39a764164980efc751ff4f0025206aa0c1f065d2f3d6f2507ba39e28e5fe4cb2619e397792954514fd7d774ecb89c3e93813fcbc5abd4a451c7a29063fcc42e2264cbc24b3ba4b1a7e89475cb57f618fb0850a346b62a8e2537146b67df20fee9189fbab7854bca3afca89847295875db93e7922f12bdcb1d179a1a160e0acad1111a6a8d297d03b3864c0d97e35c7d35eb7d429fb1abeb7a5967a99f2faa60a3333507de04cf9d061363e0602b149652018726ec6db2c25705491df598580ff52eb9f728b8a0c6c5602b7bd76a94af25d32ccc066ccaa6c414a74d475f323303c2d208a7aeb7555afd42c14686590bd12a9396", "spend_index": [ 0, 1, 2796535865, 4294967295 ], "result": [ "b20bf0f7bf874016ad63ca4df0d99831c1ce767b3ac3b0f50f2d11771895003c", "802dacd41f97a3865ae0825950723ac06924c7caa13598f67c9232efa8843a04", "5e67f8c61e39c1ba23abfea2d0f280ce65cf2302cf385b0828226b8fc36e6d20", "87b4a556c0b5dc3ea7d0853ac2357422344833b3a5cb16e4d347a0f6b74ffdfb" ] }, { "desc": { "Inputs": 3, "Outputs": 2, "Witness": true, "Version": 1925178759, "scriptSigs": false }, "hex_tx": "87e5bf720001032856388700000000000000000000000000000000000000000000000000000000cab6031d0095a13d21ad1caa5900000000000000000000000000000000000000000000000000000000727f13190053d917c59770137d00000000000000000000000000000000000000000000000000000000f537c10a005138206e027518707259bb2b34c86902e1031e3e2e4546542ea8862d73bee5c7534fedd0f90755ad7738a760f8bd3519dd0d71adf1bfbff642028e875c015485e8d7676338930d51dcfebe9e0fa355b0a45f4d86e4bc409cf5e8be215f99afff42dfd27229b55d5be188ea90f202eedd5ee9ef2c2a35b5f89945457d667ecc08fc841f34f79b25743cd13e83eae08a3ca9dbca956741ae05a1944fe1bda496eccbb7d95a4a089f04a5fac5dd3ae06694ba3189a3fe31feec2cb97598fb180b7a4e73c2c926e2f72af22bc46d74b37c5a97867486ec036d4078dee0b36a56c86bad746e8a509c812709e292528925ccec70058ed188b7b327ad59676f0ee7ae0a1b6784635865e097a6c05af564ad7fdb308dcaeadb293849c899c7237b0321c35098f37214ae4628e8aab2c1760d9a3b87712f69c4363705a1e7bdfe1209a58a24b774f38c940b5b235c031decd9b96cb8d795529a86c579d5b448691b6e9347b2eda029bd0dc7d0305dee4253ba8f964d2f9642274d86ff3694c73bdb27cd40125e3e57c2eaa86ef0b3df137a4723c36386fe15924654d155feedf70a2f56c0f25fa1841601c804fdce01c01e108a0ed78ef7e93645c39383c3472d5698f9ecef72defdbd00ac5def148ee21055d8e87262adbb72e3b9f5ba174c61a3c03cd75bd197b0b3174fd274494f30ce300ae8ac4fd3a6133f89096ba19fbe237d6ee3a0f5019ce6a652c60b0de903d53de6a8d058dd0a74a96f301f7580bceeb58e20cb2e4f4d66b109205edfd81cd1f5374c8f7a2bfdbe71224f950495f22e685c24d5ec231d4deba4d2af7d350b4eb0f7216cd692553c62e212c5f42805478138b4c49fd35847337472cdfb0a95ed19014da13dfc715eee6c91e6af4c6d13d090bbec13071ef2e99b634b1b96c6e3fc0c2e4d3d2828abb021f6721a2b7630d08d627b4f8d1584171be8e0b920ec1456cde295a7f12fe89a97b2511aa4e54b1c44748b184d4de656b06612b619b2099ae1892729f6e11a6803fccbfdf636e26a7f13d9321bd56dd733c1944f3b47a698725695c7166299c965b7e564ebc02ed3eca057e2643a105bb4007831ddc860b99342fdc938735c8e166a7d41ae9d30db4eeeaeb1bb38a09a451e1258927df33493deba07fa0e326fc2af03d733a365fd4bb6662cdf3bf7acef9369b340357d911b028e8a89a904901c9bafce874ce0974f042ccaef53a0b22e66a97990fec4a010df02820ae11beea66947fde80120122771f5b022287fc3b0cde2f62bf2780722a35c7b9fffabb4483f25a4d9c9d6f1e486e5da2857d825a6f06a91a4b020376ada786fd91fb14ad0b15b8ac2034b04c2e61f1b5259a80d491762d1745e13649d12c6bd6a21c7673fa21cf4a55ccda0ecb7a6d7cf57bc0b2879bda4c2adf62bd7b787915f5a0418f59618957685ab5ddc2618362ce51ec0eaca7650ba1d7f25be051304b3b6cba5a2b11f82c8cbc9612533d5611f0d0e1bcf64a60bb200950f62bbc5949c10b6a0b8957a1bfe2891d1eb413762b0ac9a2700df912689edc3a2a94535119fe0346ef2ff0da3fd404449395463d3eef18dc29eb6eb539c0a667ebd364eccb8a9666d932c990d13fb663398ab8e964598c3cbd298e954a3f5ccb640c932ba0105cb4553895f7b4cd58ef0252a363b28f4315cd3b93967e3c061508367cf814db05f24c15b0587f5adba5b3895a83a47c2944d47e52a1c9a39b84a954af50a3cd49c455d914c9ab25195c5355c24045b5b79a134d244f6ebfdf3b5c2267704513b51fd085bf1cb40106dd34c217200303fb2537cdbbda8fd8c7db1d4ad5aa8eee58696bfb6a5e58a979f6e95bfa86f8db432f1500dda08aba408f7210517eb5c805aefee3b1096bdeb29b30a1b10613bbc2b7c17a91d03b963af7d4863e3a5391ef9aa447ab435c69a4a1f77f502a2faaffd8701363bca086a732aa3b76a68b9632d71eb8c4d3688f4081e5f40ef72d2207963a2ce18bcf121ea94c80fb07579462a43024ca3a7e2c5e3d53b66beb4817fecf398e142846b16d786ccb034cb2d455b88ead1bc0123d0a97cce3128bc8ec1fbdddb0a41b063395b139ffc93023ae8bf25afa05be76527264e364e7f67f2367191ce8066f2242eebd90225c73fec97f6fe3a37011769d7f9eef3d7de5b62d3a4b0f6df4c528a326f5c998444bc1fa5b92e3ea258fc98f0b32e45ca4d3dbc29c796e3708da6ca0fd78345b3b5ebcf3e7658eb263b185f4048f22835c71b3976c226c420d558618daa4b43051e45852eff7f81f0192b70e88307dc99e30bd57483f26f655402269cbdaa9d5c0e0b2e4f09d5a20b6161bc1b3176e19578d0c47079bb789ca26e218ebe235626cfef665a317e02b271c47dce6199248daf06373434fc0db7c9d9f763da2b66c330d113f75dbac87d44e1a1b3a4af8fc15fa5138a0aeb023b1b357cc54da141b0f72edbfd4f53d7ead2ea105e17cd3fa348f28ad0e8d9629e66da1bc1cc557c93cc6240026a713160f8c961c7d90737180e7437c7b18155559fa9ae4b342acd42573d90228a2853c856da1d6241e033cd5a4af667cdc3678b76d67a55b8dffea7a398a0c3abfb9aff7ba8dd69fce4b40872156ef691b2391f88a07811b54b4f176023fe7b3f565b1afbe25e02a7c720b0e35983b82749358bbef2760390dc028fb92faec6ebab2a72b4298f560af575ca56d714bcdd678374b31b477c71817edc83ab772ce48ae2df2bd4df788eb46c12890bfbf11b160b085f64461528a79d0e8085ef5af43cd0072e7339dbb833d51d4c30d43c336ec5b7065e3ac88bfc04ebb76cb0196157223303758dbcff789e9716716ef8b434dc827aa1e3865f4874f4219f9b4f9d69bd38f1d89e177b835f3589ad22859873d25927bb53c2f105219a486508e7a8c941bfc372b51e8d037076f916965be6cb7ab9814185c5d6c38b8b955309d467d8b49d97372d802654b9a4c2b47ca5c980c75bdaf3487154b0fc585e548c22a03fca488d2b9d2f71b482099edbf9f91ff962ebd7f8adaffbdf68d45df9a9d9a25b2423131be2627c4b0915cdfdea0143b4c9942e37c67fa4f1d684dd8258362f0889faa91efc843c05b8bdfa6a0f30ebe12055ff1e88a4531a35b0d8e24ec5c5a1d49678b7017dbd08018197645a17872c50f39fa027f17aad11b3a5383768e4e9ab472f16fec17fa6093f2c4f7e7495141e4acd4b046dfafb6f725fae55f683b6f94092c589b0757789d8dcb2b00b8cd2b96c9a77b333f9118d9b1f0bde08e6a6667d81d76bd622cf0b225b3da4e36a67d0aac083f6604e89c992031091039a4d508b504b9caf437876cffa89efe3544bcfff3e723090476c013f65e3267f49a4194ef85fa0a5fa5c229dfede0c70af901edea230f8e5c65da6071bf55f7604aeb7c812fdd71912e1047e0a06af0627e2a8cc48b575e8c17bb4a7d59f4e349e4dcc6fd3498ebc98a003908ee066602ac6ccdd2327b7ee8d67074acfab3b845f9e7edd4e9866819de8021226c321f3a489a4bcf7da93b2817c6aaad6d7f03743ea3f65831ecdfbd13396aac82cf68ba3ac3a01c9a0980063d895029d573c298b2ae61703357535a672048b946a8fb33c3e0a6a3cca25cfe80a288f4c83c8afa026a35e9e0b4936879fd9a054bead2d7a443bc62029c2b76a05126e27fb04edfcb07acd36dad78cdaf13480b440ff69fcf792929aa8e9114b426c58e279dd80b47a3b53c1a075849bdc8f4251ac25624f2c9d69188be10e32b702fd7201dd1a38c74f28d7ed192299ccc97de5fee37d86cf677b4a93cdd4d57b2345901a0cbb76a3fef8981c3856064099d2f754186892fcc30b9ebee3208b8a6207bae8cb9d8d894cf3301640e9442689d2e8ac45a761d000a3d1f4259726e6b4494f8d4cba43f4ce68dc9cfd01aad9c2ef23b61138223a99f687562fa17e2a33025f17dcfe9e8d7608eedaba9562b82096e5e08461c263a5d579a7f104a445122d718c2e9a1e72d7157a37c1067f2ea00a5f80e6badfc25b82ce089deabd156ace425b4ab8eabd96e60da6565ac2fd225b95f2b25350ee6b06a2b1c0b88db0eaa2a33d6ac7dc594f3a2aca32c000bc539ae9cfaee05d6dcd38f7aef23180e9d6716387c0784864399eb9cbdaae5c0805f36875e290179c5e7b9b7dd054390c0449989e9c4d30bdfdc31d24c60127beb883b171e9b4dfdfc5faa0503d7b9d78284f7763b490afe2b41a2d8d115287107240758b0c5cad97c93f656bbe14a0a3ca92be59ee858eb48c9d0ab4350cbfe1bcb077253958fd9401811f8f4b6068477201aebfedd962ec4a3af8505bc567e9025f89296cf404f7511ec08588c7140c0200fc66abf09fffefc9e21e18cf64c405e68aef2923c014ec6cf65aaff5092f91a11f6fe67ae8e5defc323128882e412562455c1afd385d618f93e72e3787ef9f4a11a258ca57162004d7c6ce3c86fbdb8559566ff33293d904d1151554dca7ca46b53e7a59bc9338beffbcf504104b15e18d4c307fb1ae3fca5b1777809974351d7f4672ef191193b66e56e490106377ca181df08039f6312060fad9cda564be2b61dcb8d24b34592dd74940d1dbf5a01686d05d545a1fdff3f1fc6a7f086bebb6b289c54256f4fff10b51fff6395c768fc23836aa47a1113393e18c6fe07efa218b8dac25cb170c2d40fca0d908520a314935730f554e233518f7b9eb90a8f6149a02f9b028815b144cb6c8f81ff77c3d9c546ba12e6e605a4eecf8e8807f66c8ede1caf68f3afcd021102bdee3515b483e62bdd007e4446e78f4b9ce50b2bd0e8d2eb35e90031df6945adec76996f46f2bb20a0fdb982a9356e67739bfdc785f88c04784e830dd2c0d731b844f1fcf", "spend_index": [ 0, 1, 2531309487, 4294967295 ], "result": [ "6aa5030e6eb67581aa7c7b2708db784358e09d8c9b0ffc64310ad8ce17e9a642", "c6b316553f883ed41ae93c6d5e78560e625f38c6785cbcadbaf742787d2592ef", "b7df572832f590a304798ad0fa135e99042164719e03afbc3dce925f3d6527b6", "fae5e2dc16eba4a334d843e889ffd168bea0f1984071b275d2b002e6fce8be7e" ] }, { "desc": { "Inputs": 5, "Outputs": 1, "Witness": true, "Version": 388868779, "scriptSigs": true }, "hex_tx": "abaa2d1700010519f5c040000000000000000000000000000000000000000000000000000000006ea557d8b117df5e3bc8e37495a9d11545c33b2c595415f8b2a04c107082cea0b6880f1bc1c56ef6b5173e2411b8b009b6cd645542795ba41692ef896e5b3cdfda28174479ca46a39a9a7a2b6deead05881f812d4490c7638d7622ea64973a516f30968b5bde9e00c5e185f5c7b74f5144d18a8785a77f41d5b0369910521e3cfd1060889a73cdaea0553bdd73b9a74a4723c879d798500c1ab8b4f3348be682f420cdac352ca865bd3cff954121fa02ecfaf1893683eddd1e29a32b7d1a00000000000000000000000000000000000000000000000000000000d8d22db820b6f2070dcb6ed7fde96cd0daf36baf689815cf7434fe76cd17b40d55caa040f6fde5a2bf5c21379200000000000000000000000000000000000000000000000000000000f283d7d3fdd7012e9a3be8258305b795f179d2eaa2b257f33a61ed25ef99b46e720d64af6ad1e163e78d722ca24f4d1fcef74ea1b43aff2a2490021ebc5f4207a832e8129afd787494df1ed827969ab9b1a8ed85e425abf8312b32a6c37a5e2570a33cb36a422053d6ce242296e136e163ec84331e6b005f5ccc2cbf8302d67e5669f66166b390fc5f14464031e142b99c387aee115bd785cd9a254eac28d2e08c602d45f24c49e15d86798eecf8492a5e01c8f38262b2a78949406a6271ce95b4d403dad1b63e4a92a9ae8070ccc7911e3f6e7755e03f524aa5b4e62f6e8b726d712b775bbf6dd11580512df826ace61c2cec6b71105055f48befe2c7aca4a7fa1e7910892e279281bf073bd16b3d8c728c3b8654823c76ca4750e195bd1155e9972b02ea16a06fc65d8637fc37d589a22279dd0534d5564af0d10ec8143bcf6d20dcc769ce0e85dd2eba3ff9292464e703e4188c188fd5d30bf07a0a9f45bbbf8f7134380668b13f45c4a4dc50ecf6a338c745cb21ac3f8e7554f058c0cf57553c54ed698bed87c659ede75346332b9f75358133804df22ad1cbf2a3ee4a20f9baab0e3ec1e179528ffcc3f50812d6a8d5f0e3123e913682e42eb1d6d62ff7fe438024d8fd03a8cc8e25721a03139957c9a987eeba99260ad4369c6027b1f9acf037f81547000000000000000000000000000000000000000000000000000000008281c66768798eee90d89d4bff1de684f992a43812d0f27b9093151e22b188d3cae8c141b08c3d8f386da82dd2b16a8bdb5dde5c9e77ea90d753bb3eccb7dd82dc1eb29a62ace3a46c4cad25e3c2356f722f5de3933e952dac1fd33d50ac33dd7b4a488fa3be375af9832b25a46696913bf550b3890000000000000000000000000000000000000000000000000000000031c3c9f0adfa37aceb6b344e0a96379c576bab04ffd61edb0e05fafde6b6a063aaf7320c1a3f2eadedb450efd98e32615c1b7ec0ca2ffb5281d05cce41cf81b52ae0f4025e624d64ef7a811aec917d6ed31d8769a8ac482128780b2be995dbc308935e970fcc8c0c9d15d08503ff9f8d1cafde70dc21e8a056e056d366a9451df9124a2987eb5e438bab5a12a05b87731467e36423fe1c7d9b045f5d77468567b6a604f9ce35b2d01ad020139e1bcfc99fcc26fbcd3f01e4c968239235b20ac84f59e357bdfdeb4b732437828a6b24e066b5984db7a9d67cbc6f7f2c68124c0e3df45f2bd76f8d1ea27d38c583dfda2f2805d11e914807ab4ce855e29189dc29c762a467acfa2a736f2b648f9be1d08fb6a71c56c4dc549c0426e9d32b1ef4db61c0b8cf0dddc4a93a72691a737d85a73ea106aac065304286b9c09443bd053de8bb39078ec9b8fea69b39b8e2aef850828c643b6e5d510cf0ef8429e5488003b0afd2ecdc2dd1afd4335849879acc3c0de1669c9e2f6fdaebebbaaf83fa711e9fe34f834a90043b0456c0e1e45c305ad273ed86c10c522eb8a3f4c8d0c51d236a307ab7ada9872c6826d7f67883777581c94fd8610114b863acecb440d638332d5ff8b59cd7d4d9065d143e2f3aa26687a13e36319b3eee0df12fe9cf3101c2124ce5641be61fabb9351727a09a5b609e4df14fe2c38162ec1afd1dba431891599ca340697144c8c8dcbf53a45f9a9a947498e3e3e3c5a5a13a568587275c0f3f2255be3267675fb73c5c00572c53c4ecd49f2df83c47fc36ac9373b54808e25c2ce64b3dd1949476aaec7f6a25671d322b3a9b7d29d2dbb965c18825de47afc6916852cb09b88d8258e89116fff7230e0448600b2f65fb6fe28a72cccf44da378ad4a7dca0152f2973bb9fdc82ac01988d5509c42aa640940a8a67a5f18166b9ed42c08391ac6a5fe6e0505512f8f103bbbb6721a527d9b17c9b80dcd7858c20cbf3ad1255614a6d062c4716875d682f415f2e443e1732d432ca7bda8958fe7c881853176924b313cdaaf20bcdef7601ac4d35216aa0b2e511d611a07ff675dd2921064be23f6d401515e739d88e8db72120e0f96a0b05c4367309749d01a165fa4366812c78f90c015f39612ef3adaf24cc67e464a0033de296b6d8d8e7b7f50e99d5446e533dc5d59de124e9ed4fa42a1f69842cf28bad4e7e1d966b11c64100d9d2e2df66357d478db99d35aea74f633d415d97e9a451f97355d51970355826add27ddc71676cc700029fb1af45dd03ebb01533b3e59888fc144249722045a444db4b752bed28c49bac7f4f266e12d6889daffd0398eec625695644c9106d2f493a18d2a67f3bba004431b42159459a7efbb34313e5a46dfa65ad062051dcb737c52788d4198734c9c55b7f4339924815bd1c9ece0984b092529543f67dcd8eaf092e4f4f879e527d0554820030692616a8d773d114b902f1f0bbe1bf0eadc45985fcd5301fd155794014ad3b971756856d80f5b10e756092b133aacb680a6cb9e710", "spend_index": [ 0, 1, 2898176934, 4294967295 ], "result": [ "881e1c24059c25a2f9d1a00857b12ead0f18b45567ac8d897ca6e850312cbb57", "c60857fd242e2c0bdc0e2713799212c734c324db3f60fb0421fc8bebc0f85f00", "f5fcc4667fe355e529975a89847ca44f444c560ea86a17ffa27261821bad405c", "294e2970a8980538352f58c1756958ec21b7f5d1aa0f649dce8a90844c4a71f9" ] }, { "desc": { "Inputs": 6, "Outputs": 3, "Witness": true, "Version": -690026209, "scriptSigs": false }, "hex_tx": "1f09dfd6000106f4d2bf110000000000000000000000000000000000000000000000000000000059ff91d000d80f276e34f125ff0000000000000000000000000000000000000000000000000000000079474ac1006f953bd096e48aeb0000000000000000000000000000000000000000000000000000000017751cf70094245fda2fa003ae00000000000000000000000000000000000000000000000000000000738ccb5200d2e1794cd5eff28a000000000000000000000000000000000000000000000000000000009babf79f0002fa68d546faeecb00000000000000000000000000000000000000000000000000000000309a198600b4bececf030cc7a4427f98762ec86324677caf5e88a73f1d065463b9840abd4c40e262d892c03b8165a07abd15fbc1709cbc97dfe1192bf523d0b1f2a88c5d3d7610588296c6b5f6f8fb0acf213e38d35d5a34e5eea826cf4f82b3dde023f49d42aa306158b41ea7cb698535a52ddb25ee4dafd3a669cc7416d593a34161842e7204fd2575bffcf7d1eac9632236e781f1eb98d66d089ccda65a355248180f88304a086ab3a4350e18b837ae2b1dcf924c19524755d6bc168be991a5b917e0a7a49eddeb73eef59f1a1f833774c4e1f55fbbd942bd23dc1236090f1d064dc8da8df713f7813d467fff506e667cb98535cb0d4a6fdd7a1c83e3cd66550eebac702519f6fb205a60e977a03c90bcb13c5f74467db98814ad9bb7ab2048eaba8f0d568951f2302c1a39233a4a57dbdf4df82d5aba2a9d1c3835f07fe6836bf52da50205a6bbb14e9e81aafd784a87b522ccb385cddb7b9fbae48df6807c6ecec5cd65f47948abe0d51d1c64d1259b592008ba28fe7507fa9261b357ea21987e63b1e4eea4e0ad9c170718d5f128d0fb5ef6a6346a06836657d18d1da5189b1cf8ca816f620d04756843a96f877d875d4dc881bb6098d0e9667905ee31ec964887fae8685dc96458c6ebee1882943fbbf856bd37cd3d30eb7168839d768312153e9f55d7c017c7a5e367a95d0d4a74fb927587faedae6052b635356436120a6e45dd67dd10c9512ef091d3813577e1d5ef1adb031f70559d70405616706f3d3ddbc4450c867437513581b825c7fe4066fd672b4c7ee2e39041f473aff0ee6b9ff342a16c5870336d3ab8c2e11c9867ba47f16d33665fe060b8c6606d7ab7ef5db50d18d4ebe46e6c858ff3ba081d867a3fadad20357c3bd6772204fd7901a51c74c194dfe328d02423cf6a663f69fec9551d59e5ffb32c3645df20062cdfadd3e73f768d49eba33c97d20797ccd80a64510d72224d50cf3511748842e7944c3214a4803c81793f1716e2b997c3bb6ce6eb43636a49d9b520870cb6a63cdad143d841a3e072d61e52889e71ed7a775e5409d1f119ab84a5519976a52d81b392e32cafb10e75ee97138fc9478dee3e27fadf32494ddd7c589fb9074434e13ea90dd3d4aea619897522b7041504992621e76144a813e3ae7bbe28fdbbc5bc2e706a2af7a5b4bba1dd851d6050f97ec6f24f60c05085f366d07d1f66215f05f053606948f87edf84097b0141c834bd736898ecbc4eb1c90e4b2521a75e42a245fc45f13a0405e3efdc3a357f87a3fc27fbe463291a3c83122a302923aeb8f9ed6b17deca8d833a9463d1b9593d5687972c7988ccafac4d816e85ebd61cb2fd34e42e43d36e3ccbfbe11015c39bf4813ca26fbb28d8ff3920add8564836017eb2569ec6564693d8c067a441892beb3444f4bd54ff00c58b6056bba0f38923e844cfe0008cc5fd889fbdb461f738ed15b687c6d2f8f0a4cbb1609b532c645929f77c1d0575ddc49035e3eb15896ba5225831b15e7d8b5fe1eebc6021a8a8d2cb0e6be7b7b5dc2025d85587ffa4d0b77b07e3e7ee38a99f88d0e5a4baf94af8ae908023e35f8234c548b842d4ad8aea5f4646f5f166576b55eff9821b873b8d367db99ac446c7ee40b81f4c7632d514425dcce6af9c78c7b7dfa89346f8508b72ec7d9f05b5ecfe110f8e7130ba7e0beb25a57b619ad20e7013a3d394d2f65caa8325b19877fd52012c5455dccfad0089dd69642626c889cb328c5f567ec4ab433686ffabd87426ce440df053c2dd69b7d1d5b162f6690bbda276454494780bf2fe7691f90eaafee1cfb52e14db9ae3b0980cd44b21c056c8f4b0cd5b9886bdafc59820a735d5478c48a2fcac7bbfb3515011f5c6ed16228315a8fdc90fef8d8d41f9c27eb2e991f5ae1f6b83a8f1070954bd47341fa301d19534c8a11f572bf7c899d581d8457732482ecd72c857c22f5ddd56488de0b43ea4e8bdc1bb32d5677c1fa352d1d02cf1ed853fe37adcb20c8593ee9cdacdc151f8fd0d82322d48787f66935bc980e03495142e1fcb3fc00b3e3985fc335a5c0ad81c397d9f892d0a485e64c74fb93411c3c5f35f6b87ebaf67f54541687590579c0722f2e98cb075a7508fbddec43f1c0473121ff5e4521bb61327d898ef69f5ef42a9157ba1c8d93e145c35c2dac263b74ab8bdb7bee6d4ec23ae8d1ebd5b3b36140456ddcc8881497022a55696bc6db40be3a0c9f57ab97d8141fdf7fe90dcf0df8f5901c4ff25930f73b3a87d55b06b80fd748b01729997f5fca4e1cb8c9be6725451e2d31beb587740441ecd6b64fb757b3ee18d8c822bd4fd81012d7b13446c4dc4b14f76ff2f7b9f336f9d9a7ba464f455b4f615e206347e40dee0b2a99b1f47f819628c8c6b4ab3b8698c1fb3f437a7d5085d61a54e7c1d549c3aa7669adae4fd761ffd0b0e84928ddeb49d7297dd699f7b8a18c58b651f55f5e62c6a29806d8e44b1b328f67dd090a3d0e2964e7968b2fcbbf5d62a51ef6226034bb0cef7f5d57a0a20fd018959d78cd23ca851a6ffe8e911c4b27be42a29cc71f75f99a60c82b4506f1480c4bc85d24eec9605ab4a9fffe104d6df5350a897fc71039fd5a6df6f1b19d0081572caa0ded13b4c7c5028124c3c428e804388c59fdd38148cd17d8fdf8df4c2a4f1734e0286e6bff59b712cd0a5193b822f77043cad8dc3a8f40f4b5249cb8f9e9821dc7073386507a007ac24969ee7090c96192231aa4a7daf525ba3dfab3d11934f736d10e8b7fa5d8adb800a5986ca8ff9adfa7fc2818b32d020e84edb4fad653a3a495a8d875d51d070efa96f961c1f64d23449f4e520a33cded54a518c2f3a691198660d32d3a2d0cfcfe16b7bd4be7a88d9fd5201f60356e1076a25de008376d86b96b0adead85603296be4b4df6b0a61be6c71e9d777d22842ae13ec6f0630254fa68b61c9acf53c6ba8b6ee7d2504e6ce5d4d3dc92f18e647fda4bb72001a4134659d7c16253eb5c50bea0b848bdce5a7bcad890ec279265c74a3b95ef03e77313e12328ed4030f2e44d85c02d76e2b481b04ca4f03ab8f2abea06327ab0e121e49a5f07b105b99c5cfa47e5c54d5ae70c495964dd276b1af264ba04b95f2df45f799c71031554fcff39c741180b9c2f7432c22b779591080ef524dc72de01855d60db3766800b8a99e8267108dfecd8178928d704988049cbe78cdb2dde1516185bc69e46638ba436311f57f7489381e92040657c314ee86a63a93887c81c362a6f7b7d7637d2c88d70b6ed2ab80a97fa548f7443ac64a4241cdfc4b19e50b1261da72a21a7c2a7229acfe8b6796b728aefdf1f866edf007b6fd0e6db52ed1d2e66ac8af20ce41adceb40115faf56eb264b4ad8be82407cd8b580709cfb58a027b92777f7efec9c2fa66ac505399eb17e7d48f0a6659a5b99ebc2dd36e0b920456114b957a3a194951509a668dd42915edca3fbf59bef1e592495a51332fd4e895b3762c24ffadb594f5b4bcb196d7a7717e403911d599afcc1bc26ce664d905ad01290a9570da5c778a709e88fb4c307c407a9e61f4c53a69bc8b68668da5b5d0c32bcfef38e8b0af68e8b98c19c9f339fc454676be0656f1e5154019bf5e7047b7771fa6fe43d39d79643df3dc877f05cc3fda0001bbab3f2f1f6c9fa3295beea8b21c35bd32842e6e8533250547000134f38ed4f8ebf51f296ec746b90dc7fd301869f4d33d1ae655766fe07b548cacb36872396017a420623cfd8c147df07a8fc5161ea0f8f721fec60ba030d35d7fd99becddf43cf3cf064b167d740227cc4ec7a1b5860a174b8a23f6f9d3c754cfe46f069bc69f44a91bc4b3e1d9544f5571449152cf9b5c92bea1b234e7cc870ed476b9b39c002e432b501d18b09f43d120c1c531a5354f5b5d394472d3c2913712012390fda2e78eb4cf26495a17f02c18db6315cb984977c493350fd892a6f551a848c6bf4e002e5c92f9", "spend_index": [ 0, 1, 3965014848, 4294967295 ], "result": [ "f28f0129882d7fbc863ee68a080b6385c32ba80c9807d2c3faa0499c9a8fc3aa", "2bfe4ee98648516da59d4ddaa7f3852467839f09c6119663aacb7c8415031274", "98f7eadda8776f807ee6d2988b94d26dc6b28bdf3bd8d4f15f4874e3d74c7ade", "0de00fe6be6ed7fe240fe437cabecd03a3a6b14cf66b0b4cdc3863e9d81b2436" ] }, { "desc": { "Inputs": 9, "Outputs": 10, "Witness": true, "Version": -330535473, "scriptSigs": true }, "hex_tx": "cf6d4cec0001097627afcb00000000000000000000000000000000000000000000000000000000dd3b4ff0fd8601acc66aadfdbbd1a947a172eff604b62e8c3e8090a0e616ebb1e6ef6d3125f59da24b00eb8680498041eab005eac7cac1d0f8180db579f55ca565c48a2f01b682441db916655c4bf3e941d79d9e028b37034954fd18f5e4eda9c407bc7d92f30e630bd12a59f244b247ba3eb5f415101c1ff3ccb933fa49726f692c7ffaee11dbcbf4173d5fdaeb6859094670f15d249a1d0b521fd3aade0bdf895b3380f950a83f2cffaa114ef0a2bd51670b0b9bc455e3fcfc1f838e784af5cdcee25b367c711b3a00e362757b467b124c6693aa473270d84f7a36dd49e3c285b2fc3e688d4b9fa4edb2d46871117bf6c57d7b510934f2ef03a224419fa78a30ff82e9da00396ceb4584fdec173e22412eb221ff8b9ab3184de295fa5a49a5b3eaab279adde8ffb6702f0cc72e702463fa566e2d27644727dcb1fd796271c494e35b916a62b96a9af7bdfa5f9713f8ccd0523568efffd2a4086b992473b63ad567769c4c76724eaea2044f45cf3ea94fd0e90e7f5e85521601c1442140f84307b86bbef737bf5f3331ea638619a7685ff484179a000000000000000000000000000000000000000000000000000000000873ea8a00b07efc1db4359fef00000000000000000000000000000000000000000000000000000000ebe60da8a8e2db5d53c50b23150975f807b126660c5a1e52ba0916681c0586b6de121953ac1bec5cec423ee5495fac135a1a16ad24f42f62d37b1baa274c078d166c0cb96da40c94ada121292b2ecdcbe61d2cd8bb38f68d86c6ba389d3b2624c56d29211829e2fb435a605cea04b58aacb5525640e7dd9710a78880e6d147745b74a4dd7e6fd333ad05aa65672e9ccc3776c30df7111fd23af7a4dcd4e525785427c2d3b48b95403085e065292536781915c66b2200000000000000000000000000000000000000000000000000000000a1b109d494bf80046c183e6fddfd30f45e9c56116a82655b51ef881e2a6993ef310820cfea7ad3ca3d4b03a0437e586dbf0285ade22228c9bfd0b4a6e09e88a1165801fcaa3bace6d47806d617019005645541af87f84f768ba51374c46b84c118e9b138ae51d3aad4b9bd2b554c438b246e3b4b25e831e1718fc82960e116278b2bac8294aa3adbff8cf6d012777671c8852a2efa06dd2de4829b4fabddca2d8c000000000000000000000000000000000000000000000000000000007a4ae42000ccc9335f2bc7ad3200000000000000000000000000000000000000000000000000000000f67aecc1fd1301f2dff220ee90be9a059583b33badbe3678cc01cbc436ad3fb515e3b052171fa463e036f1c6e31eef7d777c182a501211acc92f6ed87bc7f1f049ea062cef28c443709f5c3db6dd35b0a6d9e19bc7e2d5e4dfa5ba5653ac6b3acffcad4c83e0c02cb5cbe31def8cbc1c47c833862edb7fc5236510d537ebd2ca239a2646026400a6a66b6b9f2666f1f431591873b4cf8bada2897dc589655b38402c358d6df8ee17a0375f78a5372b52c7d06705240628ee488149f1972f8fdd8fc58a15fd1929199eb032915cd464f6b29b51bda2696f3149fa46defc89f148383b21887b299d713f0bf1cac85126eaa2ae61d4cac70644564768b6c42ed3762d7b9f1f286e3e9bf41e5fb0d14d99e0bf0b18cf8b6869975d32eb90f137c28db4240000000000000000000000000000000000000000000000000000000027556429ea5e83f8e8fdab01afd8f10ee8fa20fcb75eb2fa1c813f915bcc68d2e167ffc2ecd7cddc2de40a3ded68e6c617ec37efed4cbe046488f1f80ef7891c6de643f80f74b2fa33e686c0a7989225076796a2a281c2ed87919f43608678235c10d7da626f4e4868b7699eb15f4c8e82f9563cb93f3682b1074ab2e1ffb357cb7b10f8d90baaf786acd8c7694e07f54765ecc537e1b8f5d69f089a944c16d019932d1c151b3892b18f8508d3defe64c9d570e48fb2ab39fcd5f8ee8f10dc1698da04d3529e92f4f50a459be8831db847f6db2bdfbd930224f369a764c1d7b9fd3bad5286520def02649194a80555dfb0ae56b5027eee0000000000000000000000000000000000000000000000000000000057b75a7500126ed03c1729c2dc000000000000000000000000000000000000000000000000000000001790f11893056b98dd75c8abeeb70077e143802fac1050777c07b01165d762cebe0642f8eb8e80ac983d09ecfec1c1194e58edb173a72bd76b42d5f94473c1e3ed2cd0bd6b8fb18ded173e2098834a4906a4c4495db06d27606ac5632882dfe2474424bafd0d9b2a869f881ddae605129ccd745648ee5864a987eadd2d172a4ddb550c47d5d077dee35b30f8a0391927f4d6180de7ca447db20c4e7f0ae9d6df64dc741700c8d2bdacf6fb47879544b5577409d0872419d429ce9e101f900ac52bdfdf80f5c4a479232936e8135a78f61ed539d1235899b982b550e3ae1cec8e23f68e99ec2e8f3daab0c872b1e3e5eaaa153b653e833ef145549f2edcda348908b69d50e19b2486fa33c4b8bcaad350242b52083f0c065925c81dfe718dae232504c0a23a3d38d71ac9b909985c612779f67db6b4b53846c925ddb151b72ce4574fbb516f5d82710118a7d8898b9ccf8f7c955e05310b2d92dca1f9793f7c8ff51e7612d37651bd8ccbfb143030c6874e13c96fcf49c8ebdab66f39ac73b51fd99a996653e9d0042aad8089141704787077869cedce34aedd537e2824a081d616e8f2cf4cc9d367fee8297313d1cb986015f1ec7b66b3b7660ac2e530edc1b1434f08a444984e2dcffa20fcca5b92f7c06b094efdf00e77605e73430079d770b4eddb5a826213de714844edb92336bd07c040ad40c09144415d3e36aa7365888d98f4751771cc5adc3e51de8f595e72389c5d0a16e75a932f217642c2f3373a799643f6bc7aa9ffd533d422806d8d9d88dfae56d8c719ec936456080aed951e9535984d3df654c815d7691c3c00131fc40a8c31f1a0df09a5785a2fbbdb33938a77d0a55a97f237a0b97b92842816a4e3c508619195fd0fd5b5f4b698980e06efaf728ab6c9390b523d5299c3c82c9319f8a09e8da63776a1be938946e00258514b8ea81de4c8adfea509f96554ddba9bbe9ab4d1053a72c32e37ddaa3441b826b3d23fd2c7a1a0a2640ae0a63b4e42d64128bcb441eba69ed308b34ca675e6f11efbda407d06056852f51a393a20e2eedb4775d3b311e893e6fe2995c8e600bd7df3306ed84f4ad943a6c633bb04fdb1ea059a00b1066ac8ce2105c4a05ece4edcb02101d5e2c59dd3d834cafa28554c9f2073d5e345f979dc5cb5e2c17021a654af09d50083d4989ca24609e6f84f44f056a3f2ce6af7674b7614c116aea78fa761b67067c60f612e9da7e671c1ca045eb45211da68052f2c95b020d30f19d1b59223f193f0c3f2e415fcffc7babae3bb34d66b0a281a86e2369f1e86f428d20f7edf2ebbc2c72372df6955c06c8e1e4aa52913c35dd934e82b031a9c081b6567091d82aeba56092478a9a87edc367d0dc3901db866df374605ecfd925885df426d66891df6c36ec8c3c946f69ba08811c4437f200861e0d26a8bc8608812faaf86d520840e0eaca173bf78b2a3e457de9dbab31e50dec191f8c55f8e3cb71369114dcd306b5593da5ea7527756e15ceef076aca4d0268fddaecdc7903a13e53755ae2e069f5d3b17424ce58c52e9fa155a0c5cb88201cc9263237730c9148cd826f3b7e0ccc3346b58a3bcd5528f9990b9bbb2279d45b4f33ebcf8784c5b17461aeb16be121f9a1f23786744c15d5cb1101dc0984f6b3df7db65c8d2543816117f91d8f3aeb5d47f9d060ce097d00fe6487232e33a021e6fc8759bad93e2a4d2370cad829dfbfdf53052776414e69e142ca6ca23848d4bdac7d7d73ebee9ab375bf4042869db5ff36537cb8c559ddfccd127d82a5051b45293374ca749234b4bf2ffd3a33d13a0c0e18f19400943cde7aaecb18def3cb269b7e000fe32c4119cf18e2d6963d9e8989b315d9423f0ab169516eb0e4d63a2e5b872ca14b7fbc39a8b9b4735e30fea05b17c145f99a52e1d5fbb4aaeb862cebeafa33cfce235cf8157fefebf00b7f0220456a909523da21f0e331eafaf24c9819267409754ebbd927bc933efbdc728d142c802fcf847df3780db979875378c83385d7c4e881976ccf2dd9eeda3338296fb28cb8213d716b6a440823dc689a42d8ad8ced64b4287c1fc4042e9459f77a4ff1c44a5b353557eda5ef422ec32b1106f1588a2cfcb936e55616525570930c0f9e308ecd4159bae020cdbe2c53d5520fc62242211971dd5a43788189db3110ab48c5f98a7aa51f5ad6cf8c842f67e1fcf8583b71f31af56387625784a50a38a1b248a3aa57f4cae0c0c8d2c0c93e0ee4c72926e96f4b6141b055aba8895671fe981f6c96f102f0a67390cfb0d303e83da47c87de11e7102d6eb52bd710f59b258dff8d79a7ec187ba70ca8d1af7a3a127350ccdddec6d42d6bb8bba9b5ac65049277edc126c02f928be0637353be04c1f8154b4cf6985092e9d511f205e43be2bbf0141460f389e65d7a2fdcb3b335bcfdc72142b8f4d695ff83be7a50f8c66830a93072db4cc4006313509d6db394cac45f131ddd3e8e1b810f7a86e90ed25156dc653445d5e698517754e4b9dff7954f09461401c20090bfdd08698a067e959eaa8270589ba8243b999f1788de6465d6a85a542aa8b24f950fdbc8e972503074f3ec82798d6bda5a61ee0e3d512d0cf06fd7a8c9cfba818df97bf2fdfdd0c13616e2d04fde64f0d599921baa5113bef041cad95f4b6211548b9ad834dbdf91e258bea7a64484b7cf3a38358cf30b75e5f19fd17aa2b08cf200f249357f2e8874b39edd0800f67d68387e8b39926785a40a74f8133ea42e8577b0acc1171136e56c7be0bd147be8c236c3541cef4b32a5073485b5844adf7ad41472a1712009bd295d4da656af34b59f31099b22964e9014e6971752f74e652b795b1875a9e2ee0f7ab3f4276d4a3e1b183fbaad482ecf6103ac874248862cde6960fb8a11f7e69454e74ab8de6a1f11cde5e65326067fc3011ed9da1232df5e0fab0d5a542b696b20ef364500ad79f6b554a77dacd738355554bbb9f39a9ab1c2e7aae26b1109350db947f6194a0515578869a4294f3e57fca14e3e1446ee2b120cd0c3d2e58a8df857fac16de57c17ef040f19e1e1b5064d10b0ada94940e8f607a15636b58e9b3e1c102e8975ec0d9df8c0ecfdb53f96956e21d78dbd507eaecde047ad065b3f24a7b91e64b9f175d5aa5ab3d5a6dbd192610982e377872af8a1302fd9701b6fe5fcd0fd80ba1dbfba614381ad6fe46851470ca688db52a9bec295848dc823d3ae6669809bf642f1e9718bed5d338f358ea556bc39f3fb3f2c13e175f883d30a77b6b3070b4dcf2a90b3c7748c594c820ead607a4028bda4e75fb9aa1000097492bcdf5d895908a90f7b86168ada4ea94668a5ffd72728d81a11badd5f2db96c06fa042d7cbdbabeaa83d1a95cd0d29b8c39918afc939a7f90f924d36d0ee823d31fd7541f82071a20115b8dae1918b5ac923f3205e97e35f01419d152c8ed004d48d638f602248d1c2b36acde460386173ed9aa7b6eb6a123f5ad362a10b82433724699302041add3997ace66d9df208880bef12ff706782f3b0308327a8fa29fd373c141b84b4c35290ac4397170186cd95882b717fca60b68b8c678d31f59b0002c9b57932fde5dce6e97b9967753bc0fe7534b4c0ee79ebd44003bb9a332c9854b4f1e041a30693111d74ecd62a3dcd311a1e972fcdda7e8591ea626aff739e0b681e813dbcf5891dd1e2a72feda409f71c1e151297618a3ed8cfc51f615e2807de037aef841c6bfc46a1b91a933ffe85a59e44912334d8ea6f4c569b6be0641de5edfbad3a64b355f3b92f060e2c340f74f2de00f6bfc08c1a92fc51a1bc999a6cdb867e7f04fb848607e6d95dc5a02353ba856321b413b6d1eac3e808f19fa52552eb6d481d54e3d14edca29c506591ea82347cdb9956abb01db8c033dd38d23ae7b9bf48fd38488682868bb47dbf34fbd9de7457bd15b61caa0fc55d88e49f5c542df58b01fd92016cf5afcf22685e402d27347a809b3230ccfaa73b2388911034537f18fda34c8b42f931e00ccb6867af0891cb34c3d4dc894ce66781f35f7fcdad63e9d62a6c0db6a6ed37c96c09e7319bd128842a559d70d51bb7b277d0ba2636bde0a9542151511054a59e844b275d25e3cb3fa49d78e5251d8ba9bd8041cf7f726f0be3c54aec311a7c34a94e29a3c8c7b87b0b4ef6807c423a8cf70825ab3f098084239fc44ce457d3c67ccde24861e46d22754819371106cd1a9ccdf84d6641e96f3ac400209bb61302d479f055e42c384f7a6be8468e04ecd1a785fa1dd2eb250a9d7a47af39cac8e685b40a46564bfb5454190bb6d5ab6e9cf6e1317b7dd4288618f1635994a47091956cb7e1894bc3a3cd7addcd8e524ed8dbd1deb9f6c78e1f3bc1988fb7cedcfe3e25554a4ece943bd54279dc5647ca3448b57c1ec729b5f620ac557a48042e3ef811947b210377b6e0cf5d55db80458886c627d3a078e954f0797d48d58ec07515f617f8514a2ce87a5fa25826227889bb27e854011c4dcd2affe59c03971c33b95006d27dca609070ccfd630b04fd2301bba78e360591b8e6e27c9ae167697212c1166160664b20b0799708d1b93c02af323f46852e72158e205587367c103a861ba5c9ffc4eee63cb43def8c3e38cd70ea759a5e67c7ead31a412b2cd5e50e49621228acb4b88cf46ceda11df8b90ca79f5fe2a373f884a8d742be4c0cf0e125499a252ceb6279cffa84c4c184a7097f548fe094a5268aa8bfb7b625dc41e9d2dc2f0b7bdb27712e6e7cebeb2a5e1686f512c807a14bedd253610bd520a38b38837752c3acf9f39e5e1671b099f2170bdc38dec2aa556b701be61b7945b783b44c3c355a87b5ae3dd9ef1f07e077335a7acc7dbf0f03f9dd664c881db172fc237e8c603ca6b5650be236dd3371f866abefde781dcfcd87ed58178ecbfda0ebb37ee015b01e7635152222f23fbe961401a1b6a2fd6501aacd7037576a0d88fb19a9a0265a19ed9c5e1d4e4e722f393b5c1a0c326ea7e3c41e0b4070c59ad1bac3086b83ee661b16ace313348493e09c6d36d6e056b74c37492893b0b0783dca75292596644b0351d95fd870c89cdd6f7c6df57f82f149e321517664354974be9fbe8a7f4a6752eb8f68ba846b6956b8acac038e69cab8a65a015911c1a216bf00d41b75505942c76b4ab03863237054bd0d57ea90ef2f3d1525f2487101677af9093831e0d1bb239cd73ebf835c37bcb19cc39e20b6fc93fc03f2ed1621b41fb36af3fbf071fab21124fe86f1be673548220ce0691f322dbf27125867f7d424e878a427c15898800d18976214059fe37638192cb3deaab52a2514027cab2c0e9ec2a08b92f00418a2640d8ff7d9681d68aef4051a58b2539b4641a0464316651231b5549595372cb0323e81e180368a1506e0cc9ccb901091f27c8aacb3c05a9eac8bc767db41b68431ce1e357238b40a62a68fc9652cc13a56688cfdda0198b1900d19f27d8604cdaa8e0197e9fb9faa949557d9bdca35e97412acd25d13c23a6ab4d5d2e98e1381e499d0f429d8eb53abf92fb94bf7a057c1d4c55c10370098b20ba6b2197078d3919c2e1c638f6ce98ea9b9e7bf55e5ff5e36cb6148eab6575e11f0ef0ea9014fed6db4c47f9e67f203a3c404d3b24d4ff7f08468734b58ee663016bbe7bc2bb97ccc5f664fae40051b68b459998ff4541dadda2d18051dae13ab498e8f807ba2448b2683c653a7876f5c17ce65c91e0062ff6c316c8ac0b22f48d884b1d8d89f43be0fcb394c01139fdc5d6784fa05d7a382d053aa1bfd0ab451de16d3f3c01e1a555047a7629ec4529879a6002385e48157b1f315d4718c7f557067ff4912b1a1b6846833211377caead54180ebd1feb05e00845fca50ed10c50d18637c4997eb205c11f9352d74322ffbb0ab34d00d664e7e2d5eba513c93ecfc9a17adff0093a0c7aa1555ee5b4a6fedbeea988b7e109a2ebeaa5726600f3d3679f0786ca9752490dd94081eb9172a8a4d6f54928e4137e02976565e4f57c4c137e117c8b19d1d7f9482630d676227f9403d1a1fdd525f3a3a4bb41271bf0bc8400061ec7ea3a9be19c8da28298a460f44d2139976606324b743e7cb21ac25cb9cf4fac8d9ad8240a96b8a04e542fc6b188c2954e96fddba1a03422eb8c1c9ead858eaffe47354441d14be919146472aeb160236054a9b1874f7bdcbc2f5f3c9142de5d2ce0af9a90226f481a3147c787179ec1c8e45c283bfdfab4ade49817c04d28233bd2b657fbd63d35acbf9233d91c316dbbc3fec2a86417d5002b96479aa7be6a93c02f088f1f2ac9e10b21bf117f69a342dbe7b1d81e70900cdaaeb1e98998b793cfd08a6e68d9cb7d94b777d6465df704bd95e88569a50a036f593368ad3110840ea30e9da9fcae0be665aea09ff5f996e8dd009f3137808240b533183148c042b1b975ab143177759be8401edf4df446311be64aa933a974f80563a768e3fa7b9ca25dcfd9236b21e623634fda73ad79ee0d9daff1e0da58e844296df730b368bb1953d9567fdbcefa743bf5af9a840760224f22b174c34bfa8fd7566d362d7cb41ab19ec6db5514a647d35059402cdcdc2aec31cf4cfa82f494ddb2c82bd26a0059b7e8e0749f9e56165189fee8516e2c45e74c2c234d1098bde49cadd80abfb69ffeb46e7760c3f3d8294c45cb2939d435457e39aad3335f1277e640d4e594c70e4aa1419cf9dbf1ad818e900d9620ad79116a52740e9b3c150509f797e59008279a28e92ee9068009a70d93c108d19969fc8493fe461fc636f0a6294e671a6bd7792d4a3f31304fd2e015b6a8ac5f9b350ba66c110d09793f5586d8c14fc3988ad744b0a7d7a11378d26b03b14a5125685cf754c3046a4f8bd5801fc397f8865a2f075898c2d8d7b5261a17b1f2612ab315cf04d3e70ae45611eb90f54d30fd4e5df77d6a23bbe173c01d832d248de4e435181c1303b6deaf7cb7edb84ba1fc5d8e12bf204827559ddf22c63d4d345344725aa1c9d1f58c4e39efbc2c21f7fbff8d25b15f1e415e72b2ead357c79bb27ffd99a0803945285b58dba10c428162ec0a6fa8d39f77bafcf212a2fe3a4e117f87d670d6a1c9665aab94dc91bdc6d5450a7997dd968bd3783e8d290392aa9c64a66ba1fcbdd9031b8bcb80b2c815aeb8706fcf05e6aafa49142e8fe584e7ea14621318fe341d5523c4f5eb96453a7d0d390e2eb7879cbca73316443f1fe3c75ce92108b230794e30f42388e0b35a41fa064dc655ecc5fd0f1becddc109345e0f8e923fa1b57763dcf79c89047e326ada66ed63a94d4e24bb8a8f0040561e80740f608656e75c15d06facf6e348bfb3a16c618a8dbdbe09e46209e4921d2f17d6adffbe04601f387744dbce24bbdd4fc997e750fad11c16fec7aec3d8f22d4e2249bd0d2a1ccf0eda0dba7e3f1e1504d76ff4d661aee8b7b1062f9872f2616427385a49fc06168284900fa1c00b21e76d6d14571d8ef85bec6f417893c4fb135a38cf1d6d57f22d61486afd92af96b68bec690230b995aa18977a11cce699fad3ac29a0b1794e73a8066d71cf7fd7218ee9cc9f9e3727517523ea5a1e07c295600408ea190bc4bb45da9d50bcc55c4512f3990ab9ee975485207ec54885f28eec2566e28af790cbdc375cbd105de246305ff0ed36277f928d9e421add9d1b8b897729fc0c2adcfe592d16aed21d99659b67fd17540f3b28e3b83cfea71a8a4d5acbf25b369a8f709d51ee1af3978907879b478b54cf37533bb43c77283ec4572baeabcba5a27fac46764786dc1d2b87d9d9e6904e6f82074dfcd1e0ca8a12762506172a90c2372c816252b1f9e5e6a2d7230b02d940083da713a33b179b0225f928e34e57100c77cb8b0d1f0fb4aa3ae19110e25c8c5d714c90202323b4fa950036fdbb6f35ebca5cce4a546e2864a37537fcd5523d8dbf8e3d35ffae12391f71fef2f5833d20e6fb7e313d4c782d7112221a875231cd54b163c6fe8f191aaf2cc7af4aa2d4c9d233ef9115c23f56e6ad7599bd827fb2d879326eddc235505f90a18cd3b6ef684fd3989f7340a56535b56fdd4013ff579f6cc1d568b4d52de4164d7ada29b0cef596e02b3186988580cd936e2d18242022c825e195b81c25958b2de0880d897572d864fa17feaa1545ec0c125fa472d2b118d1591f480a8bf82a653734188427d03cb86143d18ce6305e0476a2d8748aba80c48d9b9b0cd9242ab58c53d702dfc447c6b17346d9035479ef70a10f8f5e0089a9d4bd687c8a74f0bb71499f0637d44913f461b18f7560c2888ecfde3899b47920c428f81c788ddcd0fe2b029dc2e31565c92c21c2ff254a7fe9969ebf66a97981dcd2f91694278f298520e8ad070a45d845b34148f9140d72246ef0f9a88ac4ae501d6a713ac6a600f1585823b2bf389b3fb63788ae8fae1ad486c530cdf32714c8d24cffb019bbcbe055c95fdeb2488e35552dd66ad14d0dfd7f2aef2c0e4893f0508b6b3d23f828bb4592bbe99ce12f23cc00a025064f361c7272eb2ea5c38a8036c34f22b6cca443aef1bdcfc829906dba7acdbbe3b2b7ed996f1bb33c845239052fe8c8a13527dbe53f47b9f6c330629c33a217952bea341195b91d6dc54e5af843c735defce0371b7c51692c5c23d180336a9f4fa025a3280707d1b0517a2cc46fe91f87ff18ce80529d24bce9cc8360933772a4f58a7a50c0206874ee44484ed37002ddb8aec3a9c1ada3171fd410132493ba7b1afef487bebf0919aea3f563936532938a239649d0e6b804de475a150678ec2894970b8cdb0816a4b2e159e4ef0badfc7f7f3a632cbd040f5da4b541b0f2cb29cc481ed7275cf5f4b779c85a9f4bde812bfd00359c4432612824d7b6712196764d3f563de3849dec3c8db0c5c2a4a233a1191b0eb4d3b60ecf51d3d4640aab4ac83a25ae7a3785530d7c6b81d1e61fab8edb47f6afd9ec80e6d76a5fcbbc17e01cbc000f2f36eb2e3f74f2bdf06980f0c64e27fe73b42416de02c60bb81ee40a7bce033f75c7b7a7cedb35869075bfefd60eaba4e5447d69e4800dab388989cc027e4380c7ea2fd50d7fb4039a495ee1d40e94ff76402972b0c57a8f848e7ef42943998da34e682b1037a5d4f5ceec82c3226c1d0538cce2b9bb73cfb78ab7f8499d7540a63f9b07e0df3a253fd55d5f4306e1f81ba697abcc76cd95603fd3401319dbde87be7fe0f760cc92c08f155ae0a068f04193c1e7f98846a2e256f087c8ba5a9c8189908d10bd30606e5f685e92a8eee8eafd622f1e146d93044eef53395b1d3368a87b4a6b27b11f21cdfaf75cdeeda684f0ec7bb91e04472b19bec99174e6f996435293631ed0770dc9cec222f089811da05e4948dec445eeb508596caec3f3ce738083a2041cb976ff6b5100286587994ccbe31edb0fba5acd1b2a69d4eb96062a2f4a4b668d5f3b5a71a7586ea8296facee1b5b4a1d9f592f0f161f1588a05057e35467bc2628e18fcd927e152ed89d84b33e9ef68bf9270f4f593ae646ae660806c27d00beb048e5dcab3e999dcc5dd314069089a26a5dfe5416c588970433b10771b114f27d6e1b7cb57a00cb67f2ea96540bc68067b9038e4ecb1e5052e2b5903b6a88506960526c71684640ac3d64a0df67e9154d4161dd90eff4a55e95aab70809566b1d9e9905e80d96414ff7413b72a0eb202ea5c1879eb7642919ac939cbaa254847f4d281109acb220fd2e88a52dc76f6b6fa5cf3efd719a47b5195c1be675f38da77bde91340994588259591aa20554c83ca7e37e54c38bba16ded6b31172c160a49e2a6a26ba7b5ff677259b0e96b68c6bde24c1abdcda73a1b816175d6c95e818862fa95fed7dd29f84bb08e97a4649fbfd3764f37344c7ea8bc2a2567feb3cac0751ee3e6a1453fcf97705db7461a5494d244c8d52d295026371910fff45969fd430156f589ac8bb42be8ae75382bc6077b40a5fdc5eb527be66a2acadc29af6694f94d2abfc7bd6105d1ba4134eaa69a98e27b4969c5d6606d1aa4829d7994f6fc3d2f036bdd39bcf1c6089f2748b4420cde9529369d760a86ddeb26163b5e6ce06bf33fa7b82e18a80086d0ef8b54fb352628609b60906bafb2ce0a6be053ffcbda67a546733d99b441c61f21f81291021890e62c89b10e005e58dba73a05b7a78df4978513fe601d89a9ee643f01fb89bafec91e5ad17bcfe72acc3b7bd859cd147d0a8e33ec7ffb00e27c64a4d274feb9a4ba79c17f7543b6a216f1e1b5ca009af538aeaa019ba81a1fbe311afcff9f4f9f182cab2dd18eb7deb27fa08caa9b0b23e4a7d8ca66bfb422eb8846269c6dcc57ec8e6ad32a273f2befa0e91b635d1c66e9b1e00aaf33a16122d4ad0fa1514980f6ec1ec0b7858d389d6c67a15789eac530bf01826d18e0ab706b453da60fe055c9ba5c1df31f3b9e857f3b29613ad75a67c9cc34086b6d7cd58034534940e91026a8cf93d47ce82163feaff45674768f7e755b8743baf4019612c1958328fe9bc0915cc64138668b302b5d118c865ab48ae12a58be525c9d49a4612c376118d7f27e215df8dbd4ee6181182904d6e92330b61aae1ef10045ad689a", "spend_index": [ 0, 1, 2540305684, 4294967295 ], "result": [ "1bdf87717a32269847b30dca87757d9125ae7a4a7ba54bdb5094bcd3ae8c1942", "8fa39fbc122b1e2d03f52b209358ccba778a27d2466ab4b7ded97e042c2d718e", "a985ae74fc1d0b42b8f04c1d1a49e2af5cb2dce04e1a9dd1063110874de5f091", "60c6438d4af02c56e3767618189fd4996076ad5951120197639c72d34f5e7684" ] }, { "desc": { "Inputs": 2, "Outputs": 4, "Witness": true, "Version": 715592854, "scriptSigs": false }, "hex_tx": "9614a72a00010244487a8400000000000000000000000000000000000000000000000000000000cd90855900c27120ff4dc0679500000000000000000000000000000000000000000000000000000000addd625c0073cb3bbb047a8578e8670b050dc8e81238df3cbc31c53a872208d5e486c4c6f0c8e42c6bb480593f9fa346500640a95a38ee4ec7038b016778eb46a445eba8fc434859693bd099612e91d72d0a8da21ece89d9a0956491083f2daac8945aac13618c531f63acf3f423ace99b996e936bb91f6f532ce34aef686ed4561a101829d37a318f399e8927b3ddd93835f1b2f4509ad45c07aa2618d0bd4918d77f9d84da4df681ecbb96419fc27ea8dafd1f2657f039d6bce777bb7027679fa6897fd8a3d0410d7a71ac5e914b8dbae0246db86c6a03d9b3d0eb8dce9c3f3e7831c8bcd08cbe5e3fd00991116e8f98776590e257dca41919059ae37ac66e3d84d9cd38cb8f0e9b4f76dd01d3d18f0b8a8515163edd7f2ddb6a8dd67dec94f2cbe24c430fba044f7f938f9a3c6c8ff3f80692ab19cef56cdfaa5ad05637b3125d23177ca41495fd82c673ef78c0930fe7d349f513a4a21a3f2f0d9379a9df0e87bf7e9f1e1d0f04f18a735da44baaff3f46e798fbfc107393be22a7fa6f4115fb22d861ab986391c9fd2a9afa441c8db8a0fdb5bc6192cf2c0ba30e3a3f0ce9aa8df89b9afba0d8671363690a93f4927ff73ac81fc0c754a05e6cc5aefd1e9a6bf163d5359460e4ef58ce9168a65576d42e71b677b44da0c72c5eb6ca33a0e363200bda6935fa89e898b9fbe26308cb5227409afe818c3c17403834fca308fb4375db0bed101aab9344203a01629f7deabbf91d91dc6be20e23bf9c09a8a9996935f76ff3322675f7b8cca0bdb46801f8a9dac35718b91ba7338b78cb25f696dd0b61316f8141c94b5a4c78e2ecad292de849c8b9fed939bf509536d01245079fa9516e18189b213343a8f671ed293f2f68bbad654baeb1847215aabe8b0148dfb58905c8d8a0ebb5d60cf68a86e9e3c0c10f4b793d0cf0b2d572fc6b6e07b5561da1c08f42dd827119ed706efc184c781d5938c810c479960213111190b658e78cb2488bc6daf83c3d344ea9aa34d2aadc0729b133869a1ea92de26275993ca80eec33227fa56c19b0fefc7813c0abb06611fd75038d890b41337ff607cccfe5211006eb8e8a218270ae41b46891b46489e58aad8ce43fc7e0b1d99aefbb618c678e74a547d85f461db91b3c3a9dd35627cc247099d7bcb26c0604ca8a6a893dae31171c026e8287f96938fc03fd240130046afdac26ea6e14b194ec5d55c92aca669ad09a3140e600351a34bc8cb92e8267e4f416ac60181f1c3f718d225cc9034d2bddd624823fd5a320772f7201009c0f2f9c545284a9acc22edb78e932e61d4aa09ce09ddd582cbefad60ea3e9e20953549c6ae564df1b6ad4cd2c367f4783dcf7da99d47c895dcaf7a6b77f2b3452f03ac054108c38f9e4cd4c6acd9751029fef96c1592c04016a0a58a9f5d9c2490a1ba9286ef3273c61bda674eab31d6a974e7e7ba02dc3ca62e524e4a89a96f08fa5708461a36c7674588de9dee7c1540a2c287bd5a566cd20b5ff6ff7e3581a5cb326479260c2297d5f8247d0222be1f7c09a58cbc1437e0f91ea3a180b1948ccb0f1de29ad2874f56aaaaab4906166b741494dcda49b16171ba4ff99fb84c41dfdbebaddc69ac0f231f31080af8f04887e59734ec191eac3f1c1a25916b354b9a75ac31d0a63e58c5910f47510821dae0f70e1c1c2dbdb67a14ae08d6efc6a5711c0c6c86355b4ef4048bae9c9f6c3cd5a79d4517ef7ab8c48cee838c6f360628d49d52b9cceb8cd7f0f557f899df6cea8b66cae6856c4fff1e49c50ff9fddad83b3b681c674959cb4959141a3877ff02903aa497ef25cbc936b36c8b3786ac05d71a391b03c8636f82c0d5931b612b75ccc140ec056a3f6028d439db9fd0301ace9b8223e7ca7e00ca9ea447d88a8d6500f302c40e4b13b803d1708271d78adac2b162a30a26f4f0df593f3ea03995efecabd345989970d2defb0a21092a6697d32057e0efd8de0d8599cde438524067b6aaca75e1afdbb1ac04511ced0bbfd4d93847175232ff965bcffc5a07f31457ca97c042c28b7334b7c4033c7a84d0edc792e7cce129c38cdfa0eb9cddafc42a4efbfb16d5f85f2cf3b1244aebf1d89bdf9c018563ab75ed1af53d6260297890daf6c6b7a64190aba1e4ad79819cd241bf5abd87cc989cebb359b41fcf0ce3edf10e2f314aba31565635fc329a8864acaa63be50e7eb76fac299ffed9984dda7b4e55687871d964cc3d311eea262decd1e98e01beca3d7733f03a90e6b04ed560536dc3cb9291b0217597b031510bbc65e5bb3f0eeb12bf7760d7630d75cf8a39dbc7134be2bdb44f2b204576a03d91ee5904a4e548e39345deb04a13859fdf1f3c09b978a4dc2d58e9f461949d16c601b9b8103a5a0b0683dc95d42257e74d28a73de246a7a5cee4103022be8f08141a775672065b73a8403d809d82d9da4d89f67b38e5ab1f692b251b72c5cc19db96ec651183aa5d55fd763119b74a1cebd2c2e698ff797655c176c382c9b3c3c235ced06b696a6e", "spend_index": [ 0, 1, 1848110724, 4294967295 ], "result": [ "12bf734b91f86f14dd3cc42faee9f9f95327d56c5976989d46144b56d6bbfbee", "68621c4da6ba0611a1100bbf14a0881e2486b668bb51f137a6a7deacd85461f6", "b9103641610e7fc11a6a2d6c7bf378bdf4a992fb00933a409c03a8f6fe2c39bf", "6077b14cf061a280c1622f21605f815ad2c68c82d00adf4be7076ae4231f9979" ] }, { "desc": { "Inputs": 3, "Outputs": 4, "Witness": true, "Version": -594424904, "scriptSigs": true }, "hex_tx": "b8cb91dc000103733a19e4000000000000000000000000000000000000000000000000000000007a4632f6fdcd0148c8d6c4a16389b5a5ca57d5dd3c1ef98adcfc4621f779a4efd7264b5507c6dcb3c74e752fefdd47b7d1caa92a5ca64724df3fecc1d2785e4a76ed3557532e4571eded0a2385f0a72d5f37f0b1f1a5520b7def869940e1e37bdd5b1b4f710a777fdbb1524335da1cc62ab9df1c3eb313d3d1b56b54e833fa4d89b4cb54066e0c9ea64a8fdcbad8758550500256f383d973adfa2a1b39452bd218f16f18f52248b31b23af5b573f40e41e8d2333f9d5cf2a7af2bca541ee8cf3ca940f7d578b33fd13e8b885dac1d10479dcb9907bf667ac32361148ba268668da91b04a10974fee0a7119262062cbeb3f0de101336b71268c9b20c034f57da61a64d21afd3e8cd9193fe4b16b245c4b46b5e90a77b17416d5227383e19dfa72fe06ea6cb09ce283c07330374bce788e33aef9f19d9185f52e5132cff5220b58838deb8a7c7185d6a2218de5995656cbd1ee2de93c035b339f9d8bf548262a01a157d6bca8809cdfa3c97cacf843486a99a7f280257f2f32846504458faccedc511e144f123ccc9adc1e9f3b34390096c20ca467cae4b30baac6796184a9c933184dc6793d9b2b80aba55d56a8ea786aa081b6b867e7b236207cb01e773bdb2c764549fc955cfaf98d1935bfbdbfaf9bb1c34e3738812bf5f2ac4fa3000000000000000000000000000000000000000000000000000000009404b6f800f4e4f52c163d1e4200000000000000000000000000000000000000000000000000000000aa49db60fd2c011902bd5a2d7327eb901214d39999b3b939b182ed7d9fda9ac45661cea326c1f9b5753da512a87f5170970d375af04284fb973f11b32219935f25d30bde60f32ba7a796e9d699327135b718426be60e23ba076dc7fcf93215cd0703d8ac8c4370f87d09fe19c508a2cbad345b405325d6cc1bff5a9e922f683c888edec5e329b970713c1a5a31c9f2788e6de872da38893e99f5a3fab0f45d565ca28ac675a2ade933651cf73358319977995ad840abe4deb94bc99e11541543e908481f72b05f04f9dba08378d22ac97333b431ac90502ba7bb954f5809f85b5fc48efe3268c60d964caf9f7ba726c89fd3654fdbe1abd99ebc0f4f702e30b01056377a114fdb25be013e214d6964a5517b3c173b4e92ce28fd17094450993f53a9d66952e06bdcda1ad36ed9c92cde68183e06c22cd804f3b509f1c7c4ca07c8379fc44ba9d006767866231e4cddd1027fe527f14d60674a861a21f28ceb777d5c9ccf49954860b054bb1327b2681f6fbd057b3ded7b468f911a440428c5d9b290fab62f9b59273e01d7f898e7a7c00b689a4d0be67d59abd17d8e7082c6e66bdca13850fe754b60854eefc36981e45a1a3b6d690006fefcf9fd2521c6737bbfe4ddb8757a804b38110f6863430d3572f434eab01b5f60a692b9da0ff212e63655b41232403d6e4b85367b634c68f5e07b975ab3280c3113a03fa2e8d50c0fe015b1380e8887157cd539e16dc10a5e4dc82209755d5f1408169e4e8bcfaf4b6e3db0a25c4cea61f10ffa82d92d439599e3e594d2511ef4f753a0ecfc2f3e34661d295c73e6507753ba7c7f7dd3d7013bd26e53c71a5441fb85620eebc34b0142ebe4d7bf4aaefa69b3a1efe51e4eb1a72d3b4f58a59b769c5c8882e2774cba2011fbc7326d0dc542b260d5273454c137a2f73f5feebbec4e59a13d97c34edb44d3a4027e8781327af40cd4d36ac83057f0a4b65e89e4c0dda809335341dfab0287f40996bfd5cdcee0a23491d766836c1f9cc9ee5799a9dedc12ce1634a98e2339c8f6346e806db1df93013c11e1c2a3429cbb6a07d0198937853b0003926a6929371c0bda000bafc3b409d23f13dc2b335e3152639c182a65a8f5c5139f5951f958cf4954269c984302ca5ba5f74c939695fdf8351bb55406aad1a0b8a68ee6579e2c68955eb94f6d883487497966f89eb3c5feae5cbff08bf340af79d58d8c3cc5ca3e13ea626961cef01c55a8faac81440b1b74684a57fa715238b1d8c94c63236766fc25fd9f271c383b05a11e7489b87633a4324b85846b4487ba9dc62d79492b8d9805a2678cbdc225e7a3f050d435c846ffb53ae3f839021229acd939c8f82e3dbe86e13c6b2baf38d9d79aef51db0d0acd1324967c7fdb5be42bb84f267e8adf0147c3b31ecb979aa31328b3799a076d8400d246d5db9e31ece5bbd4eede1dbe477f420023f3f930a0f4998b543f035b2608e618f862aaa7395256a617de91104b19e2ecc4ac3dda6f263aa4cb008f7240fcc88c590382ccd2d8c1c6194c850d2591e1745e2d53d9d8fb183e28d2a33cf81966af225f0a1219cfd6e1da9a398099dff30571c37887d8d0f773ba1593c39f9d2862f0fa2e02fd710140009c89fc7322fed7a5f14728db863b9ef494fcf42de39dcd6e46508b0f2e000ba263b93570ee6f028537bca50d87c7e22ab6b8de23b350317cc9bcb94841cf18e7eb68b8fdbefb2025401bf2127c417e996a83ca6b74e2f4d20ea1730737197a6b78d1a057f8d67d67ee0feed3d0f30d6d1cfe9d948b7f0a86c6a9abe525fe4b56ee091ad0645ec29afe83581ba0fdc09d1b0b37d41909f6c60aa506e658590205ed2f454007f46c2c4b45d799016df71b664595da3df4cf08f6de7405563b3035809d80cdd027214a850f7757f029d2d650f349437e71f55b2387ebfd5d3e0d3e250380f6f576b624f2f11a964233c1fa3cc197119aed41f7e00f2128d29d77f90c799f024fc0fbd3874b349c7c3f3f8f5eaa86ddc39e4cb5cd84bec069e78b8a4f121746a5a133894a41385a88f2df9a1707f91c2e3d711bce65a32ab79a120b133a0ec8a6760f511f04016162d646664bd2c6455c79b7dd0738c9171f8d8c108c5ed2ab434079664e2adc222abcffa4cd5adb4a5ca7319ab0992c74bd8ed244dc153b58157549fe6efcfd11dadf190982171b13048d0d85fb77fc79d1b4eb8e9fe31690c6a452c3872089c4b472ffbba59565aa2bcf086161d8aae852c9311ce35476e2d35a99a475fa7f2b4a2a2409c9432bd055d848c2f5cbe4df9408a807a039f8fe0bf927d4d1db654950fdd81f42b4e96d1f7b8f1b228825fa4649d0f506b97b269b0a3c1608076adc62ec5e5ab3ec4954032858605a882b64b5fd43ea52ebb07882bca68fdaa40395a0748655c90d35e62b80ec1f8b12bc92d758fd18010f10e77980b531fe6b9e2ac2c2a1055925d8ee9cd24b0b97d8bf6a7c8345aa410819a86115ba04b717d0a92939bd79c564564700160d098fe4001f9187ca250d880b0880dc7bb7c6ea057f638c3496308c3f62de08988e7be3822bf75d4f757d70a0ebca25fad075d8d131f3ffa979ae3787980143b9663aeeb7c8824f00d6c8fdc809224d2e12fe206949e51d85550e200484c64c0da3fd1d1674b03b5687350793ee567ef211acdec4690a0346460144a4b745b34e7bcc87cb470b4c5e61fcd57033a0a2d3e15e974651edbc2e36be909f083a15fe9b198b3081731d4d853e386ff1902f3941b2de824db6b3e85346743f7e4150b3f69a841886c9d789b15f9f238320f77748068c4b5ff760a6e69a834d98b5a1ea24533e9c10a5af5b7d6d61600699fe39795816bebb6626bfe434ebcf1d33c6fb899ca446b9cbb8fcc29a38b7a5a997425d7ac0b3efffeb344cc8ada7614592df78025c2964cd1fd90e9444ca3e8e40c10590fb0e531aca63bab19e9bce562bffff0a06c22e9d992cfce03745ad4a2bdb53dac2dd87d64edc352327a6785a213cfd9bd2035fdfb9e3c680cfcd45213d2513c7e9dee7863eb2ca087cc9bd4ea9c08639290f32ff31682e07820d044384081e750a750e4cb1f8590cf4736a05731072e430952198800f3e586ba605761acc305f192dffebfc548b18cb91c21751123732547d8c784fa5a8cc952f9e941436617cddefadabbc1b12e90723193e8fe213b21a49933a72206487e43c8f991ac1b556429bf99eba3d130bd13aab01e9ac6281b548ff6824de4a731c81bc5cb328982e7a36f239fddb1dd4007cffbd56dc2892c1d6ad42a6f9cf2ad895ef837ca7273e6d56a48f36faf6a42a1bac12a68d5f22cf54", "spend_index": [ 0, 1, 3958408894, 4294967295 ], "result": [ "17f1939a60adea501d1df741db5aada01c24a58719bf9d2b07d55a27c7bb1318", "7154f2bbdddd70c4ff507b69d410bc417d7fcb31999a263c91d8bc791196aaa8", "55b6cc0bf1f740b527d2504d528b14d2f984d341884c92973dfdf2b9eaa1bbc0", "29078a5f9da6ba1a90c08ac1432132da1a4f3e980113ec58aaba74c3073e4e2d" ] }, { "desc": { "Inputs": 8, "Outputs": 1, "Witness": true, "Version": 337442454, "scriptSigs": false }, "hex_tx": "96f61c140001087e9a414b00000000000000000000000000000000000000000000000000000000bbb460020066e56a7726d9c16100000000000000000000000000000000000000000000000000000000a0da8851004bf105cbc37b51450000000000000000000000000000000000000000000000000000000036ffc13d0086d145c39025520900000000000000000000000000000000000000000000000000000000b042386b00f41b6f718073966400000000000000000000000000000000000000000000000000000000a13d214d003936d83037240b7f00000000000000000000000000000000000000000000000000000000c1f53e5d0032f83feea6e61ba50000000000000000000000000000000000000000000000000000000098a6c744006b7b9bea56d181dc0000000000000000000000000000000000000000000000000000000068c7606c00d0ff126e0139c1cfaf06e77e6fc81d2323ad8d445ab4ff24813f6b9b014bfcd828d4f1e90cf35b8277fdb43c1f6c7f8d6c9008bce81f0c36a9b4f2cc394d17f6618e672ecd63b31012109a297fc6d1bcc3802ad8bfb7347e7042f513b97fd3c0f0ac2127367c9a895424e046b5db194fc21c25a8ce132b3f53d82621d0511450386845a0da04eb360f133e6047ddf50e32146783d2acfe5c12aa80e892e4f203b1ca89392db85d18c64a80014b67bacb29e73400476de764834c9a1d4304ad44ce0632014349032b0fa65bf526e2d7c66081964c6ef2049516f52f3e2154e69ad2999431baa121d75db2488e41d7bd5b0cf20849efedcbdcac5d8b4ba43c773aea376d4b40f9cf71473900226ffeb66689667b7ddc6bee7c0e9de94af8af85b9d177317165f8f929145eaed786376b37e98b5aa847bdd95f416722dbe25e08c0a5828fd2b7173f904be99eb2024834a43e38e14843005b9d6917f8761dcf87e57db9a7bc7dd13f8217125c408b27f72a56da0550d1a1c5fa76d7e9e41287d37e1bd84c3b750972b5be044b6001333012155a0143dc25abe04775ad7531ebb5c763d5a279675ca655c52a80cca830019b878151c86af32111546c7e5973da75ed378a75d5b760282f2504359157d8bd69311d0765c723635c80b6659c438650ca6202b421d2922e629d0b3a6bdaddc6208a4ae49bf9229752a8846291d754a28428aae53ce63a9c62bb8ada059faad2647b27e7f5200464361b03a3eee2db8609432fc9f77275ab7bb9ca2fd361c7f0f91771f3c52828ec4fcc12455b9deee62106cf59f415c9d18b39ce909e8687085338c2f81c6c057a190597249c39b63795ce575ad760d756302fc8cfe391d19f9ed10da1e64b016993d25b14fd5f01ae8c13e28f211da8444cf468eb3d85b22f47d953a2869cf4cd9db6c12b78025b7e66cb7f5b1b36a925edf3b550e0682d0e57d6f44bb21a7532b76c6dcaa9e02ff60a38d2e795d934b9fe08c9ba900e46abd8abea41c95e9ed7861272fb2031adbff68a64c20f300422f770f2e70a148faa04cff451e396c6f6b9ce6c4a496396c63f25ba627085f0959edc0a13eebcc1c3e4707f659e6c3e0915e6273ccc89cafad3807640f8e0b1c186582c9f5c287b4659aeaf4bdd8af0bee10ad39ba72d188173f8ade7f34606387e12944fc000c6351b1d05bd64c0dd7994cee575c93943a7282934536836210b9faf05a0aa266fdc4a2dec83e2858c544d054a5ebb05b0416e8e3e7dfb47c675e8262d02c2a45a4713cb1edf91b52d37283a307d7dfe4aedabf59a6222a485480c5d8d6d12be9376dfd25e0a51fb3b7156f50231a672ce1e27ca8c57a3dbf4c9ff16fe005accaea603b3d5cdc90abb616b39a8e8111c22663ac0fe15d554cb77b8c58360b3a0e49ec7503b32ee9beffaee1f075d97c22074fbe28810372ebf67d0a8f8de51e3e683ba281f3324ec536dd2222642fb338c6734e4a21c7f9106da99e2a54f681860cef364df39cb5fd217ab558e7a30c005ccf1cbf94909efd698dd2153a303e7fc8b4ee46dca657e3dd5fc6d90828b04cd67a99ee5cee2f1eb68068d97cac7aac69008bc41d61499fa95da1831735ce3a5fdc5edcda61235784e04771d277bae6f06548a609c164b885ea74f76d259d1c7edb1d7d0cdfd493155025ce691d6ee0729eb73cb86658b004ec6e9bbea2a95b899f7afaa8e29c8b9ea9d98b744a487942ac5e604069450b9986c1e1d4cf4e392c7afaa67ef0004fd57016fc90754fbeacafa6072ce2af42758f4e60a67c31214f0790599086cb75e0f1cbf5dee78af75591ab769be419ffe68789d540bb81249f039f3ab1a57dccd3c288064993db495db279c9f926181a39c35017359214c70ec64fd60f1114ff188e181e7e741b873217b06d791a6065f8e1be48f37e617443e18d497cb725b9fcdd96621e467b8a0a86b324fa01210263a3250799ae2e12232f8d782ac03229b1977a2fa994dd0d19d38cb52b03cb48c1bf4e06da1da5a64de11683b526cbcb2da296bc81da6a11a5277d709fcda6c7a55b6841a421f51681bd60741d9cc1bdd8258ab809e38b2b29bba58cbb50887eccb0953bb6b8f55a2be09ffca0c4b7bcdcc6e9c72e3e38da0692bc189eb922a1dce4ff58aecefba92e64a65dfc2247b79e8e1cae4b8e0fe8a149fa20427d6b986ffcda76198b1c196e29d40a8e1e4bcd492a5b7572e73eb157a451ea1a8838fd48dd491573bc374582ffd5a0101e268d28a667d973d2d37458f15f17389f3e54a5297d947180eb472eb491f098097b927dd6abbfd6f76381f82c9b3f56366efcec7ac3deb41db2db24a8e922e2050aa8f62b1698b1bd3e879af52cbb5f202b846a12bd05ec8331669628f30b5694e81814220093062e3cbaa8031c2214d732c069d42f816b2be2f8472fc7d3c8b7c614f18bbcb20348ef0a8401a087876bcdde9393c529be6fe08d4a874d656ddb7ea3bdaf9ce56f665c0ed2f29aada7956e4d1adf52197fd149353e029779afce1f25f292685e0d4063f412b16b9ba8041f356ab194b975d8cc352d0fd7ee5eeaac01af1f8dd831302cea2bcfe5d81005e9b73d24f78d475b19b1eb90502813be650a643aa45ea8a101527a2972b142b8366f4b1ecc3993efaa5f274a9719cc0ff12ae48d7899626368c3939ef9a7872fa70113ccce16050bbdc1c2fb93d19643f6206641e9a776587c0841112b9b96dc8c4374a97cfae1936b031ead072db908e8814f75e874d8ecb4a413911b0526cefc5342a667d559ac61fe91f864dd0e4e281b505d5b31a3279dc4a928ec8ac983952d5dc2cb6d0ab415d7e020e50c9d9125b443ea20f30f9304067eb920a6017f2f9e71a4f07b4a1aee6c1e4d31ede35d897e2171a009efe4cc90ae37d737799cdeb0b73d2ae9ba877866d6c28b5b8ce0f22f4e92849e62862bac8be7fc2d41aa401d642cc7ed9a7042c73fd2598affacb48d1b7daad5dc6e061d390eb0cccdd5ae1ecc3a456a4e8bda8df96659037c2db23c3091516b9a625247ae9bcdac0abd7a987823d702b2a8a3777976e59ac32243ec83abb866bc627f4d0443575f7624b280286acf94e5a1e9c694820052b0f669556c54cb6422055d116f4fcea86fcdb4a7ab7534ce594a5623e7486bbb003c843520bf3a3f38c7ac8e0b43ccc9d93ac7cbbef8933b0db6f14ce144525f33fb9908c5eb1359c95bca252ba90528fa5074d639bd0b9a4370faf11d6d4201c0b4d6c0d9114f413a8f7fd0e259dd275460d030995e54fda775e4d086b04a503fdb8016af3746bf16cff65cbead0c2f4530ee5fccfc69e88e64f465d8ab44509bd5000579d91be86675a6b2791fe4512238fcdd5424e3ba12590d1a0698f3ab5fa3b3840ee3395487a230b884abf9ee8d801b6e77b2b4a4258016c31ca090dcc9a57a6f47d93b1fe31f6a37b2d28eb0b2a58f79250ce617cfdcf3a6416ecc39702de7372489e6900a2adb97c3a4a8eab7e173afa9b59931bf6857796f942ea25cf831f321c04afb9ac09bf1c15e732533c667dc53da916c447749ad90c805c7e2be056c89d4cc6b84a1986e532af2c08d86d7c25f9f8ff6ac8f3169850693c798532c6feffd10be80a495e406f8451f9d03929da93c70ca9f6c874a2288326fce6587b5ec8eec8bae34b6a930a515941546e34e8a758adb74a8e818eb843d7b30d8d3e9ec5a569b285246449a5089994c69f44bc1997a507ecc2160e5461642b2d9605300aa63f0b38e194ab60e546371fb06469331a78aa516b811ce6aee14ea202309134498b1f9fc082e6ce77441b602d41ad34910346daf10c8349230503a54d937d758a5661100ba17bc2275f1c66c78fd2c16dc8d7157f7d196b25a9a2c580ce6e92ad7ac950469c0a1cbc4b7bd7d9f8f0f5d1077ffdaac3fdbe019ca5d7f0036020a6708ab4fe4ce27bcc795b198eb6be3adceb37d825804579a88f432f183905554dbc390b85309746d4ceb274de0e805b7406c41c6ec18e9ac3e9eeb2b3c9c0b99b91dd63545c4c3d7943f81fd7408c4de733046d11fb2baf0c5730dc6e1b8a865ff1b99b23d63ba23455d699f14a209b092e1c02fc52254b129009be00d0598b6e1a91907515661ec67b9b9769379d74b536c19cf8a6990531f68608bc355f45c93335ffdf3744fda9a83d71d5f2258f226b1ab0c3340883b7a4ea4bf70462deb63fe251ba197ab63e0ece6eb3ee3aba4926de25730c3838a4a44cf0bd31e2847adddfdb6495df84daf50e2e17f7e46fd0238a001a4d7b9eb7d6b7632369a61c6f14a82639b479566ae06eb610333bf7b8b1ef323efb800ff4de1812ef1befa3b69d164f9dcda7b042c85c3023c0a65d7a5ba828a09d4b201a8a79aeb5bd2103a4ac4653f24b71e722e33e86c480bdd3c9756267389186680ac4fb5019c4c26ee8f03733f27720bfc5e21e61270a7a12d4c0027c4467a8a998e94295a20f5597aa1fcf92d913b41617ef535092e35d7cf821d4a110bd1105a899b2da6360b78a02cdb281d358652d3a26d6b04b1b498bb8e12c175d01a2fd9801df9dde52c5e44d1eefa91321418c5321ae7afe08810f3a2c7b311f63f4468879f3b9cab3c53ce609e24e94fc0b753e8bf80d90a1e8c5db717da41626f806c453b99ac2856f923c420567cbbaeed31967955c03e9782e26012d85e2fb58c556cefbb782b0052ad5e2a7faad748e9b167bff703460220fe8139ac904202a9ea095f6b713007f0c2e51a7f4062d3a6481757440807ea705d31b0f582bbcbb21bcc92c68902d51c4d8b2c750e115e4725ce6583b9353089aa25706edb0d02ca5ce458b9ada4aaf5d9eb67de043631b5a334277134f17eee9ca692ac519645b98414d35fc63a40ef2498f4e972511d2ad23e928432cdf1c17ff2191f49968b9c2fbb2a19464289223a2a1333b3b462f972affda45de0669248ed796e6bb65bd547b31830d3ff7680ebfb8a03f3514e73170b233975ca725466c00091cfc48d6d561bb4c894c0c393ea0882f517ba5e227776e9f47a78042394386698118971ea58cb3f4af225d898a9d355e5ebb30988d4fea2fbea217e2f628133f816b0422f67fe05f9fffb64db1e0d95ad7765334755c0e7ae90c6a36b7c5ef0001fdbd01c1cd410e6e8d3f9ee6911b7b10a3fddc7a69757211100d1cd938e19c38ab13bbef52195be90ed215828c948e06b11254b06d0c6332558762f4979b30cb16b5d44286c55d44d7563d9c839aad43e794896c39ae5f6c59d1da00695a25556d61f9a257b9c3b6517b08270e567d5983b67284dc702a166a508bdf5051c34ed68d271d94d1c4cab7d17fdae3fba090c99c306445b6350200547448e301728cb015b3e0ef0c5c73c07d54efd942290ee08f7cd24ffd68b657a490bbfa623f3fe91d8ec8cebedda8827cc4246c450f9f313bd44bbc9d08a60e29e8a6448cccf1c8d78b93cb03fda2c837f7f9aecac8583ef11918b057fd1e6f28a2be0fc65748e7ccb424db21beff9cf3de47b0df24b85fb82bc39820c3ab56af99e42f62cfce6ded2476bebfe42b1559551a6954f89b7d66a7772cf0189ebd69287cc0f4f7a6d3d6366109e2509b743ad3c7d30e1b31b4b4c2fa582c6d04f2e09d880be665017504ff768e201612aa5eb10a967f30267108ca11768a25095443c0c6c557306ee60e463d96d38c46adfe2213feb5fc37aa8564dbb6e81ff381b105d37b1fa50a5862873e010305709d23342e418fc8fb031b59862f9581176e80963bb6ff4fe903fda3012a65baa205b7d619cc03238a5f7b8f9731ddde6870823bd7aaf8bfef5be8245aa6853c9f132e83f5e8492e3efdd9a807dbf1e82e609bb6648721ba15bd3d6bf566b7fee38583029b32d1b955b08631add6fbc93d023830ef70d12722f7c8c98fb9b5bba967e32fcf3c157d40b9507c6fb066b9224d13e74037bcad873f92f6017418b64079106900d37814696e0cb0f7ab8cc2d294383cc7ab2a7402b2d7ea5549ac71f7f34c4c762b549ef6f8baa07f33fc146dbd707a295badda26add005e6398379adf6f9b39b1e9aa0f9c82bda37fb55abd53431c3a063935f52ddb91d52c94b0b0c1c4c6fa2d31f2f5e04ac549dfe8c720edbcea0bb9d9f97e1006b078064626e24d692c5370e67be6af073e873a0761f27ab126f32451b00a320ef456ea42a8f474797ab91ff0d0cb2f5a89180916f366e6fc59496323321c85c4fa3c3e0608af8ba1e9ac0e137292888976c8448c4bcb1637788def1788eeb80c3de15dda09d2aad4c8ed4e1cb71e4dcab6ece74b3aacc5f07d01b6e0ee79a39d38a925fddea413d1d1a57e5d014c5cb5c9dc000b083c9fb5ed3a653edff1affcd7219b57b7241ce01e88a3a7e0f0065f7db7ffb1ec66a671f61e0b41c03eab8409a96f8d83c8322078e69ea867a80daa82bb084f48aaa2703b7211032721a5c4f1fcd3b508e8a6ab8ada0776d296f68d80c03e3c958c9ee4c21f2a89ab2d67b82f1be09b9fb06acc787a9d50529ba821181d27991ee4b322e129565f864ac521048677d2d068a8cc33e6da6fde37920d1250e9242f82c0e22cbf6ed18008f541fc14b2191f6d933bd82cabc1f8b4cd225ca5ed054ebe65107bd3e6f5fd74839b4bc4732126a9283dab4c2bc24325cc63933f583676d090d56a9a1addd38032256e5727d692992225a56b23f6edefab70a7cc0e4c998f63f1ddc0e68dd057e59ad4683808d", "spend_index": [ 0, 1, 160980537, 4294967295 ], "result": [ "c2edb65a3843910c8acaee8ac8b960a5ddd4bcfd62b58f50c7a4cc5b8d82ca3e", "663c865131db07c41a98fdadc60bf6144caa9f1996b737c97ec87f32ddaa3bbf", "8d9f467cbb9282aca24a8b49bba8efeed62cc664d53c519804b3ccfe6eefdfc4", "4e6c8c853edbc3ee372ed7f2040712ea193a7e189e99e0713a48cec8117e4984" ] }, { "desc": { "Inputs": 5, "Outputs": 2, "Witness": true, "Version": -208179031, "scriptSigs": true }, "hex_tx": "a97097f3000105fa25780b000000000000000000000000000000000000000000000000000000000f7d92c900ee8828a0e9b2183400000000000000000000000000000000000000000000000000000000b046100bfdbe019441f12872f8bfa445d17f90616607523132c5d6fca1a335dc016a94ae83d7dd70de2cd8cbe030ba58488e5631360cac3cba5bcaa10a68bd87bf6d5ce18e635089d64c2aca7f6f2c9064365f40f5873c66631fa54fd05f4720ba3e2057292e8bc14744af9fa6bebe0f027ca27486841a6bc46339e7df5a2b1ebb3d6afd616f430eb383ad807aa5ac6caedf6222ab3f1627c3f8b32c030cd06f70566635a069016144734ef25708f185ce935a993e2775a7f2a30f2bb73175251d8997c977db9b5d9a84c921624a06e7a180c09d2d84f37c750bda8a20036507d60617252ad16e6191b660c576f6170bb28e3d663e40e6281741f831b71003480fc74d8e437bd83332706b81e060ead39e8146696582e086cb51c83131cce25c5de2f74730e60f184791fface969ce21fc9ac64eb9b166ec4285ec090c371148e355c933c99f79c65f41c70413883a4f2546f0f303b844fa094b30241ea26ebc3c9352e559db36c4daf13ab29d87611f834bd49eed37ab81e9ebfb64d383eb0c6ff2adc6f2bbbeefdc8adee724564b3719b9d543bf230f53697df5df96bfcb1a929e9be4985f195f07c00b4b97ccea403489243649088abb34a5b8dd9ac82bdbdb29a10d5134be33e6f83183f700000000000000000000000000000000000000000000000000000000fd3a8efcf80bdac12a52dc284e40b9db3d74be831b67e9ad572141ee9bb1801fd8738efed388e93660dee7790fb483981f8e1664c6d91a0ff75e68b36bba3ec063062e9fc5bf41841aff600f3c192c43e83194abcfa1f0527c9c7b7b715fed2872fbe84c9b5cf0addcb030debaafe86ac33699dc03dedd6f24c3c87f54e5106f99a5772fd6f7cf13fdcb25d4e8023ba4867e72666e58c4f526e2f2c3b24d3518948aeae1bd5f331487821ae32b4607e8b1f1d8d9e33e21b3a46ae09f6a32a79971c9e778587b656f8df55fd78651bf7913bedec1eb98d3921e5f7d6265a0128ac243d98bab396dd78a2635a9734351946ae5d013e6bf7f912be9e0bec689b93abdc22c0bc80000000000000000000000000000000000000000000000000000000010c9f8b707c0fa690adf9c10a15af0bfaa0194c0000000000000000000000000000000000000000000000000000000001653f913171e35851593fd7b8dc3f177d435f7d76d5d0351d3311c27ba9c677e020bd5df2e915a8531c8bba0e037b307c1799a180b382af53518861ffff74c5ca7363611387d3f548248e27d22b5ce473acc247f62cb590ea5dc8c7b7d3ed9647d508513efafc78168d7dff4be1ba706f5f445b7d4e32c0fe7026fd6b5d262604dd134849853955b0f11ebaf618eaba7e2ab56d29bf735b9f3bce5cd4bef65a26baecf830285f3e848db874eafcdc632ee0a28b03d0be14b3e4cbc0b2f7a509d7e89b70a1a183885d81e9b7f3e11c981210149217bc31f4938c31373a7e097d09e4c5cfebe6a3bba73cb675f61af1d07bbc44c35ef2f9262ac4bc8cf0250611ae4c4b1698a3fcf91002298cc5e82faaebce41aa6b5bff6745a0070062b6ca7de680b29d0607d7732cbbc0be090705cd7e467c3f577c7c5fff162e2f502d0b1393d83eea2fafd588f6700574d357d8da7e453a580a117d7a97459137806f9b0c2b842202f576493b8fe9d2085a10f57cacf3dd2f8215681c588b16363073ff26b39635b76abba71890d882516d18f20bc1fc0d19386b20fc24d2903efe5270a8ff31528df06e4d25486003e896a2f8c4bc38929724b9de57e8e9d83af6331310b76639d01fd38011a14b17778860107c4d7bbe9991c9d426ac13f2c16ecf90a54510121a1ca91542b1c345fd3c44109af0917181448ba824ee9a913c50b2ed815f30f1c022edd2b7253306b4540b70e55e6664ff3adacb859968b45821ae0d41645ab293338d9cffb38d65ca8bb1e23fbf98d458e9752f63f47a508683f4234bd45af58ce649163dd1443fce086ba28bca37906a097d9ba07443c4e48879414b11dd69964935cbe657b6c6e974b6083738c9c270985afd8838ac864cb642f24e55dfa10ba468f6bbefea10e02819f0a6d6c3d8a83243e9739fb4685edaad91abb9b2a88b31a42c95bbc806c9009dac3fa3ee83100f805108701c5beb28fa197926b6b5389b0e730d73ca847fb7352df11807b0d8772ecf6888771ed2e5bc48953c3ac8c5ed7690e200b882db04d608f326b7adf3a26edc802d8e6b078ba35b30003fdd80133d4f54c723911263a74670ad11ccdf73fc90cdd3c9f0ad6a1de7b06066633942fc2e1e4193079b0fa68c18fd7622be69eef1d9ec73ee22bd19a03e58201c59c0dd3b2a60261233cbb0ca6bcb6668f05bae58c3e50aa8001e0431e9136d604aa18184a6770d17f6e61ce4586d3aee02e4f9077ede416bb4cbdd0885086074aa350cd7929e946665c857d3aa5dd215939fb4f13ffeafd36f570daf4453e5e6e01636f488a54c489b60e451e736482ba94d627370911422b84fd54654ffbd604ecaec74edfcbaac05bc4f0278a67fdeb3e0e1cfe532ca472baa851620e62c06cb1276643453388f2f288a2764d1032ac7b9a524b9e1b5bd796da47f511dfe7950ec0d87720dcbccdb4007b0efec6e043029dee10c5963640b01d70adb0420e8403c3db99932a019377e0c8d91fdfe6e64d18866b5f882f8c1f0032d19e596596d84cef24068f9ebeacdea045f31ccf73119c81330ee89fcad9a54cbcd463c55ff7cb45ddca3238262f62259982323c1fc4e961b5ae80eb56c0beb48cf4f5461dbe6677c2806568f2977837092aa6deb79d26ba969165f3a3dc134f99339f44f300bfd537d9f4077bd9b60642c47a97f80fd2aade8350c39634759c79bfe117ce1152dedb35e6d0d1a217811dee07ecddee538d08b8d273e5cbfd970189b6e24f770efed56c9c80c4074c78cef8b15c29eba5a06f86df85480e45baf934ac975857b3ddace566dd4b4cfebbb6259ff18a4447b6043289df210eab4824b076a5dfa73c1bcd19e5fbe6b5af679c77508c3aa107c24fd4c9e977385ed90616e2f9b627965c9a9e503ff1451771423543a9cac393cb9d5a8ff2818b164cc43450b19f80d7a7cd92e0ddda053961e699cc57f99ce9a77ab0dbd3b7b0282f16c75af2fd99ee7440e4f304b3dccbf9a0d65eb46c4916fd0f3acf459c95528c8d7ef34d70b0b35fd8f51f0f9883bcceeb38eabf17ecfc5cceb6a96a871110f2c2db111a95295fe1d681bfd942a86bb82debce1aa9b2e484d7c324ad48929ca77f09fd13fff6ed44c3c48861ff87189575e38d47470e627420f48ecbb49b50aefea244c11231c23f5fd796c7bcef7309028f24805aef538edd0d5da266f830650412a96ebf8d6d88140f16433cd9f14a6f7c937366c81ed19e7face8b71b839b5530fa2ffbd0cefb4190fb1e48172c28fa050d066963c76b45607d0c1084c337c1a0836189873a5de399fb48ecb99aaa98f8b670b5949ea5fdd8019536d3cc39af27e65fb086b7181a3500832eff8f48d32822fc817acbf30a955d3452262f420a49066eda432819b4da4de9c1f81912b13c04b6929d4805059c4d023164ba3cb1a2dbbb4d69ed5066768b68124303d3f214721952e65f3f04c5c9e139839564f5039855c81b16f9cea1a1537798ab1d6807d207c15f4671f12e056e07cbe6d0cb134008614c8f2781993ecf80184bc2530d642d99d380559b41b6eb435d0d2c44a03b3226ff9dcf29ac957e9d8ca907b0a6eecf8c23751b6cfed7d28ef413ac63396e1e28edffd97e1d81c66d9d5ebb4630e1e8e103278c63b8b38a5e75d12d53c35c2e117d1d94c1f95521387cc01107aed86b5d4b9fd2712a0923faf3c6dec60dbed31bff0df448712f705b875bc3a460e82b276feb64b9bf620e037ac8b2398c439bc252486607b41e28467141cf083361a65443ae895bcfb46e69fe8dbebf901f8faa379652caf76c5f191acf358e093f707e1db4ba52c1de9914e75a03e9942bd7b78b582562ba37c39341ae6816a27862dfb476eaad862e142066127db08460ac92b0c322a281a18aa854698451b1ec896fdd537b2d335065e333a36305ae8ada624192459b375471b753ce214fdba256189bde018aa50b4cbb9d1fe3a73e6ee659679f0fcaaf697ac5ad9591b7a1c904fd99017f67fb0f0574169142356cae3dfe973ee4d3d2ce73955cf1217d6068d564aa0347999256e26be6524fdc78f0bff86c96978f71426b13dd7872c3ac7bcb03bb7d246763f5e1cb9ec08ee56e6ad6fa9d7e66685f2569336084b18d9eba14dae3ed3d39b9963c72de173ee6c03120444ef84a5c956c42c022f410d8ab46f7ccba2a7dd71cc829f0e891edb84541752add870837ea5cb2eb8f7117f2237d8709d83ca6e725da307436930639123772cb150c50945bbd2d7996267d2646950654126abc294311a16d4ff5628c117620d3a4bd4aaa0f59435fa240f0aab0dc2f49022b79a3030f6fd5c65a93ce262231c84ee20d08d6fa166f613f805af2e5789107bd7c3d7cabd8a09a824e9a68829fd57481613fda02cc23d7c0081d73fa7c981b98ad06af6e382f23a51148eacaf768c977c5b174613eef34e3b3c8582815c8ed70631f4267a585a8696f9ced6bbe7d92b1ec17892be40a8d4aafcd1c4ae7f507e4ea9d10200c27f7a9e4ef2d35254f87b64470b37d1c022a7805dffb2c76964bada340e59e38971d43d0b0c99b82f724b0fbfca72bf8c5211988c0231d9852c5f4458a0878c0ac6b46d86e8812941eb6da4802cbaf8ec39a33c951129259a6302757e85c0a27af6ea7d07d056adee32a1cea48f3b69fe760bbf7a10bcef05a440401782e1c63df7aa2ec20982ab3b50955f25d5d155dc9ea7ce3376fb1c7f3e3d7e62ca04a15f1652b255161c5cd5b1d503f7008a3092dbf623dd9ced7ca3012845a92706b0a65168478f7d1ba6261820b48c678ffdf5eabdf17395c69c8163b3a2f56ead84cc91a7eb517621db39ea42a3edad998e35a834d8e9ffd3901594ba8158ae19f276b3236d33d81d02b17616276a5f3fbf57c419b9900003be3894b99f5d3cabd4a9226406bc5a8e1e82fb0843d1dddcf95f397c969bfb6ac625251062864b5a3cfc6cd18a031ab61caef73b82a7340f788a1af5e2950b67869d73ddb4b6fa69f1ee21e937a9fec7b06f5cfedf41189e448dbf2a3f7ed7724092890a34544630238bec759e6cf7ed512cb492a2ad9ef68b2079e928bf0c5b335c07e96048d028ec537614f034844cb018139b57bb1995d86f43b63e51d090a4fb259cbd0c0966a5c4fb56f1f96b9e03db771ddaac205faa89d6df5866254ee8bcb9667bc339fe4494a2f1ef5148bd51853ca7fd1f2d639c87563552fc05c4793e5fd3edf37337406c0d466c35294a98fe53caeced772cc910e3000ba42f69f76a20d0e3ef987702f4781d214e2142767164533ec437f31992846f90af1f92339dd44c445f43ba87bc400ca43567c9c1bd1231734aba642e1e2e45c10adbfb970eb4ad64e3c7d9d3b1a3a92f628391496959ed9e0ff99bfda2bf19e9087dcdd4c049de6d5a11578b940df9a216e070a82f8954ed42a45a8f6893116d74f15142b45da7322d0d0575aeae811ff1f05f9283e2a1eee43457e714383f25031005f7dfc1fcb4a4b6ead58a0096e9a0f68352cfe43afee9d695cdea3c6fbf4646e2c69059d28ca858d8bcfd76755cebe7f3b616067c6a9bb5c5404922a025d00565c97cca4c5cbfa9d950466cbba17c7f12fac99248211434a9884afebf72e4156a54d33e2eca6c46a8eb5eab25391ba031bcc04abf76ef65f299a10936dc20b570fd50b6a734b9714cb8bf77db282cbad866a8891857614fe48fa738302de7ca23aaccbb3108480f425f92f317d3a538f732d4e30f8247be738fd49577303156c77882d7b85941affc159095c62c515365ff603fd3985c4fd1598e645d6a56096522a3786c24c8b0f561fce66df51d7e6be34f7fed635319c3d899e66b18a82d05f9064e7e66a82b1694fb7503562aa553d097d5f4a6e78676f010285c88f27b5a0b3e9ecec27479b55328efddeee4a7ebb7d401c9a7a7a2815657c6cc880b6fd7801f36b79fcd809320b14baf520e23c3065e7b081b4fd9d55c0e7e492aad3a8d6abaf2e279c5c89d7d158671dd6138244863c75036684cb8e7fdaf3155d90a694d395ec3d2770f35ebca5880d3183980b691c498414c40d4cd1e084e3c36ce1c392f92b297ab63e1d9ccd84ddc6c45ce6cfaf39df8a834609ed1c88e2dee15020070662022886bcfd4593c8300cee69c0b414df1a542cc8efd80aa0f6a4b868abdc0f6fcbd35ef79e10ff2d5fd072ca8d082821a8329c8daf651237426206bdd82287524d6de21f6549bc62738fbd1a2bd66b9489ff3a769461ec53761112d6f1fc16102a4a66e126cd354320de2558a54dfdaeba713d135d23ae2100bc22b74680f69275ba8dd04200e27ef2ffbefa0509855785c6a37223df654b9720addb65be143cffcd4d0796991a4a683d566325b70f05caa668f730808af646c811aff91621cface8ea17f2da5dd1fff5387e65169ed16586bf20c9e8d82cfa27c0a5b88a7f9ec982721b51e810e19a27d42b2b211684c31751cee0e69dcfaf8a", "spend_index": [ 0, 1, 2519856964, 4294967295 ], "result": [ "ff2086489bd8239a77392745c1d4709be47f9f3a622cc0185e70767ce8c7d386", "7389250c5334183c2ba13e0dd8fc2fa16640d07802418d63b3edcdb42e43d6b2", "dae332e69edc29fe196749f4a8139cdb401e89bb7be4322da29806e788ce8608", "83a6690614a97c4e9bee5a61b6a6e8fdfbc956ba33c7f3411320c7f3b20840d6" ] }, { "desc": { "Inputs": 4, "Outputs": 4, "Witness": true, "Version": -1769011343, "scriptSigs": false }, "hex_tx": "71078f96000104fd70808b00000000000000000000000000000000000000000000000000000000350b590700f0a00891899e8f4500000000000000000000000000000000000000000000000000000000f2cef4c800a8bd1f6472219e52000000000000000000000000000000000000000000000000000000006dde36cb00e70ec0c43d375bcb00000000000000000000000000000000000000000000000000000000558b89b600a67d6ee704a265e2745ebb9524c88857f1ca22e99d95d20f3e2a996abf3ae45c711e2b198c4ce1fe79ed484a459260dcb6dc5f0bf6b71ccf9fd93e17b414c03906b9f38ca3db4d7719e5ecb3253896f5e2df8ad5e4ddaf823edf806d0c417a00c01f820cfa7bd1586052b0940292736f41c6c44e10645f7c380de93fe9d925eca44e23383478eb00ac80b180996ebea3b6c4f4edb599fd2894ee978d94f3de95c34ce7827a375d4d5beda4aaeb3bea83a13aecbf9a98161a6ffbd5698a48ed0aeb56eeab370b3822d8cc5c6f5fa08dc3fceb92453ac3cbe7ce3224e4a81dc848574310c3a8fd8930039fc5af7cf59c32f8171b00db8d82870a2de6c56c336a15d358fb5c7181cea7e861b1a4e82f98c52b54948923d4edee3aa26c2b2d371c19aa91525e5fbfef27b9436e9fbfcc00db7f64c31e6ace8c94f6b074a4aa6bda76b3e9a062e7e124343d0ca6669464f4592eeb02ab7f467fe3b364a183f6be75c4ae239d2ee6be4d77cd3246f2f83a4eacd0ada764ddb4e721223deb0362171c8607a1fe3dbef48184242ae183d220bfe68c230ecfec6bcc24443790f3cf9232506df8a8a1c8c32f40d028a27ea9394fc890c3d0cdc528de4470b971a56b46bb0effc8031691484bc942f24c2699d90719aacdbb4adf518a7cd1f44eaa5894c98e7f3bac8ceacbb72d19eba571c35a3a9eca102156dc2c3beee5e51fb8bd70610ffef0c70601871f668e7f3a6e4f27b166e678329026c9005fedf0e48677416f6f39f1cdc355ec760dd03ba4cd4b129bcf13eda1f59726117ae987c1e28f7dd3ab436ed877d2b1bd0b041bca2590d6ca7c0a1a2e64e8d23c6a42425e64b2f7a592cce4bfd3bb0796a372bfb47294c58c7d0483ebbf3a2da3dd5daa9e11b52bca6dc8c3e2211e1ea550603573f34f1ce36a0883e09bc1d49cb239f8870173d96fc6e07df60dde863be15a0556b2f87a4a50e8f6132aa5a847c354225adc51d6eb49fc179158bff2344e17371b7bc4eb6a60ea29e8be5b785cb63607a9433ede70109a88bb99770ae32dbb9064028893ecc7ff4b8161d9c3305bfa21cb5b73dc41c91be927111a5c98190025c867ace9358b4f6a6bd5138172e276bc6a5f1ebdc2b04d4cc015768c3a3cfbe04e449ff7fd9edb982aba62e60580ab1760bd6d8c7adcb606b3194ddb584dcf03fd1501183c77e644d6ade06c530c767c9bb4aef9ac82573884d887dc00b6b24c41d4d33988b97b9534ab06a94766c9971520a4f2eb816d47c8c5f383844117f6ae686114f6b51720667cefb3acd2ec8d7b6d6fb64bedfecc74424a60e5e4855a4468a62fbfbb94c522e0ebb1415c2df4843e8eb1b65806053e28930759262e0387741da281e48bae924a671c2998d08fe3a9a6a8c4e5a0c72384d8c2ed2a67701d5f7e46034ee7c4430395ff2953a5aa0ca9869f8e3d45477930134e1b763bdf7c75cd6ccd914c1f820bf938f922c070c22fe6853e5ec96227c8503df935290423dbde73aca4eb203f35e570c8abe4890dac5c7bafb8d9c9d5388e895c41574dcfde1fb23e82be0b8f90b140c07eb7a0077e9bac74f2e45a94b6b6ddc783143182ff95e0ec1318f5878649620c863dcd116515b2d379df6777166c280eda1303351e627362b4225b5057f8a0fadfd99b6db8a78396cd498143539f90f5be3b326b2e26faef68236eaaa0a5d00564f93f69f66d6442d56ff4d5cb7cccf8e10c467452703044710d38aaedc0cb5aac4e9aed47670fb54ba6d6ce0fe14cdb140c58d47bdffc0b2d28a26c053293a8fde201178c252edb515c15e5034802ec8f01b59a8eefe5b6fd1bec5cd99f1e5ae99eb06e52663688f75054a1d9d385c580e246e4f235c7bc571f793a5f3183696d881f3c01b7a48bc4e6a22f73f872c596d5200158aa39ac3dc9301fda6a4aeff63e45cb5d885fd8b3db414f4eaeb6132ab118576878d577aa7b989cfd1062c6bb58efed34a07d6c6896d79380996b54cf6287620a5fb143ac3e9ea6265a8a1ddbd7fca6878506985287c516fd629b52fcc97b72e7452817a4a2ea4527f3e7c983f60a76a9d5c1e52ed427ee065019ccec027d8cc1f132a9d2f1352fc85855f21d4cc40b86bf33fcc6f97fa3bd6941eb5bc5331d6766bb31fbda0eb46f978a336312b14b9e6af83d6ec793b89c486ec8c41ab9af53923938934931d387a29259034af2380da3105fd58eb21ae5e81230687c5dbf8a0fd1151937d9abd1f1736aeb50b6261e1ea7d5f4268f24540a6eee067a1d5f211067c8681b5d9f902fa5c2c08c0185a6484ebccf4b364fb41fdbc2d6c6eb8111a11afc5476ca5cc37913ff504178f22a6ce2ac4e60cbb0c2465116428fab889fa39246e31e60a39840771dc019d2ee25482959fd4aff7ffcfc3d583e6b686918a73d1db5dd658a8897da241b40951e5b078879b30007c8f914fc978ab93cbe92ee645d1eb14290e5af48c0948bcac2d401b448e397f5c80411772c122a021af51deffd3f998e31b25faf1aba08d7b48e18c16c2fab8c0eb45456b474091fcf373b91f4df98487852dcdb60e1361a8ab8b37f37f9417174a178f40aa98c574121441522cad634880dca326c13358baf0d77922f922d9af20e7764033b5958fed0b9ee786608319a661908d2f3c0cf5ca3c0683fad6738d40f4af7e73d48a9216c4649c8d8826bbc3d6e9b72c82a378049b1cf75214bc6fd99c8a6a403eb923329ec2aa50702aa03fd9a015da6449dcd9a071468f191bd6283100872182b4a89302797627cf5459b9abed93c01987aaabbb981f7014cd13e9cfd862728c3a29629c527c91fcafc6a1cd092dd4ce8af1e2230fea4d41be1a4cea6a87be841e1dd5a0cd4908cdebca27882376d9a2ff789bfdb7ba13314bce2b9a00eb6b71ef5d4bf498458a5e27245923c9407c0fe88755005174f6849475678ed491100c9fa4805678b349f4915e9aeb04dbfffa898bdd7f07083f50ebe6d3aa712e2030305142f968a20862359078e94f1f94c11783fa7d4d8967341358e74c063d40cc768da891c64cf92c92a6960db3ca484511c326b4d823efdad3198025b4fc3944ea72689b0b7120dfef825efbc7753b4a1b6cbe60a03395b382a9b62ac45388f0270990e5e720a5cbf61bd02bfeb221599d622e749557930841a1063591b57f00ce8ef8ab2d9518946a8b4d780d30e27cdff3748b705e4e4f683b513502d04b7213c4ba944325ab3ed7be4eb58744de16a7970fef27b23b2348b4d54b8e927fe322b98e47bc50404c9009a4423697326eea9d13f21b288152dffc6f9d433bbdf0a3119787a792e0f59f63ef6fc47bc7e22675279d621f8d7ef1eb96840e7928da8e9c51506876bbea54af8cd20c71585c8aa013c29babf38b4c1426e83525a6e4d56cc734de9ddb93cdfe373ac75ea8b7c8bd4d1faec95d1d805c8b12c3e680c2c909371bc95bcc579a431c4d5df19725b1444e3d0771c5350b17ba0cafe804f7af4cdce68a87f5fbbaac4b20c145bddf8059c524717cf860319c2c2dbc07dd3b41338a151ec6c3236c02620de1f5b40864bbfa85a6cacee63744a49ba070afc5a210a7ed25b8707c23b1b05e6ccc1659dadb9ad2bcb0d07e727f71cfbd67349aa34c442e6c23005b9ff921a3a7f36d8d3c0e2f23c06031d13016e07d1146995fcfe6bad4b7f2ee3a5a22e6e87307f710b8d8c3b00c2c55df509cf378fb6eb0b7627ad9939776c6d4f3a8e9b432ffabc3e8341416aa32de789dc06754f88633cb498581359ac3abfc7713da3bd7d91fb2ea5ff9e7a169deb3ef1947f1487e1fccfbc28f60734888c80b718a156659cb8919cdc5ccc702b1d7718126189db6d9bcb600060e216fcf0d5a4d5eda055b254bf3b63b1675324681675b328bf001f4509becb0150a79fe22b7c0269a9114009d4a9da4bca8a872e81efdfb46a0d6c4a73ee5b3b99acff49ffa404cb3614a1774d8655881e7d41fa8a4613bc98dc7b22fc913cf01f4aa990b984fcc540e3ea286cd3486b4f1cdd92cc3556118f02ff259b6c1893916998628db54b14c803b94958d0711695d90dfe0d8102618ef82bf999d96781928b284751ede7e3bca8b04ffc69825b8622f457b312eb95b31f765ae0891bcbbaa40fa886e9cf4a55d10ce20945f364b01cd76eeae456188e4d25f40d02e31675c085", "spend_index": [ 0, 1, 454989834, 4294967295 ], "result": [ "2ca8b7b26428b71b1c427e1bbde29e7219adc411a5857f92b67a57a4e17e4561", "b835b1f1807d7c19fe9914cae81d288d884d5216e35a9f51f415e5415200c00d", "626ae3ae67e58ef244df2e60c3219cf9bd30537828a70fd98e0d553db185ca6e", "49953f533811a49e59f60d6b507d447528ee2e16af04c29653a889a7afa34c9c" ] }, { "desc": { "Inputs": 9, "Outputs": 3, "Witness": true, "Version": 1087930968, "scriptSigs": true }, "hex_tx": "5882d840000109d11d906e00000000000000000000000000000000000000000000000000000000d1c8d516fd1501a186435131d0d9ef0027ffcbfdedb642c4fa0450f8eed99b17f0c3474757c7c9d844b0f79dbaa823333099cd816f889cbb650ef5f599c314ecc363ab80a68eb7913e8ca1fca9ad2d1f75e26066b413e3f24791c53f25a09944458b4208adaed92438b3faadf525b7cb79d51e8b265508524ad32ad68cd8f6464a1391e9253dd90fefdce871b92cc10f04e87913c6dd1d8fd5335c078431a7a7845c9e258a624b0ca6a3d65be769f069de978996245fd855babcd48d319578805dfa8fe7491e6b0a9309fb0fabf259274696454968abb90af4333f53c74463894d537aba51c3146ed2253f6f492ec6ee2d6546476d1b604c152fc67bf838ee667e14543843e5fe841336d7e3fc1a0b772a8f0b68c09388bb3f333ec3c907612a9478af0a000000000000000000000000000000000000000000000000000000003247f14f004fa0189628f5b62500000000000000000000000000000000000000000000000000000000adf0cfc8fd9401e650024b0336cc11f1d733ff33ce9832236f517e86ad9d92dbe3f99a60d760e759cf036ea1df8f23f300cc21a84815a07ab8862ae5448fe48a61b5c4a73405f145e623c93ba814014d71e97007de76449596edab5e4c8199e617ab7f618b81b99c72d0fb093ea16e18ec1cd6b44b083511609a1ff64219f12673d869b7679b783a988b63ec97482780ada3354f4f7e60a7e646976c20c1435d7487dfca1927199086d9ba22ee53527675a890cc0ff97709d64f143eb8058a5f39c0c5e0b29aa5c1d336e8e1e4334a82db93d955a86a6180266aab667fd3411269a18862be399d8fcda14b86dcd4d8d01de1eff667e130ebc5f8446a68c65b69ae54a562daad3127c1eaa17fc3f25949b9c5ba6e56a4e0123f5906d552a3f40f54dff4bf599e0a36b8b59d381f67971d8210c4a874f22d4f32cf8c895df7db0343841b86d2dca2af9e6b5cc35aa853f35e3b7433ca49b47133e96b828e6edbd26b24e3a589f2b0479bb7d59bcad7e2c956208400d96ccfc612c04ef1f6772829902593fb73a1960415cf554e142a1ab4b7938c0b60c9371366d0f7aec032ea26d0cfd7000000000000000000000000000000000000000000000000000000000120c9ded03842ac4ac4f2978f342400cb7bf6c57742b077a4d151ad6a54242759f88508cb1b1d51a9a56ec7f3f60aa90d42f4d5785468f93ece58937ce5471b4b6a51c72b12b9f8ffb09271648f53d05df8b2541f07aa9f66747075f343b722acae5d11ee89bbdeb8c40cc6522f470f7141ea40874fd8f3823e3b3ea4be67928546f389a60f22f74916c48a2f74429bffa625f84acdb7a4cccd6b7cac765fb44708eadb66935a9d3dcc6e417835192a9426e5dcdd7cf4df24ddb9b2a9ae1a30dd22a5c6f6ed4ec3432ab322ee791a83f5c6991dbe864c96d9c48cfb500000000000000000000000000000000000000000000000000000000072325ce1fd6a01c9fab206814c27c190b8556df10cdb80f1ed8ed5083af50f2845bf463a85fc42c308f5b8d1f9474963a8a5f5857511b415f9c70b5544db3619208aab12822862c2f8032c1f34876b405d5c2ac3403902bb68b88f252cd58269e11774b803abe2f68a1dc2b81d2bab923278824c33187a91d94fa57523adf4c3bab05977d1b91f190314247c21402f31b9841c5dad2e91a55d2d55b8ab4c979e32c30b1c3878de7f96ac377d4c57f833b0610940ce513c6da1a96e24deb783b685a2505b021ae12f58a758bbf537ae7b22e0adfd0650699d14359c9969e2acd89115f4b5699f2d00034fdded9423cb93dc1a71f6c7044925787f8e7ac3763d265f8c6f8f601ca158d123065abf8e240d22331a3d8d6932e47424fb365f3b8817b2d6132b388e18b7750ea859979a9db75dfff5a3aaa3ac7651e90ac8323888ddffcb5d85f6fc44e21d4e745f1bb2f98709881372d1b02a5f98d59789230189cab9f2a0557deec93185ce163ffbb5a95f2794fde6401fc3e02c00000000000000000000000000000000000000000000000000000000ffa093e2aa83442cb66f504b4317063a9616dcdf3c7eb8342b8e376492929e3a7824af63c20f7e68933e09e050b7ad6ffa6d19c002f5c996f7ca21b3c6bce4c1c57aed09a215d190ac43450ee75121aafe112ef6530ad1300b578c063a7e0f6979d087fad031d8ece71fd924d40a989f439d4ee219b1940071338760e63e40f6f9a200f850cbb57bd28fc4d210e362442baff1c68e169a67ddeb5c18bfa9cdcae253d49b0fb5da5727657848505bd11b9e92aedb8703c8000000000000000000000000000000000000000000000000000000006aee706e91bdcc8afde1b433d68ab15dce8289e92773f52bf999aaee11d9752b3bbc21be66f0bdf751b9f3a76bc67e0e840c0732b95cb8a74d105f783fdcbb329a46ad2938e0cc234d070fcd78393c08f184ce76a813b90412ed507dcdb903dd84808041948e6157e6ace0e96da464a774c7d139114e61ba7dc70990a8adb253cba2761bed4fc16d95e0d25314efcbe73e6a624d1b2e1523f2ff2d4e3c8a0000000000000000000000000000000000000000000000000000000065580be9002ca46165d11b55af000000000000000000000000000000000000000000000000000000001f2269cd00f8a30788031542986735a1ff65c88b802469b6494733b38d715068adcc3e0f23abed17c489cd02f15910770b3a152124eb6817f964c952fc03b20916823e7b2eb78ce2bb699f7f75a8aabcc783ca20a173b1cb970eb856dddc4e7b015fb1483965c33881704f5f644c8cc5cc387f9f2093f6ab3a5202540c4cbb5926cd90029829f060ee1d1e58041e26438938c77ac452e235c147b1a2ba7ccbf7785c761f8025f76fba58cd5db56f8468865eac56349ba8cf7d071022895dbbbcb98f83ef1dd11be09567944512705cd0734439c2a48e504b442b576f90f8c577478562c83f7a4d2b36560505606450f8b1281ee013db911de9d028c660c70fbf36581b680b11c4f0f5e01892b94cf03e96be8e9b6f4ca3c8a17e221bb97e4059ba7b17e2c0e5bfec5151e62a590b11bf358ad25c2a621aef685f35acbb8a1b53af4fbb9e7fe764c6ee4593dfc940155c8a1f5de8ced50a7c938f18098d6b670f9fb66c161ae33b9cd140baa3f4179cf66aedd3467f4edac01f84fb6e3043137ab7915da543187b0149990ebf20499edf3cc1f61ec1cf66425c05c6e7cab47617587c114cb19b5e05a6aa1132a1cf1593ca35fc28c8f163da373bd0b2cf264e67a63e57608037982a3f73adc2987c09d2f394913abd30d7e60b63efdeb2ef7a3f44bb01019e87f85e5820fd2f154f3b8786062937a00e86a9fa0f241d6b27b16031371a8c5824917b7c64c39e15dec48551746085161b7af95b605faaba0acc9e02792ae92af2c9c827eb4dac215710d4717ac21b18734653e3f4399b4eb894d713e5de4ba1c27a12bc13587da6e47d77f135f3d7d9ce9a9003ea3915b05eeefb4c039145c669db6b8104e98ebadbb3386f8a7bf9865efb18e26fc8cdc901f76dad15fc0cd8f18be46323f16d425acfc170a8c20a84c3c2a081e120ff4c09210e694e9dde489d222b89be1e2124878bd42bf726df6a3ac2de8af64694b8c97cef3864efffda643656df603d61fc31fd1eeb499c4111b9dd0f1b612e48f0bef9d867c666bb8f2a3191714bbd4e80e8f5e994567eaa174b26e583fb9739b31235d03f5ab507575fa4c8c82970705fc581a32fdfa3cbd4140c9e8b01c8c1eedeca2177dd7be00f46063d23aa483ee1f69843fc5bd63dcc6024675f9044152e11d530fdeea913b329b2f13476da2d7d3db8e478147fef8bb97395bb32b394ef16629c0dc9a639d4f5501503efd255b65d1fe5ed611737f7fc0451d71f8c0f540000281bfef07fabe9ae65ddfa6641686f0425ffdb45264fa32aad79a72b717d14a9eb168e83d44ee35305b4c3c7c16fd6f63b4bb1ccd38087c905b653270e0720e92f3018ca90c78b4c679993edbbaf4e4851f021b32df88ecec3c41abe31e1832a7737ef0807ba8276a9e7979067a90c3d129f9bfbe14dbd5b3cf9d69ee074a20572e46988f8749e8f8c6b4646ab8e756ca2ff9015be14ba0008f3c7a00136dd300a33d81b2002f4146834b9ec1650eddab1b9c9e80a163072cb2675c50a8b474ef2690529fdffc56661dcd4565c4868571d38da25fa52f724d1717de4884e26c58ae97f89b6fb7d3a3330a833f09c037ee12087e23ac16ad70c9e0b15e733f5cd024efc3863fd6f01c342e5db193b50b4f28ac75a7936a31fdba44a1c82d62da1dc3b65259878d1e7ad1e35ccb6fc3dc5c76591df1975da5f241055b50f1794d201d4c9daa47b31ccf6ebe8209cc1b9bdce4d9255dba5d74d929bea4c142f3ba02e91c23bcae26b0c9055296cdcaba4067377604f297a799f431ddb0b2fe89c5d486a5b087a6d1a03f33985e2a5bb208e8a45cc67d3f4c167c61a01fb1caa413b910892fcc91055763f69b62c7acfb6f19223c0e39803da2face3aa5f97a0b460372a1a2b2b315c32a300779ae9f99888aa89936c6a7709035dc54fa32c5f7e4edcc06ba707acb5d21792717324d37a27d34a32e23f1ac6b499e944513e44e0082a1043ae01b4f7e56294d89e6138592f8482ebee6eae39541a1629afb8380e42a8b5cdcba9e5696c34cf55c29f3de0a4d9c02cbb42dc2ac325877487969dcbea36dbaa62e0f03b65efcd4134a15556691614e72d07a5edf5545ebfad0155ac976da8409047a32fbd44023d543848eac10a9431d0001e7904fdde018f6691643ab0a74363b5fc7bb25615aa7170cf1f708e8c664fa9ae853a619dbbb47dec3a02cd76e12319ce94052008449cf909db2fe00b20eb2ed0a36b39b9727590428f6a45d8e6ceef2ac582143bd467ee796274f5a92f84bafcbea39f295cdcf8de8474fe03c5709a43dc73ca0cf126c5b39d8ce8df0461d5dcdb6d29f9860c7b300dd571a62fe5ca81f0a96a0bb050fb11539a878e2c69c9f16793ba315c35886add81b33f3b39854e468288f92be2c8822e8f4e074bd7222200adf8e15f6214a9a69d73cdfe78f5a42e9dc5346287d83feab8c41052bff3757673bbec13182b1a2e18e581f1aa0d50f7868b9a947816cfafef7577eaa8280176002a13db76bc4fd36aa67aff8b000d5069ab18f619dbbe2687833c7ae1f8e4cd078d240c3a9bff7109081314b342b61387e86c83b646c1f47570ba13a9921488d591616e0c9cbd0bc565a43c5b77f8ebd4e6982c63afeba586bf05f70d3bcd130dfe29833c9f12a7be2d6d635eb5228cefd7e4490a2b8c6473e38450770c189af0de097367457c8abc7f22f80205c0504eaf5e8d19a3908a65467f7b1a4cef40c3369cc6ae4c8a4553081566a1667decb04f520ea73f3b2da9cb3febb2c5a84b623e21d620cece5b4bcb40de3641afb72ad71dc00673d414b2a5d1f45a289de1f6bb2226aa3a31711a931ae68f67ee9efaa0df12e6acfbf4485a5ad74e49a7355667fcd12efd4c0124aa6676322213513bd81322778887f8a83b90092801d318ab832bd270a37a5e97004e5da6f46eb97189f607217314320577dee6e47dabedffb2f5067ac1d50ab5164a2ae817671171e6a4e432657d856c75a3cee09cab538b90d3fa96aee3117a2fc5c780896fc6540f25e12ba8c9bf554fa2efde7126a039a64e7d830ccd735c753b52f048c30a613ea6524c774dbe4df42fba3cdc5827c9dbd1ea05c02968868bade637ad406ea12796a524e5388bcd354b622db22e14ad7c3b95a7c861ca1bd103e9a38288ceb4278f8b5ec7f60295ce9255e4c34eb6e4226969cbb5c0ef66e7d74e6853165028a58044101a07b68ec19e2cc37acc2114226379166297e53950b7b1078b5c0799c7f4805fd104ef202b50aa2011d3339d50fb9e2d37a0fbfaf303cc4011348acc833646286ea13ae7b4f13a655bf78edb1f30d1ac3495b67f22ba70bec37542c32efce0af454629a0f91384149cbd59991de11780ee8d3433fe8a4e9f465ea86bb0b5213d160bdf4de6de489dee6c60bb73281bd206d3deb9ad8e849c959d67df008179cf0e91b7a70785c55fb35bfb9853b17ffbd7ef7c82bd56d25b2a3e184a69d3aba2fea43f421597f4abd0c2b1a74758c55b5824ccc1474f0c8a7dc9eda88589025833d2abeaa53cb8c07ce020effea5ffd9febf976de95819fc60ae81b4b6e1918883b895e966259fdf13331ee8b7d7d301fd1c01e4befbac09ea666c088b6e686ad7dcf07a36dc9b4c3908014246a34efd904f6133908099d3772cd45f7862245fbfc2c3d935125ad06b84f2237759450d8ff071da1e798d4c092d49de5911de9bf172f9110f9c8adcbcb2e18b9ad0057f1df919387947ee0dc54933a7cf02d9883c711338951481ace24e570664b50a6a0c4d0990bd8d6dbeb1b70e6fed55f04715cab4213f5e01ec28f6fd3d03853485b1930e29b995a17aab9d411f7e55613d65a8b5558aeec5cf9c2361855a3031810ddaa5b0067554a269f72c3dfa4a7b591b8c2bb26e87c69e7aff9ce6458f908e855c3cd9c975ff35a49583fa1d6886160f6592e3b17765e192093b6d26f36ad1213f9e5b6e65830d73be96e4f0b431ff60e74e8cdde280c6f7ff184939bb5c04fd7001c298a056382619d7d85f178b3cd8399595d2209d32d07ac324718e88b0c65db437ae1126fb84baaab6f8b6d619c011c911fcbb4afc046b84053ac6b02c68a735853e7223db64de740311ced5992c9fc1707cb1ebcfed06adf122c0155c0be4ac95844607da8458835a72ad57936567a444bc3ea84a173246c14d8a3b38494e691d60f243798773c74e03c82a0290dc9761711d05439ed9a876f82fb0357cfa109b76229c60c79fe2cf1921c684fc46c3330eef8a581393010d8aabacc50a31fc5a6c6620f728986321cc9ae3922678a6315e356ebe2a3e92daef08adf3fad5308ff0c748d56dcf6d5f96bb4a5b3813dddb790abe43fac3c431a064229977d2b7573dcddaa1c18c11a3aa215960237418bfd39385885cb6ecdf7fc02737fd6eedbf9e3094eeeea9689e43d136cc721a119d1bdc90c42efed7c982251ed86876f4706ca58947bb1a3e2787b36fb3e19529947b066336553158b427a403902cde7a6d072a6aa6d6e15ab9e95ba3122da146403559d5107d51441f3e3bb40f5f869534c1f49f7aeadb7c6b9d18b3a496864928bca65656d7a562adb078a39292e2cdf08690837cdbb3d501bbfa6847f77bd924bb07c4518a843edbdfc7b1fde5eea2d4b702e7f839678749f090a8b803a8da0b80e9d248a8b689ca16bd79c0f7289b88160f0ffe998c00c484e30e7a978e99527540cb8d0a15ed505758664af7ec5983d9d08e380c22ddb230d8a542a5a0237577fa20399133db58849fea3a85fd4ed4efa30c4af23e3f14d0c8ddffb45f191145fca63229dcd83863db507a7a602bd5505466223ece20c65ac753d28efe27a122ae2563dc1bbd2449a4e80aaa19450af5cfc23c047e66b1b26074a72828cdd81cb00b3385d1c3f77722b232cf59bdfc23baac41e72872ea034a12fcff4b7cc903ce8e30140000034bb3c82984c566a5c3e95a1dfbd795ccf495b162339f7d767f0e75413394e755bafcb49d3ea87c1bc6272209b393af99bc6f17489e8292379922e659797454282366d4ebbb3408c2968cc9cefd8101ffc275bec9b00f0f305b937836bdee046d36a26aeba87b63e5ac2df090f02d7941e3c6cf3e0264b964014bb3d52d4050f8c5fdafb33c34ce9bc2e31e1c749a7cafc7c6d87fbc0862129e7a5c45927d84bc32bff30f4287dd27f9e35b61f92e9ce5d499ec93dcb0a093a94d2b2a400b0cda1e2edea33db0cadf89255ce9bafce2a6a8945bc4daaab6a0f4ade3ff870464daf7292b83987bb58804f93e17b80ba342bf439eda4ac68cbd01c27576fbe3b90d83ede7cbcb8bf3ebd1551bc167ffaf17fd20c63852990a9f84687ceecac6a3bc11eb9b02b31de864eb137ae8d34a49a5a31ff8c0c625aa2d0f8393769bc770f9c7a1c915bc854473dd9103e698b9554e8bfa569436849431510fc5bb3a7f5fc9a7cdada6b626a77b388a6c2ad8405103895236b58040368f107f78289007d9a701d03c8983f893c9bec8bd0bccf5cca6fe23b7f84a5c313482a07aa6d296beba70511ee4b731835ac15d19b5cd3fa56b2c7332261e05d3c45f3d0849be54149b30375ca6efdd8d5918b3c87ccec57e60fd81014bbb81619eb52cf7518feb7b9a7c31e06c1534ce2f9ce68c41a889119b8fb7a08a96b27663dbc2834624f89d42005eb25a9da928963f76505b41acfbb78307ab7fe7c803083e0ade89663491e0f34de4784b0767891931b0af5de19f784ffd32f005f367c4cbe20f0af216f1ba8e71d7328051037a843dd0b6464de272d4275e19ff4bd36984f32225bb85924422e8562fce3191fac0faf8901b97930fcdb2a75309a6439ae3cc8df4a1ff96535758ae123ce155c8723023f2119f34051c14af2f6f6ba3029fe0658535a1f156e5c57da55df9474df66b906129765b5330fd0364405a24393e00131dd8fcade97467846f2148492a419d7d026e3a06c8e1edd44ee3c2a5dcae4dd20f8ec446b74d90070753492c2656b064fb59396c3622723c5e7487395eb41258e2bb8319a5e9db2188b6a6bc5a6d24965ffd2105a94f139c6ac04905fdedb55f9b00344a9887c44f031553fcf6d0ec4ebb4c2b6cd8e8b4f53083cd46adbf10eaf646cecfb218ba8de1c7e5cedfd0a8142ad3ba730b71ea559d0210eaa026d85c7604f9d437b1fb6807e87c6cfc75d406506076ab631b7fc4f8681e9a09894da2fd0ffe79ad5bae1e4afbbd57c315fb1a566c8c1f320254db2a76544346a29280a06a5666c02aa07da806d46537a405f364e667f2215b2449e39f62dd441c3d5c9926787385679bf046b8839702dd2da4bab8d018a4b69ebf3747029b", "spend_index": [ 0, 1, 2069202832, 4294967295 ], "result": [ "1f828c6af674e8d1e1b008c6e775a4a20439e73177943bad98045c5bc590a9b8", "6785d0e45096d3acf1afa0b0d6d20e11dfb69a021417ed14626a30009f792e5d", "aface3587b476063d465dc2e4f9180a16f8af0d4123d1360ecfb135cab72aa80", "47d0b57b0b89597c624964d6e436816435ba96288a0eb47cc2e6754ba2b9cb33" ] }, { "desc": { "Inputs": 2, "Outputs": 3, "Witness": true, "Version": 1959860592, "scriptSigs": false }, "hex_tx": "7019d1740001023867b0a9000000000000000000000000000000000000000000000000000000003f6d5dea00948107edf99ae02c00000000000000000000000000000000000000000000000000000000719a559b00560d4253039aa0dccd0e2dda6ac8985f9b143b2eb3bc5ff298f93ffb1893ae7e1884630415c30cab9e2c71abd1fd48e817b7277cbe3bb1fe28456fd8213fbe84ada36962c65fcf815971c8efc67f2f411c719222d4b376c6f92d1c56de8bf5baeb2cbaa72e48bd29c0ea4deb6bdfe3113f813eb872198e3f06ee4e3b646bc4b3626f720417c62b02256fdb4e0aeb747197900c0e3d51f55872aaac60354dc7595b42e115dc1927b4124c31fc37ee69072fba58d351794a70e9f313b26b23240c7d90c81c1b266ca54bfeae192ec32e132b386768a1675d8582d210ff1456c8da309f67def5d377144d0c9ed67d45da982bedff793f25d17cf19b2ac4033c0f5c9bb19ffa4946396e7076ce037987a48d486f647b9b48e2a968f46087283a20f817249893c88ea2d5ff64eb3c145c7c2cfda8b23d70ceb4ab4b984b655dc4e18fda081f7128cd63a8090041699cbafdd9f7bdb26f8235ed8b0ce542132ad77d09cfd14f51ecee08c8db139cc99d6df20bc3eb1c54da1e6f0db8558d157aaaa89ed1a0d983c081e5bd8e6fd248b5dcebc712b873765badcaa18c9ce22c8f9340ec89bb53cd007c0e6834282d3b7c703ec8daa6e5fd6cc4362abd4b47cbcb295996d437a58fd7851cca5d25819324e51da4177b79d1e1d35f082e482115db9d9b06a858f50d9ff0beab6eb83ff28deb3ed1df17f7d237e3fa6d70204cedf82f8f99837299dcf8889881a975ab09495dd64d2abafc40b852a7e97884ad42438c3906f743731020cc92c0b22657a72c9526e206368489a9d53697543b57f427a94bbdbd2fd3a4bd7afb2b56b6a1c3bbccb385e1717471320728441e47a1a74e714f060d495d8600002b57abdce9a077355f7c945e1fc62f91900702688b00bfb8bad563a266560213d087b0746ed67176c424d82828c0d69de039245e72074ca1499ad6b6d1058d85ae4a9e39965b2123c7cc0ff199aee0f6cbfd8f9dbc4defeb3f141fbe6d0d617efeac84c7548b8af3f7cc17c959fb3e8ad5e628b167ad72a7c7a7a454c492c37118da23435cc88f8b5660898f17e526638800a118a53fdaf094d55945e16ac956138070de1ff8bde5261cace53c565bf340660a60fcff95bb2fe24d936ea32990241f3f0f48d33fb385b468d08cfedcab0cbc36d5a7351a0026a7d4fa0cf4281303feab80cdb09ee1ba37592e8ad12e7ca891a736cc4452647461c3689eee1987eb292976b9b354d654dac5aa7a12c34dd3687766d65852381a2191d69d4cb84ed513728d7bcff8476279a31c022378afb2d4b57e53ab19a42ed52dac1ecb0edac702fd6501cfd5875908f51d2488056c6d6a38263649844b905436bf387ed391af5475bab504e0ab5c2e22ebbafdb5587e6e6cfe7b580a54c97554cc6254f07848b04f4ac982b69ef43cf3d1369429fa01433b292dd455c6e8e43efb4131dcd000d265f14418d6c2423bfe3d11061e1579a399ec0f0977c9b7ce77717765a90e2a93cacd67bd6148b43abe8d14f4cd01a050d06601d9468dd2e97d462aea18b474e659babf483abc0f102098600a69c1f5fd70d214710e29480ae4a28cf11873e99b647d650ce0dc5ac76333d60e3aff9005b0e9261da1684911bf0dc1a5c2f96e60c3dfe0c6a8df5fce68c61c604bb5a6bb7667957b79b226bfaef9dae992d10fb6f362d6b907a83ef12576d1907eb9e0144ef103ca20f83de50472417ad10513f6aa78219b1697ce9ae9447bd72bfcc7f5dc90327c1e4b5a70badb70b05107efb6746036695974129c2bf1a44eae2204daf10f7039edd39b136aa29b2d7ddc3225556cb5399b93cfe02852fad98e90a1f60f215d6025d84375ac2eb5773885e131a114feef4a95eaea11b12b7aa9366f5709d37dd494", "spend_index": [ 0, 1, 2627618632, 4294967295 ], "result": [ "e61c8a21d808bd6b58e40bec6069d31b548bc0e3fffa1e5e45cdfadafefeca65", "b1c93d3736df196ab73e1715e4a3c773c687416531980a554e53f9aedd3cb4a8", "c9acc5ecc7295e41dd9ce686bc64076f445f58a2787d07efe418319eb16b2440", "ab97e6cac9ce22d4edf7a13ecd667a77ea8ec17530aa933f7e38757d921a0cd9" ] }, { "desc": { "Inputs": 5, "Outputs": 9, "Witness": true, "Version": -582183053, "scriptSigs": true }, "hex_tx": "73974cdd0001052083665a000000000000000000000000000000000000000000000000000000005f485b35fd6801431cd23801907a784851ac409634decbeb657f57e914e7b67f2356c0d3c5cb461117bd1a9912a81d4cc8e367c0188950dccffbf84079ccaaa02e97b84045ee87d4948a82cc6792911955a895f0bc5e2570ae9f852434b7e47b1f7bb28231e482746e73df3e7c9a2ff47dbd168250af81b1f67e54c017398a4e4966844da3d210608c53ef9df1e7e60f32d6b22bf91c34d594449bc7591bda0001af45cd07ad7da375271a6459d74451b3397b5a5c8b9fed2289e494204b1bf71101584faba6448186c0334ac5e2c00916b41d75cefdcea86aea5eb692847f544bb961f8a5f3762ab5f629b4f5b1b9fca38c83cd54a72438783aa2fb5b6e8bddf94879219c451ef242ed67486e3beafbb76b783f7cb40515a7ea86331ee5bf7b37642b35e816567fac199235e20350638382411d4775bc963de3cbc9c28dea3f88a422a619e57f11fb1433f0ff059ba8ccfe22792f8300eb3a9f6588c44639d34905114a6987ad1128cd3e1c327932bc918f00fab7da5e00000000000000000000000000000000000000000000000000000000c1bb96b53f4827f22ccc59cc5ee14fb8b748080bc0827affdd669ae7c9d32fc7268db1f6982d458303c024abf63e7070fb787690335b608ae35a4aae84ca4a7550991751df33c2c0b29622d700000000000000000000000000000000000000000000000000000000e92187c35477e0373a026fd7cea7643ab45571840eb7346f0e221cf4461bf35718c4319982e2672b7f083ab5958f47f816a911d8820feb67497661ffa931ffcc8b994e707ed10fecd6eade3a6d28ebf476a959c373d0f6f544f667d58a802a5cda00000000000000000000000000000000000000000000000000000000905a84e620eef79aacf885f15f01c0bcbee7a5c46c16b71c6570afc5836ddb84904e1c85f0cc02de39343596eb00000000000000000000000000000000000000000000000000000000c6e7076f000632e2bc09fbcee918c04d692fc831bf3c13d8f129beb80528e9bbd0cf3fa2d2ecc42785190d41ef3cec8f810d2d24e712fbdcc9d375550a823261269941a55d285ef2e861005fc69793aefc3d9c9674184c6581c0e565b2534716911216ba4c719779654d848f3c717d916fba785bbb7ea590000ff6efab5d5a7acd50e6df99388c5d3b8c045540ec29ee5624f9e558fd1f5042165f4c0d1cbb6ce585ac72399d10ff19e5cbb9713e6601755366bddc0deea6995b06197f8144ab4a0a3627b9597cdfbce33e89ed2d7b5dd1a046d3ef0a1975f420c0bc59acfb1431b624c84f41c1b6d99f9c389a4dde9f63be1a949bf3ed8f8981b95ba4224b31cb070b25a5a67265f32b9b74678a2df22acaaf0c733ef2010a01052135a6854b08805da0068833717c4ff09b6615aa9df33050a9f18a389d4bcfedd764552295604c35e84c20fe87a08224fc351ca935e2e036740dc094f5b3bf2436aae0410799c2a0d8edd7cfff3e4da4384c58f569a2bffc5c1317ef80a748ce2a87de5b42f23c388b502057286b3fd99b196394196d83980de7bbecc1146fb95d02a339ed56772528d0a5bbee26b26fba3c33b9db160df85dc83daaca965c5ebd71544474fc902ea694e7a148f8818ff3b0da797561bc04e039f5e97e55228165601c51b6db02dde391028db4c907076f1bdb3b78a49c53ff84ece976d9c1238cfce0e14073828aca0c765e09fa2d27e25fcd06c82d3ecdb3830370f55f1ea42b7e682cf79eb48f100303130f7cf2fe6722ffdcec99c71fa263ff68e133759ec9f672ccd10d8ebe6a0b8e2e27f4653e5926c9bdbe0b2fb5cd729a19cb252a83cdc44504304ba46b2c52311a98414d548849bdca6c6d57da3c53cd7e4df714a68ac5ac5f2f0a731ccb19c84114d8bbfb4fb0bc155c94059f79adb6d65063329e691f4a7872b9022675282e9baf7e64561378d0909036af437ce4b95e56a1374773c203c6b9ee712c9e0c745e5a457b8e37363c1cf584c36e633679cbeb79ffc743f4888027b4eed8e45fa8a582a2e9c43a319cebbf225b342e8f42a28c1455c2817b95f3eeeeda604a6e53ef7fbcc5b6785f02ecc2a71a1d39ebbafc9fecd825e231017654783a31cc05f01359ad89029273df798d37323ac5c4b3f401fc535660845c9e894106a0803e53dd3060be45985b6a7d48f0a3aff81b3fc8d2a7e5d9eb6e808224ac5dd721d731fbe7729a227d72d42621223c4500ca287f019e41c88483fd1c620c4315b3b7357664710a402d8ceb07a50590e8d5a5a6b59d22ef68ef6d35a0ab5154dbd0bdb218ce3f869b335b231065f2fcc1225a5508ee94a05588d0786b064abfe3e65f0def6d653e3d05445be6c561fd7102993b2e4dd89af1af2a7dc2950830d1e999e99960794a43e32e2ec5ff98e4abadd95073cddcc33d953c4424ab5f2161b95f870e002bc8aafc8023704cc86a250455a1481aadbcd07e1c0199c0e6e4363f4fb01dc8905983e39fa064ebe1de8401af7244da7216ff8893c01fbb974272e32494bb6eaabd4d6ecc0340e6de827018635ccd6386cd7a8d6cee64814e4c2d89eefbee931f110e230e8a33ad942e2d88374ef7fe5033bbc7bbf7d7b31c05f22e8081e25fb33faa7eeac363b6603e9e30f6cd5928e5308384e34acf8a41f6ea7c1169a710dd841caebec6416ff8a4e6f99b6cff1e937fdc90f8f194e112efa75982969e5671bfe73368ef62696da026a5e520d4f8249742b92ad5378c2ffaa318b368ade2a843cf1b88aa10037ea491e9b4bafb72c831ca50ba884dff5c4d99d0d8b129ca5583f1ab02a251f5e5db820e0327b98eaac31e53ae45d9d51d8a83cde314d21691239a02d0e5943804abb7dbf6bf03c1b7d6b101eddf5f13e31d0cd6108fa81a1d420b7f3fefa9e4d3b92b00fb8d416f25f7d15617bceec73361817f41875b699f7c3e98e1cec69f293d9778427cf1f94681c470db40e8b7e9f15507e86d9b938ab918958521798780c22cf8c3507cd0ffb1dbf8081679dba9c4cf9568e3e98aa402d18fc782414fdaaebf446f45a1d666ee5f024639d39b3bd7a00dc2b59ef55cc8a91cdcdecebf3f1bd6a655daf4b4965e51f9546d15c7967c661a2264b2ac28862b1543a92ae5b70931bd5371e30a9feeba18b42df6fa91dc9fd08b63a61bdbd2acf36bd8ac213cf2b24c1b23c20d8eb1b5bf66620cd247bd2f8e3de82f0c9ca0d0af57ff2e5553f95f25ff43949e56ccf672475218c634e5b1167b41cd2a5c02dd0a85f53850d322daa354939496e450f089ca64ad2167eceec5455a832b1f303daa81263434022c075c624e3cf7e0920735d3c91f6d8ec3c47a471a13855b55784ad09a6b5de74367e4dcb5b8a63433c81235449561ee0acb420ae4dadb0683f8fbba2ef50fbbdafa0a9035d3b3e13e6824c496cd14ba1047f1b9595dab67a5c50d56cd97e8a84af645eb33912a173248ac7678130e4191ac5fc1475932cf5735c2ab74588eff8a83a1f8bc9dd2448b2f11861b86f7e0856a64d7ca4d0f1d29837b1609b13e707e4e3c5e1ac43b0db62da81fcba12b2a1dc21eb30a200942b357bca55f57d9ec32d78018f64cd224a64bc7a6992092481778b7e0913226919c0d89a011fc20d6b47c554fe94158fed3fc92a5f2b2d2cba745044625f9da71e9b5f9879ec2860def5d9f6733545575917230d00f8ff5b51b472a1d4c3c87982c9f653b19a650c67a1bf7e33a7fbb89132ac9bd6fe727218759be282a1830696f06fd0001ddfba61b151c9ef04031e7a6e5b7ca15cb88da64fc97b303ea1f21640140ad0fe340d08c97e3549d20f777a5b8c6283a3636d8b4e409dd3266b7d09f981437aa2a893be0b8bac90f43f423e0c46c6f7b5c27bad92375da64ce7bc08dc3355af033d9b6303e9206cfcfd158b1fa01de372b208afd80febbc43b6f55c7836b66e399ea58c601ca9af4cf92ec8f0e5c3d385c332e38a21d5e55cbd741635a7b8b745d686a58332596ccae9dfbfde4f20103c7479ad14773cdc8d36c272882c34d34e261d112a5b6caac15bf931cf1315837e922312b3da35cffbb85e912853f5cf273e2878d726d9f71d8d39d0e2d2bc89ffca9c61b2bb3d9a986fe284df209d382b0f8f23996656e0457e3a6d43925e758a34bb9f545b8e1b7740236329fa93132fcaeb03f6949049fbd1c11f034628a2cca5ea733f7ec50bff1fcf1af770258a8f355b008ac044cb47c3972ebc4353dfe86c0835e6a2030fff1118b57923672aed6a96d4155d8e55367f9f0ea18d4e11cfc4143be5c027a399f6753017a25dee8ac50b710edfdb0d7c0b8e856223fa7dbd2a408c85496dbed5c8f13668a26832af397c2deaa466f21b5c6a0c38609a03b740f9993914838ca1c7cb18f88447e9c130467e268c50d9e62803d3219a7e10b38a6507c8a6ce000313c0aa9502fddbb3e3d131902e1878fa70ad449be7200b6a9604866a44c0db0bbfea05282a32864147d6d8fbf18ab6addf117af2157c4d13297c47743071f7932c902890510ea0c59dd5e14eeeb3a147b11bf39787e17a5d4966ae9eb5ea43fd150768cc09fd147891f87947291c61b4695d74ddda743ec995b7908afe38ad4f6d5e359fb40aaf489a7a4eb58480e7daa01a4919de1ec7494c326c3056d2bf1cec0ee165b00969a9173b98a614cce0bdccaa36fa0e636f4ed4b212dd088848a4f509cbff3d0f6bef613404d7b0bd90d6a8b9c1b0928c8d15cf057b111b9173ba9a07af0616b7d13af1dbc29b494462ab6484e51b889c71dc0e8c23df73231ab4cdfaab71a0ba40e6da76d954c785ee9236e486473fb6929b44cabb2c2b85bee99639c8b9a84be65cc7935314607c76479f927eaaa1ac21a7235c0098dcfc9cd0f4b6470b67f27b4df713b0b13e7d41227e3d420e107c4d9ecec86e4054b497c6e19c3609b09d573633052c60546d32b82304e393b78367343daaba6f592d4e2012e427e63f4e454287226305b9e5bac9eb3e82662fda422951b1343e1f72a035a4281752b0793fa582685e6a5c8b6e5d9ff9ee392370aaddb07b7d8ca6cddc75adcdac83e4d6622ca061c8bd9ed8f56c87bc1d9885002eb86fbbe35b890ec6758baa102b98762bb680ea2f633f7f77332737f1fef6a5bfdaef0458547e8a7b79c1dceb6739bd29d96472850565a43480636647fef16021b1e430aec2471cdf1d7c9a6ab573081ceb573ad18729784e78a0054016cb38870fe48e48a8070aabb03fd9701f5b670d772834589db835848a121c4b14407325ce7121518adaa5274eaa555bbbfec7f507b21c27116121f89f3c84167d4f1d42a2af145846db53e9c2a8f88f77a25f2087fe7745a025a8743f09c926719cec16db56ad11db0f1ab8f2648311639eb64dac15d4fb0dbad430fb8d629c3ef2af4f9e0968328a4c7d212764a1e94935134ff27240b648dcc23040174905aa7bd36f242e084a1698cbeb7a9a285a5bf611847654679d5e74036f0071d6491de3084f0192a6fb4bd0a1ba3749da843584171a951f2eb3e263f52cb052b9e5fdebff91fbcd6637a3ef9829fe7d93d6cacdaa4f94162192b8e93eb8e8f7af25736765bf28c366e1cb1a519d3136dc07028d1d0c560531d2911f901fb23a26e35a14869aa4cd5d55cfa6d9adb9f4bbc9bf8eec98caa09c3903ea2ed74f3da121d6cb4954b5998316c69b513935428e7447ac8b79fa41b0301304b8e9a05ec247f9ac281a91bd721d1263446209eeb6548a5266e8d2a82791758424e0cc8850ebb2340f6c1b0c24a0c328623826c8cc31b2ce3c059ec341394fc74888cb32dda5f25f5eff22ed26f7b2873c52df9178f28a0ed8f8f4faf432ca70aa6f6f6acb0574754bf8e6f10f4fbd07e9874a51e7fd1fa50518e6bdd9241bc0c027e702786af494739a4b72f37ba08e949b86a4e89926b73817749571dc874e4fcd473617071e87aa2871635227da9257600ccddbc68de9c5d8510187f7cafe3f6220db62d2d7e3af1c5ae926d39559c6c6dcabc38fc0e71a96c95eb2029a14a746bc26c4c0e559fe32a651e218091f5716c0328a510441cc728a83d66c0c519650aaf4dc46e55991649b6f5dd8189dca9f3eb351c8274681d4d644d926d3799cd44d7473f3a30fd130c199bfed08584f7916f1b44eff79348a36351ff39d0ce07df98fcc508a2831e51f5884f281be2a7c83e4b2b16cff1459e1b862b72ecd2696cc483ffc778448a42e0ff6309bc0ae5721dcb988239516dab328c96115b2b882c5112b1e36f52e737a0091007eb02e0074a914ea860e7a7ff042b9979cb9168f5de530e80b68384e1b3276e68693b0046e1f9a008fb013738615b577ec58f9419da832f30102cf6318f5878b322bdc9328640f7136c9b8592e892e675f26c32b5dd229166bc259459c10360aa8eedfeaf893ab8f818703a800b0409c1c4500d69ba1c7e157fdcee9989d23d86a9bac053e7055fa2c596859b3c8c3347f8f223290e4c1a7c5e9627bd5090ce562b27361ebdc2882d93a21dfe1bb0037e83500c8a81ebca2c5e3e117b5f0d50b3619fee8f89c18e5fb55bd147b0e89c39b6f8e027631eb1b0dd6d488e3079a55297452c64094d0c3a25323949801e623681a582dd9779816032bf3bce58f94601a8e9f04afcc639f08e81df7202ba85e06802128ca7f5d341b6b4e3c01ae93c12bd92cdb7223530f9993ba1dc0b0508bc08e2011ed3d3305759ac54a85d335bd31474b55a03bc909602fdf30193b3229e2a93a4f9153355a35039ee0d98ea713127cadd4b7ca9c488312930dbbf81bc938d1381b6c292f33385ca92eea8f131bc0c304575b9a48fa03a424e8c9766a179f844f6baac352b6da31e841673660de4ce2b6e6d5caf32368504fb84d1024a5b2f6c15dc4864bf48d8a645db39aed07eb762e9c2247752ceaf76f61f033e76191d9099e6e8ff5a9b787a1b7dd3643dc417f035a20b2d7a1d99e8b1b8dbeae858f6290566f7c608e5cc7964b6fed8496e8c579852b43c3a78060ca91f52afd035a5863491081d57dbf53ab7b4eb52176082bf0d717c68003aa77e82bcb70808601d6b95ca510248af410a722cd81e669d32cf4685f37b67487245c9a13497dccb9a30403efa4e1bb120d7540b4dc39bfd4992689c412146c4ac0f3043488094bf3549bf72664a58626d015df30b73d036f88b82b22b6807edbb5cf506b8b5d6ee6bd871ebcb3b8adaabf107033b02e92e0677ab627f5c844a19e891940a7f0c3c28ea98b5b338e986ed6e4dd6e25311eadc37cce458d238fff787079278f02efdedbf1dd4209ab789dcb4088d7495345d94794a94025e9caefa53ff460955c1660154668fe4c8fd63491b2b5bd7f5335c99c7d05dc104ba24172e074092ce5fa7949d0d9d2c449d8c0682236e400cfceda2ab232def19549656bd6abdcadbd12c95edf6c7f62545b3f7916421987062fd76010064da9e389a4577abccaef484c55fe77253d4367a1ff3f92b7fa0565ab489eeafb573af93c4773fda641358ada7250a85ec5348b96a15d455e1cd206a82f0ad00e602d450acd57463de4e23e29003839f5bf84e3a3c415536699d8f961ba8f76152178c7fdac2898f0fea6968926804df265145ce7cb9f5dde543f70e2b458c76e2a53f08069abfdf76f4586f9d31287b1fc08056645b3405abef22d911bf44bc0cc23aa8c29338d6cf775043a4d32868159c596fc75d7a924e4ee242fb1e59c7d22f923448a55625c0f8999351a95e4d49ada8ac1902d395da4e52ea81f3aeb429d9becbd4e6f8057b3a1a3d48b7607227f9bcda609b68be03efd4eb8a87d9709151d0bafef2ab615b12d9a77f3178c89df1044c0ad048af1e60de6eb617403cc7c6500d778d33695b9d37b01509fc46e3766ea9589e6bb3998416618bc732ae38734aad3ddcb927044bd0180281db02df1e54076b5b273739136b4348a00ab2369de94ddb335c8d10c568e10b189a50dc87fa2862b5fcb760", "spend_index": [ 0, 1, 835738094, 4294967295 ], "result": [ "2d734581aaf467bace1e46b59c39c08db99f072fccf6d23e82f9b1f702f458de", "a98393b820c393220b19ac97419980b868d41ecd214d61e2daa6044c4a3fa760", "ef56d4431fd774fa93b02e9da15bbb015bb38c500c4ff276c96ef05b9597ecde", "d3ecb3e839c3a66e296e15c974fa1f0d33c52dd94a4ae5ec27f4d6744c17313e" ] }, { "desc": { "Inputs": 7, "Outputs": 4, "Witness": true, "Version": 1967939290, "scriptSigs": false }, "hex_tx": "da5e4c7500010792fd8d6c000000000000000000000000000000000000000000000000000000007e46af8600670e1b8f697adbd600000000000000000000000000000000000000000000000000000000bbdef6f60068d2d65f6bbb38570000000000000000000000000000000000000000000000000000000032d173c7001daee86dca936cf2000000000000000000000000000000000000000000000000000000006aa761b900f3e89cd460eb4c6b00000000000000000000000000000000000000000000000000000000ccb6e26800c31e0cbc5c9b6ef0000000000000000000000000000000000000000000000000000000007c58f6fe00fefa15063e583a62000000000000000000000000000000000000000000000000000000005689de2700c319399c04718e01085f77ef49c88c42059d42ca7a64f34426c8de3e6388197bb6e68742b62c0ebd42bfef7261f3950313fb5348377be1f14a7b95157d3fbd0226e22d7b43bb9f9c673c5435e4e0a25186e2c9f5aa2da6d9b1e018092349d7515cd9d2a44f01f84a41b20fb8fbe769954f571bc17e0c8a187c3188f9644a04f1f05dc9c1bc1a17049d3ce44f0e93d0ff50fade0bc4914220a417f0f88c606a32a14d8dbe845e5ffd40f2b082154df5a3543873606c2345a51fe46d20736d0c50ed7e041576d5ce3ad328d6340a37cb92de870a7c817483240fda75a7417bc8d2c1de8734dc523c6f13243aa80ee7c8ab5935d30bcc41f282c6cd3f91dda229a81cdbadca68124bb0de3e4a771095ea80f1da2a7d620bd8a2ce5c7d96ea062a02608eae58b356a379967bcaf927ae3d41b2dab5d56551d0d346c36911640feade98759a6fc0fe3dd7a1468cdaca58772ef7c9f8b1eba14b7715055e2d94340c985ecc4cc2e1216fc2824f0fffa7dfd70821382101b329fa42803b056079272ddfbb2eaf65ba7da081945bcb30af729b41c1856d7ac14ae2d6e59a5abf6e8565774e200f8c6fd01d31b48d3c5b1dcf48c8bef79640c2adbdcb929a8f72fed800ff41b23ad81f6ada2423a0aa2e2fe5dcf20ad7b92861551c9c6e8bd6228cf17a05e99bd5eed4d7a6d4b685a80515f4786fee03c420eba331852dddca8d34a0d136b5be7d2b5d3429e6ecfabcbd870dba31bb70c3350485f4178089c6390c40d8a75ee8465088ca2595fa8204989c2fa59ebdeb8b3c90aa3e81532effbc2570b1ec44a1878a3716c39186ee2d6a56a67b2bbc76d7939bf689d563e17608fa6ba8fe05a0265a4cd1c910ad6e9cfd1271c9e38f1d3471f7ee7f57909d6712d0723c4fc8a0c1f216596616304915263c772111ba3dc6da9b8fc3896e147c9cde7ca13fdc5d010f41137edd51006bd67201d94952091f2ca39494d34e979c2c5897668e5a0828dd9b291e428d31654117836723782cae1cce61cef09e26dbaa140b7dd935b1e18e9820555573e4a93c49764091500121fa50472e53851e3c28e9bd3cec955bb39721d863de139025bc4be8ba05b973ef67fcebf908afecaa127c7f9aed12512392a6d3f102595c3d5a2b3286f4c7bfaeb5c5fbc486399b74966a6abf6e262baea23a2d14332e02fd37014a3d1c9c7c5d3e01670cf5111047e0f5adcd1436c627d32c9e8faf5e273b5639f42303936be5a7ede623355493773150aec93259469c59d68ae2b7a52a190c277d9ddada8176a20e83cf2eeb5b6bd2f4edd9d27f5f99f50db42bb54415ce5dbbe680bed7b908d8206bb5039459f5e1cecc2f589475336671007e213eb21d5657d45b3a33f21c705ed0719f8fa8fb9489753b308eee1d538c5cdeba642771b0fdff3a9e53e58c501bddd7a7469d5d5e7e65935e26ef17d07b8808513bbed340efd109c4804c53fa45c02102605ee740e5b003c9d054b88ae9051124ed669ebe901147a3b37289438b6f4124b321fbbab415524ccdb4f2f47845f08e7b58aee2c166e0d4ddc799c94830ba8798820e535f897fbd8afca6822e3bf4d20bb0b92c759c7d5b60350ec086cd1665adafbb02f605d23bebb19b2d520d98dda7ac6cf45255b8db17bb1e42be38d633e9b4053631199db0fbf58444a5b5781d03b68fd0ceb10c0e936360326db9db8b159de2b9466fff9cfd5e8fed6e4612e2964488192b6398fcc9d3e826aed8b8000002fdac0194f9857e10851d93f9508bdb431a5ca40feb9d5b69b4a47d1450c76f16958363ccdf47967c344c60d0a1eb62fd11b5a1f5f951548014b47513bd1e3a4365f9adac793e028caaf5553697ab6d0cfc0193d709453b5f4e94a2d717e3246f1a6a058557ce0b9bb36ea5261ccfc83cb1a60fc2ea36ba94343ef55b22acd8cab7c7ff573a87d654fa0a4396bdd9f870c0469027c6fd3986c99d83df7e602a75dba070ba7c79b58d1d4ae65c84f70551b47ab9f8ca7aa29b9afabb1d5a2c446b42cddabc0f6d8c2803558ff6f1fd28da66abff385d277cc0b63977d2a53c6feb24f52a324fbe84e6c5f620255759b7e001dfe5c82b473851e81f14177359560714bdf9c2f2a606c6dd3baf68670f6ef095ab26985bf537a9009362c07339e5160065b66ce65d674a84b7c95507cf71447999674cb227eb743e649bbb92fe1ac08a4da3bac66726610754d3b6a64d59d94bea2d2060920ebdb319c52d44bd23fe315b6b86a2ab9a5fc54f1c6dbca08694709ead0dd992d3f418daa01e0026bb481f99a16107166f8594e698e85e2f10b91e75dc9d58c5ca9616a69252263a2faeeed71d64ccb86e768d550cedc24fee65ad9e897769481060679e209212cd4e6e9483905cb7725baff7f4c43c2c7f8b256b731559be1888d99002a768622a51af6bb03deba3d185bef9de84c994bc6196ff4696620169b7f53caf763cc9ea0496cb933fe7b8765d8005f79265f2c9b2d9d82ec810fb02e8832dbfc9745156343ad74f0c11fac3ddd911b6d16a669937d29321c8a606b9d1d3afffd15cafcfe822b44ba2d01216bb06da8294d58e81fc9035b3aafb957d0c99dd72fa61c4c4661f11c585180c512409f3cf3bee6333b0fe475417ec9c2a1f781f3353596eb3daaef8b91576b9deb419f0e4adafd8c5e028efef2e9faab37fad21e8c8188059a5954391ecca6aa9b87002b35e2290ff63dcef5640f60032d491cb72645f97d24276944076e30bf34e386cfc1e0ce0ac3632dafb9fb0c2634077c2f2fdc97bef19fc576c12b7a6f84b2c4ece672ee1c60e26548a1af55c90e6fa04a12352a00d2a2f3fcfad95249d997548c672f52775a86d441cacef8aea861786320730e7999fc0475e8a9afa4ae2097e9709596cd45903555b2d18365a5225696b7ab404ecad8089fa0860aef0d4705a49e8c46f660d1ad90d7b518514ab547a567b7ce06f65ef471381de14d98fa8d612c693b634a9a1c2bff887bdf9de59bcd97279f1203feb5f0e024c81b4662edc92e324162dd7690804ae96af23904b5b78be7da356159928d3123bf37ed90f97cb754df65419ebc9ce97cb1bb6afee8516c06e9327fa0323752832124c4a8c609397fc5be98ab28ab976d17447980c31c37ca2995bef7b0d6ad7fc8cee2dd1f59fc35928fddf01dec12348c3c693c66765ca7200c7e2193bac0656d0626a024d5186c7e885308ebdd055e233c4eb5cb82295a6f5c6472a49dd90b9ffea4aa82900ed8f498be4cd0d444d96ac5ff0c5feb63d7c960942a3308eb4dfd3632692b5cb793aba0e2e0b321d663c86cc5841c91ec570f19237dcc3c575476506b463503bd66d377103f985c3a2d4d6fb325dd9347346bd74b4281ac439dc364e999e5345f5261445c89f758c7b04c67c132db5ef7dea7cc14e099ab2558c91e46be167256dc9ef770e4e0726b694db32b7f56a5d40e34d7ce88406db1556137260e8fe8671ed8f75ae5819a7a81bc45e7cfcda70272b6872216afebf9085e58f0cafe86cfeac94257e596848d95b98ba1667b2e39facb8f69c603ebbd68cad1a4fee47c8c8efc058642b95cfd4e672ceab02a83c58d93179bd2a7de2d5c0392b132c76f807ea754d24523eb912429476410e6fc91b5ee277c7177bf947c3571f8396b78156136030f4108402bfa362df0c7ac29ee852dc1996b5e7aaf3bf0e6ee74dab654e5e5050ff8c43f5ee6d433d2c420b4d0b10c99b0625c358b5b4570eb113589eb2c7f89e33079e9c9f9bd5b6b8add1a101fad6db97f2c9a8db4281b490ed4dacde83dac9bc078225daa5c099fb2cb23727fb56e1300b70c94b1e7bf9a5ee6f8fafc49e91e300b03f884d", "spend_index": [ 0, 1, 4201556418, 4294967295 ], "result": [ "f376684bfa2b0db930959566252814fdc4ff59ba9d5203faa7330d050ad97efd", "72e9356eb5405b41e6b2ac587ddc98d847d0bb08eef936d7fb0860c07bcd74ac", "09ddcfd0d8cf5ab3c2f6af59118f0b2f7bd7624145cf4a4b9145c32f844e7729", "02b1bff8bf3a967804f28065609b74af482b26f4a64621ddeb70d428a32add89" ] }, { "desc": { "Inputs": 4, "Outputs": 9, "Witness": true, "Version": 1625509545, "scriptSigs": true }, "hex_tx": "a94ee3600001046790111b00000000000000000000000000000000000000000000000000000000545943e30092a9a53f1c4b2ec5000000000000000000000000000000000000000000000000000000006ee094afb7b4f5af7c7d82265bd2e2b8bc5ae38828fbe8ffaf3091f8ecd537b26b7aa2e3e240f30cdfa8dc2a412bd416bb9b99d503d26886841452e317616b800818ba2a3b9ece930fff3d87773c4a604246a03ee5f0a0a0b4a989708bdbf7280c966c9492e1dd84e9b3d0a84789bf1d8d6cfc6971992779d694ff4a772663abceffcef63b87915658906a877ebbedb213f9536469d33f69bcac651ed5f213b1289ab8199581a4bf27349250ef44b05cf43ae0615b43595ff95b98ddd78ba90e1757864b00000000000000000000000000000000000000000000000000000000da523d1800c1add33322b102b500000000000000000000000000000000000000000000000000000000f87411a8fdcc01bd9a5d2365676f47378ab9d858c3624bcf2df9a516a3c0b9043d4388daec747865a95d5f297c59881192b98a81f2b6af3baf5b36c19ca448a31314f00e4de81ba068cc65a1d764d7efd1a11d8b0982bfb50f374125485e5f081ebcc697f013f8d837d41dee720bb04208768565835328bae9b514f2440087c3c8da37b5d46cf93a6bd93841f6fa5fb64477422875716dda7ac0662c682e20afed97aeaa4ad186fcb18c82b14bbabf4273e00ead6c6175f610e737d6fb2d817b8706e89b78450f04a04afc16bac6cab646697323eda5efd55a80eb1b44a283820390d6ac28b1c13836609ad1aafb7bce2378fb966b087307b1ede3f58d981881fb8781ab9dcb65bf0d360d7da6f8bdaf010a779a1209011545f5cf0e85bc2c43de609fbe2a1efc57e11ccd369f8470e819dda356034f097a6e520e192e158630d6ebcd6edf35961d9868dbbf99255e97234e3c41d468c7b1a225d843abf70d0688381f46da144aa45fabe763e887a670831f844a3867cd3a2921bd275178985622c4fc0540ca3d2574ccddb0992b53e7716eb1d7c92c6be2022f14bf68543fe8149f3fc0ee2e9374e7bd5225622e8f35b4b41a244253736d447febfee9575f98bb2cc370f714485c5fc5ddb785a5fe55d022e75d5fcfcf09b1287f580a860d03c8d2fa4a5de87d9f56b5644209805c61d4b4415dcd71b4e97f802dfd5d60acaf49e7872b3280c301d76bf39c4390723778cf31b80319e948ad8b7da2984e7395fb0ae8fbb0183692d7832ec38f80ceed3b8caeedb9fe463cc8e16f9ac50e139d6c541f72b55ed51fb92abd808f453d34af516eacb831f49512cc72dabc6bfbcde8efd93e95d751ec26bc4af76eb9450c0872aab95f49ff69fe074da673eb3c6ff28d48c5085578639e185b7fa4df87bf247945cbdb7e4681355d5c36b763ec54138dcf19e74321344aec55871ff545cc3cc836ff9d62c65cd510f0cca9943b1e4ecd81101cf022ddfd7e3e609f1183623f01e7d2700dd625b0c781f81274634c48b073e000b910064abd4cd212853533b9712eda61542dbab88554b497f8533550d59be0f18976e59a27fcc106bd36cdcbe93ecdc92588288a043c1ba996b73f4df2e934eac749aafc81914da297c4852b3f4e2beaa5fe134c4e5240d84bddd864913ee59be547c78c6e4dc495ededd981e97bf6437cb88d8f5b34b675bbcf07372af1b5fe9c4e2944fd7e15e85a99b7149c1c7eaa680919b6958ecc569ea7d19e76c820e9aeb1b7f916620778b3df37059578da8d8df69b940b5b84d11a60a35e9bec9eaa708492fcd333d0584435146a29cf2987e5bfeb3fd44548fc8b1f15477aa8f004c2f2f3a8552dfe2a691ebd19e6786da5c851f9ebb3083c4da27bcad3338ee61f2145a18951db4fa729e8d3cf1b52bd6538982422196bfac0cb601d0d54057f1f89b59377e85ea9dd796d6181a23744f555a286a80b8df454d06679da9ed2f16533978b4ea26ca74f3c36a6adafa4d253cfffcce4563e936fa51aae9ef4b95e935bd2dc791ee2bc51f28521e4c51fc867fcfa70db703c750ba2f009c3143a2fd0a63b9551caa3cb90d562b749cbe3cc6b8bf4e6ae0932f949c53be5e1f240834696f14d3d8c99519649591ac3b86b4ca1ad05582aa26c278424d516544cc8f3d6ff78c81fe0172865a971cdc2e34ec9946426bc9bb8dce8cbf9ad7515f9fc30f005f267e56701fc0d34397e3214e9c682025ea6adbe454d693bb749a3050b1f18d665ae6df1b42ab548e5574d9ff63f570dd287e3ad60c2733d4491fea889bbd362961c51bb3b103900fdf2027f7170cae464b486f1438f0085231fd8f3d664c80dca6b4287ba08bc7d7242c6dc9787a217eda280bf8a21795d9c474504f45357f0fa404d3e2e5bca1e5929f66dc5bf01967debc0ca6a209f831f1603a89ab336e0e9c10d4f4b9635daacb43824d3e2b847a4ce64da9e24fe72fda4b5b926686a9344a9fe6dd119f7c4c295f346e2b711bffa3c72fd45896cfd99aff673b98ba4e1766d0023aabdcebe3f345149a56c8a4cd2b6c129fd43351a028e4858f431432aa54b10dc568667b4e4fe36bb61578f3a4dc48f5923e7d5c0a1a6df4d97e94c9bc99592bdf224d70f2141a685ff7f45c86499af059c1b445d3fed29bc3649bd14f32b2ce4ce858612a0ae69613167349f100847ef13a44d0d89693b4b78d8aadcf4d49288d4f2455167ade93d1a5b974c8e196c8b0a7f998426ba6b3d6c03e0df46c5981ccfb23933fc271ebe83d341cbf869e2efc8cffa4233e306d9110f9a32317cc0b1e2b8a7e3360c75322212fa2be127995bf61337f17230f5390780e9828597c30db06ab9649a0627267bfaf7376840c9c0044554a8cc141897d931b89c276f051de68818643eff90ac3a8098c7f5796bd2ad6c219c37bb5fbc200bd83bc8f2af1fec796fe37b7fbaf000570f7586ab2653b0bd68f6fdde362067a7c1348faa2818c9449fd8a6d9fd602fc61f247894c3d0ff817ddbf3e247b98501738d5c7cccbc57ba124e3c6cbcdc164eb1820a0e259a812c5609b3b0a904ae9e8c979cacd5dcbe17f0131bf1ccb89e085515421f71c0bf5ae6146c4b918274d6b89ec04d9f1ce291ffc0f4cfbdc249ca96bed942cb72a9b8d358ccbde6522c3365ee8927f8ce7c526ad36f1d77846399de60f7b6a52dd5bbd522e285943bc9a909dc7ec39251d8e971583ad02fa3dc500aa869c8759d711fae7947cbf5b0195d58b7405e58d4ac9e54a58f9a621a8b51bee3f8abd9d4b6c226e48d92c3420cc7d3303b078715b9d567dffd7d3bac2b5a57c9432112b907e1796deccce0cd4042694958cd658e9d3c04546a9982de3eb37d0ed50a0ebb29f133c0501fb838d62ed0df0d838242911390f4d43f044a15a7715c255ef19b4d5b11dd4731f274707d777b8632515559867a4aa3f003ac3939aa6e30aba14664c99fdfd8934db73bd06294665d6e32f90d5c83e838d7ab72010df44e05d0e5286d561c2a4f81eb587a4b6b254fc8d5daead403eaf3764b89b764c7dd731d1be3174e18b11dd3b6b4e98519a778d6c0e1f499c310af93b1560f96e10efcd3a9084e59c4ff47a0c5c4c7ecfc4e6d589bd6e08bd06e942d1247b88121e50047d301f4a869be59b34955c715bd446dc67eebf193d8fe00d76b23db2ecfc3dcb6a06d056725758f33951c2b5fa120d47b484635e1f2d8020bef59a16cc7421160009ed3b6069e479a824b11893222ff60ed1980ca3bf88de8ce972a644a752163af20b36d943b41970aac4b850a443d9f18b514bb3e03b67d033da77b25fb4f1c489db95b2f78c9665218274e62c98273301bde352ae86b846ccd821885d3361f1d5afc13c1b1636a997ca26dea1b334bb78946fbac6569fd69014c9bf5ab713a2ee8f6a72bc6bf10190258c6f48bd0b395be267414097baefb1456aa0a0884cb33c76a123667ea435cd0de4dc413650c0538ed978e291aa24e93559ece861b675275721f926ecd381c53dfe7291b8cf22f747f5c55036bf465aa4f153cf1624a574b5c080c4ca682d1f42b91a4e82b9511c5d275eec167cf49a3a89450731350eae2c9e5f309ea1f8e68472d3a49831c5c4b4362d8f61aeaeec632b9706983da569b85395823ea55e93b23bfcb64f684a9f4a68aff2c93b86e7cdb58ef623e5d59eed84f2b3eed20a4de1132bd2f812b61efa9b17aa25927e42dbab8c21f4af249905dc0166af99fd611c43607654c01cfa46592c3d9cd0b0776da70f86a1b55b9c06006691ad3705177fe1e6c2cebda66f941eaf97364130787a06b2a214fa3bb038367313e6131498a62b0b30ba56edcbe7a58fce7608310a0228537181fb19ab602a5e9372fcf7492f1ed0beb70be36f0f757d0df2cbe73332dd7ac05d60b2e83e8fd87019ff6bc3d4fb512dfcda6a3e29e1c01fddd37c6ab6c11929cdb86df09441e2d4b0f80d6576b0570ef9843a7607d7b970cb8a8e99314effcfc1f0e913920ca0bdbaafb2234d1a77128a2838d20c4656451b5e8d72ea1efd414b08c15ef9306abc123d56037e1f59bd27d63aa88be5ebe28245c80ca9e0be4c4011407bb4120b9717fab695371e21ed13aa01ab717fad00575a9d85478f1fc7d53302e939716485f3b852d91afb3564021c1ee7a8ad9bf20d7433c16a01451fe4e1e2f6dfd1aecf77bd9303c54ac2fdea612fb2c87df6c34342685a0f03ae21b19748a15cf1a60e3712458a9bf1d2d3e04d2f414b2451f1813f8592898c1c5a36a73d71271aea66e10ec13c2dd490339e5dbbce6f3b16b3b35fbe08160b5be033603f72e3f3ff5aca86746f7250e9a359827d0ca7618ec524c00d73bcd4fae39ba28e87c35ffcf4463af0e48a70c86bcf132aec94fda1ea17caa02cfa703aecf748c6c6e5c1c5d169fe95aeb9a6ea012705c5b01a6c6973a2725bcbe9f9ef40de926702c21d7283979ae1c8b585f3e0004fd8801deba48b98f0262a3c550d27c988f26f10a49267a3d9a85b3c409b50857c67b3ece0331cef7532c133de6e7f6b54a4853698a3244fc6fd15c596ea05458c4424c20b6339c0e744852463beb3ec3cfcf8bbf65d08899dd74d6e3a556a7049a7bd61d698a17b34b30e9941b71350a5be9e9e8e0089a4874e5342849590637b707437f77ff172b712ebd9a9ac1b6e76b2fd33a49f3d36f50497f46c6f2d3a085b7eb0563149fb8f2f39c047f50525ff854b14558bc8f7c8beac426c3dcac538f75fdf4fd49aac42969cfb20585bff065ae5ef60945eab906e742e1e749223590c50118e8359a90a4843de23a1c823dee772648ae06f35ab654effde4ad6c34ceaf25eed5b0a18a505b3cfc207e0113d5518792cf40e9b3aeec4c87d9a17a4e6dc5f2c695526feccd08f5ab9ddf88175342fdbfe98ae206397a3643cbfd14625dc5c82c6298ccd7664f08ce5dfe1a0301287fc001a00c2bf659cb177ff56a62034075ca4aa4f7e8c1be7c628f9d15708de52f91419e873f90f21834047609445f15d252341e36ef057beafd8701d2f319c25614864faaf46ee3f5e36b4fdebc127eda0ca9ce6ed22a9d416457931fd9b0740d9683c1204b16bfb6df57cbe29e7256f34cc3ee19c5d577462ebaa2b4ec7ee3176e57a3f79aa277113d2739a2956160696327ab0b9e3db0ced2658c31473838a29150bcf4ac3de0d46d3aea6c779f907a3fb76e207bdcee02b7d90c1b7204b7c98252606c46a9551d641a7a7140ac45ea398037035e9423c7f63ff7e69e9bb627ad9024f3f8c668bfe5139e811a250a8841c1f7a3ea54a61663c120d0beb3d3adf70d2cd9828adefebf536f0b17d92069393652253f4435fb5a598678de9812c439c4a0ade84407b092fec5efa833da4acd19d7ad43964f418c99c1a5bc26e5508c67f092c04a5535c09bb73407a65565d6ac5d77d3ff6a71fc086281421ee787941473c0b72c2209baecde9ef437fe3754b3765c5ebecbe225afe368d811e41ab8ca75f6cf45f7f1264defee12f268375cdff5d336b63df800e88bb686172b18b9ce4b02f1121e44ec7496413da8a1c32ec09692bd3c2a3f826a9eefd534112cb1e8fdde01cc3319f7151e3dd276c948be81cadd2baba98d7dbf4397cb6ddd4c7b31a3d95eb7f125ed79e15c4c30299514baf3cf2881db7711b8d7af60704e76ee3d86ccbbd0aa86c2f308b8ab89f534b9c2b3a1546b3c9821a0c6b9f616f256421b345d25bb84e5fed0c509a52e1f0796e510601e794019e1c3332134f19c477e4888756a274fd8bb63c79fbf5c780c0b1b1fe937200857d7d0b0d5603f6f1d1b3a0ff9d036b237d2f1bdcaba86d10304456c8c696ea600a9f7c4dbeccde3d115b01a70003ed688814b3969775446edef9fc0c72c1296ebf7e4693ba15aebafddd53b77e0e3804fe4b822196180b8a6d9ed5bce10bacd1403ee2767ba6fca2d776f862446b5dc5fe3897bd8a77ce3eab32eafb75ec6fec7734e476cea87adc2b97e83afedd43cfaf2a624cbb5d5a047d967d53ecf8e72f8adf3c0f24307cb46a16af5df7e47b7107a1531cf92ba131aa35da4ae08877bda6a76249f8f57ad0ea0f9f6115cf2aaae61ffef87a64081db7a1575c5ddedf1629cdbaa784dbf9392eba55e6ee4fb8e52bef936fcdeeb66873fe99328b445719ad443ee1df5d82d6526361e09ec9d0ab477b1e46f6fc23bf333f58514e346168b48d1985acb25e57f74ddf8eaffb148d2dc8d8fe02016a81475b0c29c8cdd9e28b2532892c4b39076106c96fd3e019291b4454d04ec10b2971444d6b66099e958baa1108e46459c9280763fddcd814ba82ab527abb7d5768d9682c1374750e942b9dee5eabdf79abf8451d61314882fbd3013048800148390a072afc8ed947b3ea74937f2b22e13cd03ca7c9751a2d21dbe4d81d0875324fcc6a2583b5bebb87e99d16c80b91d76a346d06e9dd494d762bd9b1d742cd0bbd9a4de5c420da980007ac55cbd5c46640e3ac3bcf084dfe5ced8ff5a11fd807e6c5ee8fe32329a24d3ddaf560dcfa4648314fdc14db47f8d6534cedef625f421847f9226d83b3dddea5b41470e67ade0459c15bb726023b6d27467c5a08044a14812ea24c4e68000bb0bfc90cda986e7c81f6ff341526efac4241e82f6430b430a43e9c4114f7eec04126071855707fe8d1e2787167ddf3a2b8d30f95f38d1b3a2405ce83768780a0648b330dfac7d7c1426f7564103fddc01f370c6b93e266c89104335521b28688187286103eac0168283c11af57ac7f0d05d4f9336c1a30009d860851b8cec27587266059f21478e7ef2752ccacd71705f951d6b55b3afad1d0ebc583be05ee6e0f6c5e756596efdcbc83059f6bb593beaa91a490a556e78cde7e6f3821de41e7324057908131f0c7f37e2837a6cc0f1321ce62b93e399b0b4a79062024783a8446c9b9427349d90c7a4d5ba6722bd48628c30d159948f0f93fff844650a00f6bda9b10faed50f3940f38c5968ab767e80bf4ac572c8397842e8efdbbee5939f6a4445813ed3c57c9b1fd9cd7dd4a6dc40d109194058129e7cc3f7e0487fd2f556fffa898904c8866abb30d66d2c1c6bbb3d042ad8fd9fbe3bb093b2141ce2e4c3c7db1f15859f769b3ab8929e852a3fcde1f6dcd25fd8174ffc71c42f7a64996c65dfdb0c12ea543106fbe9a5bdef74604e103706097a66b8adceb20961602b87a2702ec0b193f22756488cb3bda03d988795b2392e1ee0730eb182142534ee7f4c3208c63aeb157e932271bd934ca5fbd56462cffc8a9f3e6b3d99d8e2d8871304111f2d1c93f26e6b5df35219e5e992c51b5df47ef739bb08b44271059c9dc1e1944d7ac8f6c05eb919aa5a6aa7da1c1b90e8f0bbb104652d26d8a8b5e2fff42ff63930635bb12fd1ad614cfd2501bd4acb786378759292bbf8282711c45aba70d535e33b5ce634fd9beb6d7f1d0b1fbd32688186d4e6f8555236544a2661050973b0ecc043c4d63905dd40189755b2359905ef140aba96ceb5de166187fd0f0872f9a90e39cacd0bdf3a9b560c699a0968b3f092f3284f4ded68f2fb90fe02b737a4aef55cda3411ff463924dac13fa10a7b904656337b0c4b94d3107e917335138b4ffd5f1ab7f54292bcc733fd69d3ae4b34e0e08fd1f5a0d305890b9ac16d87cd7fc97e4cf944e25695f0fb619dfeb5e8acae19827707c3f54f0762da943d8dbea354b23cfe5fe09e2afbf9e21c987e46da2468044a3a5cde33d290666d4a3aac527b0a71c905e9219ab03f0c29d6e54d3422c4124d0ea2398f7632bd71ba93209bbaea4fd2a79585c3c21d631f045e57fbfdca0130e43926801072279cc31ec402215ee3e5e757c17e78f261083211705f6dde460d6a5c02bd5131e513ad7d344e7b55aedd78dfd52dfd1f9abcddc0e673e358976b0c71c50ac2a36cbbfcc11ca367ee9b1e452caee62117eef0da47549af53b89c429eb9f3f79acbad5844ff3dde317abbe534ea297792e3513801dc8248d2cb8f9d1a92badeb6af91a299dd29fa42c5d1d227b03d4a747e54c31b9f3d61f3b9ad05155a30261e8c7d6323591c315b165e3fbb683abf854a30dba09b5e5e5966b010bde007c1b491a70218b8080dffaaf21815aa7cdfa0ed109dd9fa5c5cb2e11600e405a3774e45ca56ea2fd3845d134f3d6a020c5b7840735199a45093ebb8c7f8cb2a242525bff4e597d581d1a705584736b7401a21f4f8715d2b6e9f1323abc953dde8e2053e1a53a0c07f892b06289274fe690d42359698dc1c96fc18e1ce600eb76a57aeb872831ef5978b5e05377c02719a4e936572dbab0c175dc8fbcad4b862bfe1207ebd76b3fcd0663eaf52d1c6700987a012336b3e832d6ee2cdfeb82b428e269b0325f92e5b7f3a5cb5fccc139a2bacb72eacb15ef991e9815ed4c8d5f89ac442a0c37d528748aceafd7e37fa4721feb0f523b350c4784d8a6da7fd1b6d18ebce4dd39f9b15660db", "spend_index": [ 0, 1, 441925001, 4294967295 ], "result": [ "61fed38368a342a1336624b783391c389a388c8cdc13dbffd4b6cb1d14d5f663", "5a7ee9baa9110eaa3059128e189c6ae509ac87cf1ff8e1d367c04a2dbb969e57", "b54fa08173a4158b4e4f070ec71a9f6c0ab419375a8973fafe5f60233881d668", "30b58522d3d002c2183b16d31e615a7e236d041534f9348506841732136ea676" ] }, { "desc": { "Inputs": 6, "Outputs": 10, "Witness": true, "Version": -185036123, "scriptSigs": false }, "hex_tx": "a592f8f4000106e8bb51a700000000000000000000000000000000000000000000000000000000708d7cf40065e4b9d0c8ef8fb300000000000000000000000000000000000000000000000000000000c71111ef002814037f453325a5000000000000000000000000000000000000000000000000000000001ffe84d400740f76d220e3e8bf0000000000000000000000000000000000000000000000000000000029e6fc760068e41b6d3a60b1f500000000000000000000000000000000000000000000000000000000b93bee93008c720b4adf815472000000000000000000000000000000000000000000000000000000000f7d388900619856160a2508eb4263293469c87e673a485139c7e465bcce5f1fea90e7b138534b906028798e78f92bf2a148c43ed94759ab86113a6be774baee58de044d18b2835257c627292f7b6d561b14377ce45a7b0a12fed1a76edf981cc235366749e396363bde8211ab5b80ee9601d1d433822b04500dd6c32d14e368deedaf2f51a41eb8ed771488d77beaed08a70e41d25f72d5e33bc8cf26a5b023935750e26d1a87063ad1213a796793be36ea06117b39ba7ca3863f5897455a80c2a9cd5f6ff415186855ecc867b986bee4c71d70fd0e64e996b72715c71f9d7032f163c81dcacfaaea94cfdf0b0580941468687583017c3d656772be4b5ac32abaf5858faeb566e3264c009fdca65083a4103ad9c694c683713d6e70186c8749b2fcb35e1eedd7c087bfd5f3409a8266538f1531a52bd0d0cae3c8390022a5a95e85145d4a8b01a1818450b6925f942282b956a64dd577367381090753e13e7cb2eb4c3188b92881270282d6c755063854a620e90d41ba317fd49710fbb2ba7e895e715a544dc09317995d9e498ec7b22f35b3cc100ed5249a3bc0c0a0e73a37057d531bc869310b647e75cbee6f7a85032dfe60c882f84ee1a6bbcf97c5a739292cbc5e0978875d89f6dbfbfb2d29e9d4cc5019a5c07767a583100f8027648e9babc85d50db2e9dfd881326802fcb616b3b5e65f92fbb505951ff066dba1bebf9c6fe78c182950a5ce2c366741b00e42491d025db7af388ce99c304f629e97934aa96c807944eca1a07bd49ee8fba88fa023f99017f418a20fa297647308b556e9e7840724b2643d16785ba345362229af335bc23649c13a19110342169229061ecb8b2a9b232aafe35bf87482e9efbb9909da3fab76ed83f968a898464c6ddc595cf7a7ac802a23f70e6b5efea1a5b3bf0c3c0ab7afbeaf577984126cd9943f922601da4973dab58d17fff67a95551e95c2e62fa13a9b8cea640d6c26a28781db18f5444762975955d52dc16ff4b427603f86d581ab40df1caa10bfcbfc4dc8a416ded825a724af5cc4d3f9c1f7391a187a6ebebf61b8d5c02192dfe9bdfb46ea4818d98cbf73d11958d24949cf6b646038ca369d9768f634332578c67ea500bd6b0e76ba43a072f582613a0ab6ea413da30a1b1f544a1dc4304451dd8e01fe38ce9dbaaa5f372274f16d0ba26f9ed4fba285b341ec86da0bd79ae04455ebd2e94e4a2387d46dca72cebc7f92bf194dfb9ab31182c1d0511288463dfca0545a8ef6c02c600ab0cf51d018d780245adaa303f222098e7839e5c174f1260a9dd3edea1d71ce9012e60f2b7dd66c010b6e75fb7bd5de8b79a853f2834cc827ce248c377ca91973fc6514ebff8eea7188b05b36f5cd36ba6124c36e94ad816afdbf19e32f7d5c0959bb617c70ded54a69e1db94d6d006f88aa9cc5f30ebe39dbdb8ff24ac67284dbefbefc3ed7c1861f4b04169d453e4b6ab7cc6fecc83631b2faef2f11ec45b749c81d5bc69cd40291d68aabdb6fd91df9180070004a03696d7963dada036e07f16e2e737a7b16b1e6f7012d399d59b91f19455339ea675703128911f39dad30e14b82947e3a7d329bd40fa08f2b807e5a1d8e1e521479cbbab88e684a7f1c4328a46c5012bdc7b55008d5e12ca1d0b2e996a4caec0becbf8ca2a1b69d767b610e791071e4c1a338002a383ced4c092b0b67ae2caf2fca7b57a06bdd6ef17d9f587362823695d6105360245294e53d2dfec39d4e29ddb7eac0235ecc41531c0b8a7ec0a7311fe2b6f3e45a0f7c65afa43471c89f0b73cf419d469914720d7ed4a30ad43c7e59b22e4c60265b29a8fd2b5ccf83b31f4eee6fc9935ca18ffeea7b7ece9361a6a353e44988f14e3ae548e61dfc8fb6756c5d5e5349b021820a1a45390b4d81b0aba648ae282da6e7d38f1c6b358c7a310d67dcbaf3febf3b6aa7f7065404c9a1520b2ba52c4d66c309ab1d93f3c29966ea72e779c60a0402fd5a58984ea80b8934b0837281a5c7c821ffa2fe84eb683557c2aa26f113adda1f8bdf6b3dd0f26299795bad6930fabb06292c50f1856ef520f7110fe8307946483ac4ce0a26c80048f4ba48022365925ea34fd6e87373481f83fe30bae83a1ab3a830d23360defe7cd1b26a40aa38ec40f82e22f21233055af6739efb49f6fcc59143a22f0d8c4ba7fb4eb6bf9f9d742ba20c84a2124fd41b5f9988a2579e0b337e17e8cedb9d6b633557961f84005a365da0a71b15b272cc1c3ca14f542b1e0ea0cdd0eea992f5dbbd2776b798c050a383e3d20fbf367656f15cdb45194bb8795619ebcd1345104aa9160392ccfa4cf5d961075f0299bfe063ad6cbd027d64a889ecca40c3ed47dd19f12f5baa5aced2942b80e6704ac877a3018be07c0f7b567017a0b041674e6c0c677f475442353417390080dd4bd88ef7e559afc7f7ade37b3a0b6d00bd296c70be73a74120ec94c0df09f139768c526b1812b25b1ba1889a81b35804c3b6dd591a020b163f35ac2b4e23e325350e7c41724578e2902ead93425874a6a7866afbeb94cc08aaa4dcaf4abc6c2f7faad48afed0c0ce1a46fb61c894954d8ba1a880744943f9648952e10a23b3f694435af62572bfdd43a1346e8a728664280d30354a11530848dfa565984e193bf2f80e5541c5c4ea71b63e731367af2d1d23c88c3d6dccef78ca0e80733260b125affdbc83c062c46cbc9f1187711d73ff98e0cb9e1c6cb2dc7453cb73186a40b63b95d284a326098513dc6ed550c582f94af981c735439f4fa7b52dd9d05d1b0cc4faaaf30ad277d9bba88de0db5f10cf6ea9d407f19f6e5d742967333c80b5043d972d6e3a21b650a54e68118da346fa78f4811d3b4d7891286558d239534e9127bc9e920dfb5da93f949ab693cc848825e076d9f8f7726196b87e133b3e8085b2a6b38c5b1c840d3efc6f512d64c0218ad1faa5c749cb565aee02fd5d0166df4262f22cf93019bcfdf0ae93f18e3afd615f902b0844ad0e168fc77056c0b636109b94d69d12cf284dbb992aace32c9a32c0bbe5ec5380fa143c8c123282a80c543222df4e22bced32c1b7890a5fb2a67efd5027966d6d68e055c43d0c2c0634906feaa9eadb0b2e0fe6d91a5bca320bd8273cc15db9e0f7dba60c6e8bc2b77a1d70825af39fd0052a6e6c8ce373d3b5e71a8b60a3ed1018cd34de29f2cace3d0157fb0fce42ece8624e72d86df89e8ac9eed176f41db7e729e5912cff3cd81ee07916771505a1890b8d7bc997f2ec973aabafa130b2c5be17c28a13cce96b29bc991b088ceab221ee920b84c2a5cd755019628fd205afe3cafbbbcf42ce72a1242535ec9b100d3603fce9dc2e72febc65c03625eaff0e91b76ea8cac0ebf55782ec1f10c7c40cc2659ed91e1e7d3f30b1e3f440ab8fbeeee9d236a116019ce6aecc8c48bf9fe9c03a210762f8639936c71a65662f269acf39426edd58d2aac43a771bc9e246c283fec3607309ac425a1cbf9f8ed292d015ba9622ace377d1b5c6e86d9a11423541caa1c63bb362bf5ada5143523e9610e8d61019005c4b8727dd9d92987a1dce4ccf5fba3ba3490a374e86eb8ae296dc9166f733d87f6923a3eed1230a01dd7f2083f1cb704e0755d1c1a5bd97799c9cebfe1ba928427fc12a0a67ee5dff4b1470bdd431900bbac2b7da6e07f6b29bbf10c704b36bbc79edc4339ad4868c0fe62170882ec0da64384f6935648542befa1f2204414afbfd854141090f51b927a8551fc5e949b35d37c319e812e89de5ebaf2c03e635389a5e37546006abd699a42ca3c6120af0f0a24cdcf60d735849594a6aeb3899a51c37afd9c5684032d22df98124733078f8a1f327ffafa2e9f8a142a8d8df4b9de5b70bf88706e78525cda73e190d6f8ce061353a15fb888cf976abbb993ecf7d7c4a8a066bc0c64610f24aaef64bcbe65220b2069134489eb7562aeb7af7dbbfccb87ad43a363bf2e79ec2b0f7c117fd0bad18668e91c6d98ab2616848f371b54663d3903fd26f5ebe9c63d034beb49ebebcc6c0493c8dd91ccd5e59fc428ae437e65f8790f4b48096e2d381a39f8332cdb77d1996451b4fc356a3380f41a1009b6aa5b22d73993fdb373a7bb25903bc6b608effadfd557c4101e6e9362d77e94f641742d2b0f209f4ae631531bc0b1a0597a166f102b64311b477e9bc44aed12f32751ce27a31e0d8723c9a776a61f30817e6c4a4f8cefc00c1c67f68e93b0d52f5f714968b5485bf4b3b0b53a9660fb8fe1aee1c739cdd558773b369894ffb841f16333fe04133e53957ca1b69ec84a0624bbca7aed95dd752871eb76a371a86a532714a99ff10cd593bee078efafbc1e96dfdb8f79b9529ce2835848b84f2cc370827616fa756cbdf59a22bdac3d7d18a5fbe0408c74b0f37ebc8fc00bc4fc5046fd9105bf8dbd6da4f5b8b6fd569e183b67c397e3cfd8a65713cb44eff2de2842755410381344b9f3a8e23deb6d9ba8898699806185f3d978d56abfea986178ba3269241a922b48e1868767a1ee86ac04b188c1102c11aad73997a4dba08ce0ab3d63d71d7bf04876047b7f286c751addb76ae409c4ea330d6eeccb6f4432acc38a1cc059aaa4c587847ad530b43bd791ac68c29a5e428e93b15a43909456b6fa10292ee5a4c532d7dc5e7554f7b467849a935ffcacf99f8d6fd650111d53e07e199961d5088b46450a9f6ce448a93de8caaf1058f65a6613bbedf7ae9cd22aa28a3140c4cc18b73fa4c3bf92f92561af4c19f1635976d1fc239405b2068328e3431214462385b9bc5c710025f06759758dc3d6ff1b62d4e397c7107e1405d6cbbca13a352ce7e04e918bd6bf4f0fbe9b394673cd98aa55d93eb6d11b649e58a5aa5c223650d1024c94fed3d0b9efd48dd4da24dfdbe5c952c9b1d80e057e3efeb51b609d3e1422898db4a8ec004ff2c38104ba42d3584e0915fe6a2cbcec85ebf8939ab11ba4be91b35ba6ff694dc45d4aa7094a86ada6e5f5a522902f0a134e61b5f5f7daae5936a9c38d85f29df0e1a77323308669ec947f7237ff4053160ba6d170330f726a7b2f59dbc1680d401bc9dc7b29640ba834904d6f1b293f5989f2d65611addb03e539d62c294d184995600f5d369de172fcedbb9ea34ae61b31f4d7832ec575fceec2ea685d272a854507d2185fd25cc96250869d6908901c5c6fd92012ccfbe6ed1a8fac96f7331cd08635e6c3e73338876181d3efee51741760358df9487da9cdccd382dc0567750bd7774bca526b1720246bfd8aa992289459aa5e95ee0b45743ecbe1fa8b302a7e403cf7644e174634e15656c343de781410b2b7dbd0e37c6b93bb709b161159887c287739a57d4ee08b9a11083463a8d344e272b80ad6cdb8626901d5b1b0ce41d73a4b107585d13f28de8f9891a799085c826ed2ad8d7bb78c15e1de032cd25c772e63e9695cc23d4877881f73148cdc8161c287478665eeaaa23113a07887f69efc146ffd7dbdbbf9a3bcadfa7c64fa293f4d535550e8419c8bc4192fb6c5dce42aa6dc9c67c0e967af4438390f0e972371a5216c0253863f34c6c4e631b522ffa1889f4c38017e0b23c3fd63ecdf486ea34f1fe019a40a254277c4ebaef0ba2362e25fbe7f806c7c227085aa6231932cf303a87658fa7a4c001f0d4e46a5edf05972c2bb6bfd2f1501837135e8f8b6c2e079936002ded1a010ea9f171b622d3ff68e234e20274ec550d02acbaf5fbfac2b737a8ac6023ab533dae8ec9bd8401aa0d0b2fba000001fd2f01404141e579ee903e56f1289243287c5dd84e17d7b55a303eb34c2797bcdfd22c36f435bf8812771181ece68d6e5d6243b8668e54b86788aa5649a7e233da4905bc311a5915019b062e61f0cbe3e90a920d2f0affe0dceb8f275ea37b006e3f784c1abda9cb69d750b29bdce86cfe03a649d2f8236846936d3394ee53a8b5a73e4af97ad20fde17b4d63058c012b39b0b0469da5a2d0ce8f7f9c5d4f65f3f8ea0a8fbbb8b4a9f6f156ebc54e2860c82ec59879f3704f25bfee0866f4d68c6dad93119a23f167d21724ed0bb22211f26c055cdabdb3f19a74550bb65f405bb1209b341d0b5b5287eb8a5a2c6c0908b39a4755bd65891ce628fc900df05cbea37713ee7347e24cd8e89c16bbcf87f9226e4007342a2b969acd20e8e49988443fb8edec541aca26f9b7ad5a2e38b385f266abbb711", "spend_index": [ 0, 1, 1289772662, 4294967295 ], "result": [ "c971010563dc437bf26f5b6a07a3113fd9784b8725d9d2188ec91c1f264a52d2", "a38937f3366efcff64e1d6bdb117038a18aa143fbb2e5b86752244913dad4faf", "89e143275f8f32676495cabb322f8fcc10acc1a35b1197c168eb54e1fbb6c982", "85affd74d62d7d0451005be0147e1e1a0b5f9af8a53352b9a0973ae4421abc5e" ] }, { "desc": { "Inputs": 7, "Outputs": 10, "Witness": true, "Version": 632683292, "scriptSigs": true }, "hex_tx": "1cfbb52500010740e8f8f7000000000000000000000000000000000000000000000000000000002503d248e30e77076ace70e26fcd219b9b6bfb7da2fe31a7fe80640b536b6f84e2946e7d0cb86e3ec469ec52bfb084fa3c79ba3f1a27234354742a68a78b7ef9f8602429e9e7f04490be0dde782835638b16df8dc7735753dfec0b66ad9af204ffc6a7fe4ae94c987117a1b7002f666ff18401727e0943f61b7218d48433deb61571c2df7b4b3166339a78bc8e6a59decbb68af1272b44e4bc4a8c1795fed1f9090c50f78587e90c494b1f6a8e3b3f6cd8eeb23d2390dc0ed7c70ec38d0fe8b33eea242ed0d8f349f8c5dd479d3d21bf4f5b7331b2f662ffdd06d44d17fe30fe8c22e11cfc3e525beec6b625d48b2a9200000000000000000000000000000000000000000000000000000000cc0029c83596530dad7556553e8288c54663c9f586851157d1b7895f5de0cfd012e97f28eb4e1c704b641a5bcaae6ec5cdfb97a4b4b655bc5f6232e2435f8f013a7f00000000000000000000000000000000000000000000000000000000a25ce8dae8d0bd30cc050c5ec668359b7bfff30586601d75650a44148724413213039fdca7c5efe0e9ea35920f8cfd55dee485edf867b21670ec04132cb56109bf31881a792d5c668f476fbc790f1e2869fc256a2d5ade656975f973d90c7dbd89d0b873770407aca7cb1268117a62fa4436934f7ea9495ba52cedf6d3512ab53f9f98f030160e9bed83005f47e366be298218cccff6524f3eb2e082ab64f8762e8202497c5d307f3fd5e36a6ea8ed6afbdff9ebed70578447ef094eb798065cbe67f05182b086e26d08a52a69fe7b289b579e7a4839d49ca250cb05f82bb0374cff7e40866caf731abdf99f9612b4c2f798adb808000000000000000000000000000000000000000000000000000000003646d723007c5c6fed6e889a6c00000000000000000000000000000000000000000000000000000000259275d60b532873914391bcd42b2b4cc3859e21fc8f86ec000000000000000000000000000000000000000000000000000000006554e6f9fdce01cde0bf967002bda3fe15efb88cb1e3eaf33ce78d4d9ba8fb3596f871af10a8a629642cbf2f4554477ebd643352b11bd2aff04071fc580d206ca4a61c1f0f0d95e4a04954363f4c4722eafc091bb96d34f30467c4f1dfa9b11de2d042f028d73f74afe9588f852e196b84d236d0a7fcb26ea5674b1070dc64cbf69cc9afe692232b0758b250eeed4cbdbd687e51876fc4b029b27bbb0ec3c17f64b85ddc5e58972d7e352a5299c1133c94004431b09706bc6a1d036e8b204d7b77895d718d57c5eda7311dac7643d1c2ac235bda874b019f6c83ae637225928bf46bbf54173a5c5612e61d956075c3024511be9f51f08f65a9d83b2f2f2080a036fe744e35e727af51460ce75fa1b5e8d4d502e7143e850921b7520dc6f1b289093c83225618fb6eddbafb041e7236c1fdb8f921bf081802482f717d7ec5eacf0ffdac78eb4dbfc3f34ee84163f2482671f82acb18e7315f08c34967e541d63e279c796a2345b75d4166a0298ac47a2c4ecae9bea1dd47a7f406eac66ca3a42c6a5542c1340f943ff61ea33814174fac06f5341ce7e6a3dddad8b92ee3bd88e78ccb5bd5a7d20c72dba952614f853af114976d00eea017bf408acf76ceb48884903e6f09dcc115fb8149e3198366721fa6a6a9bc854e53a405bae316960000000000000000000000000000000000000000000000000000000045c5aa5ffdb20165f92f6a5c7c09ead853a6d6facd976acd79bfd6f5f0422a051db97502c31654a791f1df0272fcbb102e5fce40805c15c17b0d2d6e2afc3a43e6f780994c4f599b4e203ec6c4703f7a84667bdff6a3e37dab6bb2558217e04b542ba15d12482a280122c3c821765ea73974b6f9328f25525d0d8092e932c685bff1e5dc98acec92f1a5a7a54e64639fd3e2211f7afd9b370310fcb1d8236c5c72493a378e5ccb90124150ef2d36fef47986d64ed1eeedc48bb7c165ac9ae46ac9bd1c7b7e9138cd48fb649affbeec0b85c46b5328eaebde9973a45eba938dde2e73342ee91c14022ee4d605c7ec48fabbfd84ae2a8f1394c44f1c50b5ad4130c7d88c5fec42fb71759670c72230c49cd9be5e3c3010f3345dfae932cf254f00a189edf638b4dd430dfa4297e0ee8ba504f694f59b8b4b3575366869fb949987fe0cdedf3c143a58feee268aec26f507ce5094e6a5e616bd088d94117bba64dc680458cc548fd62d89e48db5d1e8eeeb4ad5616176eef10ca0145833bd9d889ed7d7acea7092984d1e41dc2ee836b1377bf2c28f9d6ea4ce19305e5acb39070b3d1154dfc3e67dbcd9d2c3b81e4f5dfec5e682b1800db327067227066b0a42dff4e340f41924c868d2446d37bf6b0c024a357e127207787f0baffdbd93417605c2d649d8f12b68d24bb1f6e6c104e0ea524e980047184c1beed4f75b8de6a1da57a3c8872a5b7f6bd00a4f9b75bf0522a679ec3dcf3fb02f49cb84b8e689956ad27b6a68265fe0f0ff76b5ffb2afeffc6f241b7374b7acebb4d20252f0fa17f208dd45a644135c5f9561a77ec440b4008910e789152816693ccde8783f1b0af94cc9cefcd840491b33ca75931ea979324136f54edbe30eac853f730a5735ad3e0975c8e75e8f0cf44b7c648e4ca1550989a08cdc9a1239c8f93aa0920d8947f069b0431072f236b7af1ff78b369883c5e4788cb29ff9573d2b259d34cd9b644ca07ef9ed4ab30d65313eefef0b75f4d1f9a56592bb80510804a1b3b25440cfbb02f15c3f8d333411ca73625eda1c72d4b5173335f171fae4b7abf15c064c4c55c42ad8d99647313e8108c951e280a6e08f7212a3f370b7de4b0c99f4a2b9c4c2281105d75fc21057bfa36d817b62dd8977ff4fcb97297b42c63aa12ae3c7deddfa83dd9c16131d5db81ff81b0bc847efe37230355ef89e9a15ee88625d93138634d7251cfa50e801c8ec09da22b3c72bc23bd02e672fc0294484287569d22cea3cc58942cc1b74160e69d587e656f9a7ca7d42b4ac8f19fe8157151ae05503f168960f1375be6801b113bf1b0b11a413e743c2e26272a062b1cd389e531a4ea08c9ab34c52e707d732866e6ebc5a017d8d316a019cdbca19cbae476a412cedf917b72c509b03de852d86a0284e4714f3326aed6379bd7fab762257b7279a4de32b185657a615e8fab2ff3a7ac444ed21bf8c4ae53b281fe33ba3d3e74ca57f8eb54cbccc116d6c7325f82e954d74e33f350143ebec3544853bc87cf5b3227365459b2fac2d291c5d8cad2189a927a65de0325b23bf52ee21cb7857010749a4861e477c6479020f1dbb3d07e4943cb09f916a7cc5c4501d7eaa44a99764127c4c47f9e650e795596aa3c519fbaf3eb332ded4c781fc43c9e16ce1f21b4bde71b16c889ae2d9a907647ad4241e388663e5c06ae9000265d6816dd37467adc1d5a9671bdc5c1f6dec146266012b87e817e5c92bb3732a7c90f1bae3782fa4a61fd0c515a41a4791d051e3598dc30d1fea9a65771f161b4a7ca220defa0cad49fbb1d74a11563d01e0d59b3fc8a2209fd016cd395b05463ca538d972af482a6c81c1ee19be57886ce9d8d41632bb965591f5f0c8d9199d30d320f2deddd21c21d12029c0b0b3de350b40a4679830d0b849c55cab2e840992c9ac04dd915cfa2f3ece904e44575e5559cf403f1003c753f9b9eb6a383fe5e5ca813f23ae7bc0b69e0afa751634d8d46a3344b4e4feb8d89747cb1a06ca8d69dd18e22470ea7b103f37573e8722b4e0182d817ce7e12a0bdd0c33f932a4217eed288c46d697d3a0c466092da8b15677381a771cb6329bb171a42afc1b58f9c04c837dfb42c82debd37d02a4b894532e679c369ef5694b5c9252b0307bcfadf5de0cb6e5ce3b50bb4a7b5aeb2ea37512abe25b078eaa556af334717c86dcc818061401b75ad7428e45a81658af39220989ecb975df9c25601f0b6af3ae30b81ae1e008f506cbc2bd28fe58e8b4bbc0d848405394a9a5dcc8066c748cd82d9d07c654e872395058dd6d7a9cc53ce212c68215ce838a803c92e829f5c6c998078c82a0d3891fc286bfecf071d8bec2da0934f58dfc9c4253d94e1f8e3c774e6461b1050388ba268a404100f6cf2d590f2e59cc29f52451c87c6394cce83c8b04ce1ca5afb63e001bf8b99aff752f9e41b028164f21e610e59b4a6745677fc058bed3b215fcac0176ef4a425762f2b93a02d4673ae6eb51c7b967c154136664576c28c9ef153ef3035f4522cc19d880738d0efc8c30ad75fad6a7e458246a30d6fbac6f86fd911bcf8f031822253bab684da4ff67ae8d7080e90931395f3e61d70cd1db561ec3fa5d0bd046b636b9891e064e7ead4d2745ba78a3b0c09947e0661033b784153f8e3bac5d4535c4b932b492b29d1518a1deb730c1132e2ce4f6e9c9da9126407e0710c8f37d86e4836164cf35a302a412527979fcb1e17e2d56ac2124c7681313d872eb6c09365754e5cdd90b73bb832a4f2165d3801fcb0c4810d37d8f07d337de25220d01f239af918fbd3ebcfc221799323856d6f259f84f33794a149c0f994c1d0f082d217ac2ca4c08271c66f3628fc4d8910c23e2a518d553973078b6159072443955faf3ea16a00cc1a128f73e84ecfab6e7d1eb4a8518764d4a5c12a98cc54fe88288550666495923497a02904a9fb0b5c182fbbb1d9933d33452b2d05895b938bff9cd092488f796a2cd952e3daf40c85e2fe6038870d9edefbe468f1ead00a86b3be9c7fe5a028f5bdd4df57077cc826cdc55b5ca5ff5a61a46182049c7031d6411e3edd9c1ed2bd5976db20355d8a7883271f4b3b62b1d0076cf6413cd209b6c71a1e3dd4f4a0ff7eed310d4685c8b3c5c18e2c929be043acace3e4ce06a0a700fc73ffb004b99f8d3f6f19a037e99322fcc5805d6c9e0af4bda816be0a99b64daed3737d371512ac8ab0674c653b5976c44d2a6752d535d6b0d0699353b098f1a77744aab7507244eebafd5c07f75457d4415e38524eef250fc3e17f63f07c84e52295102f1ad924ece3e12a47087baf0335dae60d09c5818dce4a171763098d80bc6b17f602c148fb8106eb113f8a4624feb32b4f387f5cb9dd784f209cf0b40cd20f691d76ceb68112316ee846c5f295f0b92dc8723a21a62cbb5470bf8c6369e8d83394d12d1b9add0475355fc53c26a3fb8d852a6768ef87cdfbee42304187b1feb352b7983dc505d5b6d16a5b59dcc526e7f4f57ddf8fcafdb3786fa8ef80b829bacae1471564cfd7ca01d7506277f942d32e46453b3505c3bdd33b73fff1e824a04180b2b02fd3201e5a964f58eb9fe6d456d8687365bc025fb61e1416698426779edc304935c7c40b77e734f8a4719a1143506abfae35cc90c015427e5d8e5f711301b13715df9de0ca1aa1c9ec2793becebae862447ee50a1e87d23830d75bd18d669733863f9274bb00c06097d60af40ac4c2c8cce250a9603fc98f773f4db26572da6be8eba111157e170dd56f0095847f278cab301ea14f114d6a9154338e55e80f0e42fa53f7ab912ba0101a76d5184719f6d7b2480933fb036d840d867b1b97bd0eb17e1c0873ba84fb1ffa666e31931a6e1adeb03802e503f7ccbd2be787d762893615cefee231686d4228eb4f04c456a8177005833e5801ba4252ca667c9c731de7c0967667f01659be3cbba0cecd1f1c33609c74b4ddf04347f13d05a9e42990618249f5a73f26c2fea6d3cd6b630872d90a807bd754b5489bdc8ac377edfce91db0e5cca3a94e62cbef5d48855d6d0a74456ba4eebc6059390203cb39a7fd5b6a3d3604169e105d7a3e3c25a2f7cf1b5051381b02eb5240fae7a82e78b7b2b11650405b9e72b0a86fd81019f416ab13d09f757cd171e903464facbe3be563a6d9ed0f9f6bda71d645b87e0a295786affd5b968080fe681e1112ea7864571f1454a0f047773e87b99e366892e5c900ae9c9f4e088ac07f5a00f6da3a38e3d516a94750f3008d9843b5de26623c30148c71edda866fdaf63ee47a28860d4366fda2b9c97aa8df17a239d2bec2f5557ede90cd158a2a9d8900b297245218b1867ca9a4037a59d615a68eb04421726d1ca055f5c2664448ef25e7b0e82f2c6468f8502e5835e1081b0d84b7abf47c7747b6fbb6e981e027c1e9637d231a2fb63b30d21f182693425c3d0cde31be1737e3fb20e95b6a89a872c0a20aeb8fa1258a91911e6f036f40e1a1054f82dfb829448f5abb53e77d15a76dff6dfcd6268afc12efc5d2fa37f355f9a915c4d3098c149abea6b0db3509d8706b5400173bcd11b52c8adc65c0297897367a851b7791c301219047adc20410bb73b8bb98519495d6f91cac3ed14e5f2c4de971470c8439c61a8527be6bbc93a75123875dfcf20ed6eb9b1127bcfb17fe6a7b8c6a7fd1d01b68679e1c45625f3eb18744191f27c381f6d07d154aa5b82211b492b5df98b90a093be6cbec9b53f63bcddad8beeab48643151da8ccdad95da617f9508d99cd4f61619b3a02a3344c3633063bb32809353a63047e426e2d2ed33a076ca893f551e0ff2d912fcd3666601cbbe18db4831c113ca7626c3c3070994a0bebd64465a817e9571ae6cdf4dd0379a3f8b46e84b4c54cd9648640e58c34adfc793493bb28971d20266cd5bd3d2f2fa0fa209ab27a421778c5f78539d64ce7e4f98183573cc31811032d243b87e962a1527bee80bf5abf237c9d78aedfb338b56f9d37b251dd27e5aa10e180fa150a642bfe64b9a12aaef314c726b925cb9ea0c1b89d4545420149e224ab645aa7f91910d6697f8002fc31929c4c5d6824d34d20bfd6f01f6781fcc115c7f7c6fcb7cf0acc72b9ca8792c8e094d19255823afe740706c08863c9030f8b2dc50502833556e0833206b190ea2e22ac8bb0b9d00284c387b32c634ebfb141bcf69caa9f1b6ebcedbb8091173d8b5cb6cbac712cf8efc9bf6678ecf798f5373b4c0161240dad65755eefc28be8ffa48b9797a0332e3a3ee30d1a329ad85e062f0ea33987edb77bfcee2ae6fe719405dbc1b872a3b64652aa8501f10589a0018be1c2a783eca3e7a74b804980f08f77d8e6148691636a259b24f89a67594d127c05e55f33a104f71a6d2f29b0d0e0a5e2a2e23a2a913ac22d89c94dd216517c66b05d2bc7f51230baeea214bcfb5cfe1a1de7c3dd4f40ed42252991210679a602509306a368a1e882324aec1621b2e64603cc7169c0f0190793654c956b24f01934fb159e1ce8e01016ae65cb0643249fd905d05c0cbe8218c96ea8fbd576e48689755d761e7c691dd8098aa106a1810a8362328d8c23f56c342c772bbe521e7493cd74b5e1f087ee90302eca6fdc401b24939258bdf675b60e3cb390e5aab2435d59a0b1039215a337aa8b663651b70ebd041cfdc6a60678996cd47520550868a57694ff7213bb95877da00c12fd1d4469a405022eb1a81ca2f9c90a9631a10a419219072e9807132e9ed063093a50d949cff1b8367e703f9ac009e95367952df582cb1c61a68bfd9ea67048770e3bb3df521633bd5f9d05d8bdc29a35fab8b8989562a089bf8e2bbabb61d8ab678d3cf811b117bccc93457205a5c9aa70f903efc8206ff992c7462b814ce39c534a3c4bf1cbaa61701544e88924039eca613e5e2f3b5f5c1762e493a6f0a2c3af8d6240b32dcd533852132fe486ae07d9eb746b829b5ecdbc547a72b2d22bb926f75a0cec8a85074511e9060be7c931e3e878936abbd6342cc5fa54bdd83517e0cb4c351134f9368704798cb1faed35975aa72c499349b9f35ee9aba2c79934f5da4c4a3f631c16a41e2e672aeb602796c0ea2ed30e1b2e4c42a3c752948b95aa46730fe628e61b5b91a7cc5a76ab8026f7bc24a81095017cb6a752eb4915d5cfcbbeb828827edf21c0d9f1a029ba9a54ae322e73134a9f4160a41a7e230378c6d0bb39c9a83d8f298f121797cd9f3f1f19d40a0cd927d0ed9eb94f2c90cbd50f5c759588da5fd9b014718314f3ddbaf7a75b10210092b5d0976c521b24db0699b8020c0daf9d534b8d4ded49c28dfd3e73b6f669ab564383bcd7674305ab2308088cb59aae588b75929aedc543df0c5ac4d97fa4ed9a3ca48a8fbe7c74b935c8c383a24b4cf71c045b42f163bfebd5a2216b19c6c48e158325b79044ca640c32b8c83b85c3ad5f829563ec1ad84fd131226481aca3783a929936bcd4022f1e9664ac859d7082e938405ec57a940d037fddbb55db2c63bababc89c4946e2e15901396ebaf3a3404a73f8f274c681ca9465dc62a97655b39422562eab306d34ec12c8abebf6204b430477b9588861c3ca764d1521ce9e48e3ea632f4316cfe9891ff2b396fb44f0746ad7f33b94cfdd02aebb0d7ccf46315518a5e432154c9fa733c7049c6c06384272c2820dcd23d64f75649c4ff5575f7a86f8152eb81a9852386e3ded479db614ae321f62ff43646287d16a8dcda99fdaa324da4cec58928600a44c438fc4a762904489aa5ffe55edbca342581c23f97a1f08e17f60f0333a59ae567843813b6ec1fbe23338b11197bf309570bb7fe8f3ac921dda4947416009e1074e03fd9701c043f20920307de99e25e6df3818bd1ec8cdc450950aa4e1f6e3fd832067f83cd611f14e1071d367e1657cf5ebff715f8f8373982504bddec6358338779cd7562a5b7edb35499289fb83db7542327a3fd2bb8cf38d580906b88dbce9243053c29af1e151ebb4478b7263e47111013af7cee1403739d4dfbd1c1ab697eba71cbb3ab8897c1d4f39020868a8cdfcd4f005ef075c362145a5dc8a23639d6fed292e80489b28d64978b94714ee6baf61cf65cb0f8c2ff834d2de8c57505fe19cf4b8ddedf017504e5fc66e023795c6d084025b1478967b3d3a05c37aa1c14d58c5c9fb0257c64179ec664662bae6f9bdc45b7cb87ad0a9ec24144adf1957b32c04cc400b6f3e604946a5ef72a4b5fd0a518f0c315a66837c6055f3e0362e758d4d7478c8e6b0d19fdaba7d07e6604ba962e34ac26c30ebbfd72eca581323028c66465d327345b9ca2306cf3cd07fad775a116428c6c1a1c7f299bf03e92201e4f6ae9677801066ffd8ea4e6576f43257ca0f0b3f085aaed63af068c457efe55c169d4a975518d9752a966c971058d5c4a296248f91a0ba4d8598d59633ccea1be634a67e857f80816c41701bab0af1af996805980470b63838aa2c7ddb90a402eee21e8fcc3a01bb6f58edcf134ac578d7b4cd514ae30204cca56f46ff2ac8c100ff7db6fc74e8a234c0dfed97f5bafd8707fafcb8e67481de7fe894db6ec7e6496dd8b03c0d4a58846c98881e91c1e9f99e612bec3dfb0c820b19e91a28038141ee876929eecc7fc3814e851af12067ef12fdaa01fcf045c59941e5035e20cd11b8ddd40e2aa72cf0f74f3e519e407469a5f6ebac53f44a55289078a00776b487ea0cb3b1cd0d48162a713738a72cf56c0eee32201906fbfdbc113533b4195807db61479d7cbdf32d176642448ef2be97b5f58e65bbdcb6e46bd157a90bd8a28d044bd74f9dfb5d9ce9c85948d752e1dcb587f913d363014ab71f477ff45c0736adcec8300e12e77b0a0c6a224e90b78bd5b708563ed19306e388b9fd7a3ae61097fb9a482c972c5b33e2eee656ee89f6f0e0554efc6da73dcecb70ead0f8d2ac8d1727384c4c51717b6101e94c9f3ec10572f87ddf071dea6be3187653fa2b4e3743689eb64aa02aff507f43dda2d39cbcf715c49bfa640bee3cb8a023596633b2fa3ef9a09e4ef4912e09e492812094117fdb6dbcde7648fef48e92aa9a2a2eb8ca3c15fabbe1e589898189e0f30e9440716073b2e30f9a4b523ecab5d9fff2d605d7655b6c91db20988ae6726d1339f0e285adb03d99c0235ca80442c672d0a0270c41e8f6052430a8480fc1c1a9d730b6e32d7593aa48385e46acd81450df9c0ec9a5c44a35159017604431f9313706540eceb48a0b2d6fb7e89c71e901fd2501b243cb9f954d8b8f8368cf5d79758a8b97576796c5c18d509c95354278a020a0b7673335ffb69860a09db9728c7d1fb1257d8ccd3ac9bce6ce7765b74f8531d53721dcddc07eb7454df4a818575c8149869b7231c4abea270570a67f51139b1ff0a7048fce2477da14ff2b40f3856a21b0926b987f8644f3ce870ef1999ddae736359fe5cf317b104b2bf627b4fdca10a526d4535a9bfdc1c93c86cd096598f1f7e7fccc3e914bca3c41e42b05b14d30cad1db2cb81a88d473c24f7bb40e5bbad7a46dd7a6c8c2e4d0e6ea8d69bbf9586d2874f47e6246bd275a4b424e32fd5dda26504e3fa2b7643237b66eb276d1967cdb81271be91033669629f0cab03569c96d94f3c61afae0dddd035196323e4136c84bab5fa6dbed8af35ad08829e2f4ca51f13c7802fd8f019762865a2701fd9a62ee13d102ed51bf14c4dd249272ad2c2b11cfff639edb559bd3accd2eb1a4461f7b0faabcffe72b0563607ae8dee319aeb9f34dac34d1c8c39e37baa5df56d0b0f1c5ebf9d11f4b837bf6f5b0eaa12c2e2a2589296edbb27632035d3a42bf185baa32a8f9efae6abc8785c0ff09fbed29dd7fac7a095fdc1561cf4ef06c8352bee42ea5558224d7886552a7686fdbebb57b9f3640bb96ff50795d3fb5dc8bd5b11e6ecdfd29226548586bae3863a4aadc69dec312b7137213556a28f7d5309d89f38964659605fbd7f633406ad66fd2e64a036957c75cafd0abc7afae86bf79e75f714285b66c9d57a056a8d2d3578745204a868cc7bfd65b56c659f7a8b5bedbdd79ef91dd5ad566377e5428c0b01942dbfaea35a26f452910e416acc84bd12fb521c5f14e16da9a944b28063693e8308f28d5e7b6bbcf7125d07d47ca367479a38ce7d166dd3d297e9edaeb8aa21dc6ad26162ea6e16292c81bd1bdfb06605ccd09500c6cc561f889b804305fbdc3f3b87d2bd1aeecb5483f466444e5d4473bf8d7cb57ea5a78ccf8eb54c41bf8db67afabe1988fad2e59c0b3e95c47480486e0635a1d79fc76b81c8a32e85326f960d48c6acf73023adc95a02e6f2189d3d9a9c713b0524eb58682d1d2ba39b3cb40ca7fe36ee3daf2edf56f07759744c7ebc4faecd3285394a113cd0dde20bc2aa01fd1c364af98ddedfc694435ac994903d08a80632480061ad16cb3660eec48dd652a99fc112793956ff7c17c53c062b1aeaf5cf0f26a7eb89e2b068e5bfc98246edea3fa2ed35b22341a3fb9c5a81222dfcdda883a9e1c47d231a7411127fe47292ae20109aa869b0500dabc3528d36a7f6750c539386ea71da0889ff6a6c1c6fceffe7854f0ea482cdba6c99e7b199c33fef2da395c3db679789ad78c4989bf03c9811cd54ff754d46bb000146374d108098e05fdaabfbecbcd8a662f97a347366449b5cfadcb90dbdb80da54f49aae02f26736bb439669981af2775a974c624e25e0432ffc7d737871b7aadebc8a5c76baf84d4210df11bda86e44545116d0ea1a7a0cba02fdc2621a41e95108cab01d83b2e87092a030c38eb68203f9c76cb955907dea684fb9b2ead2358474cfd649f915baba237c113d57a568a72db98e905d17356aa97d24b439a84fee8e3907847f5028b9bdf66606d339dcc3ceced74d810217192475cb58145fd6d90f60036040f1cd87ce89d1f264efa049a6198ed2e900fb6d359012366088e2c5e34d80de53dcfc2233e9fda09f5ce6ba451d9a70b292fee607851644570041662666314a20493fe1e9483f729965fb58f8202f838901f36e6aada07b08aaca45e5", "spend_index": [ 0, 1, 1123610827, 4294967295 ], "result": [ "cecc808d192a9f822f3d0fe65f9b06406c53acb64a6cd783b406585b643a21a9", "099a679b991f97f847309a96f0bc71e33f2bd4c06f4e31dbcb1a58583b778476", "43f91b8025baec1f25dc121a3099b787babce80802b1737cd8188c26c17eb777", "d40d554dbb960ad52858d382ad44b4eb7ec6f917be4da8f24b00bd7a5eb53738" ] }, { "desc": { "Inputs": 2, "Outputs": 4, "Witness": true, "Version": -1199693507, "scriptSigs": false }, "hex_tx": "3d217eb8000102869733b100000000000000000000000000000000000000000000000000000000c7186b0500b5165934b34ff67d000000000000000000000000000000000000000000000000000000009c073fec004e976226044f06990221d7b31cc816fd9aecc340fd2a4478e48f1a24573435b5e58fec618c86f9ef5b28f90c63ce7d250099ab463a98bc1dfab993f8b53b1c0dd69d51b2b0d44f1b27beda090ba650e025f7def2ef392f9e889636b6519a52724a14118f77b49cd4b43008caf5dd9543aab138e336a85467d0be24f4308f004569a61fd2817e43c1222ec3273fb0b9898e095a77cef35afbb7fc9b567d7e02124ae96d15398a81ac1e673aff6294d79e17c0c04e47ae18e80ade55c80305dac6592bfe465468741566f126ffa73850db4086d43c3d645a0b670bb1e87f00c8a6509a1ee76d9a4bfe91f51a36e5f3491b2387df1a0573a15ea3044ea534c4330c0f4627fa6a167099b2e53d17c2fa95d0643b5270685e3e0516d95725fb2cc3f7219163830e6e14b4258177cc8c9bddaa05c09549320b2465f471dc6c094bc06ddde5dacb8721aad1a3ac46eab1abb5e5b0facd59f0d8598d6ffd21c9596c73d7cc0328ee01ec7da03e815f87fcf3c5b4cd684bd6a83fd112887f38a3bed1e0bf2f8461b07f459a3e8c763431a1913993ce4679d32ef1fbaa70965a1caf20e5152e7b2d21a90ba3c79fffc713a2cd12c8d706091319157784b3c9fcc1c9d9dcc488822f5d1e955f210eaf46d02caa7b654d23ffd346c33411fe812078a535c7e4ef152a7219c039b631399ba8717b5379c528724bf0daa87e5e2795f38759cec0a9a6a9d8850fbaafc9be8eca828094ba93c72734d4ce99fc6ea5d990d0cea219c78c19ef246c8087f15785b4bb8b747411c95b1f00d1be2355cf509f1a3208916a851ff87e7417d559f7225f5793384ef30ae6a5f8e625d2915ac23fe4a884c12e0cfadecb350b7b6712859b4c0ec05b38fe28ef1450862009e0420de3c68579c8f870ab50417b7fb2d7a9f9b17e8dad1e16b220d8fd52c56ce35cf715b848984c8558e7c479d0b10708e74fc19f43a79df102f4c2f13f4e5d3a344b65eaa525ea0d52df29877b53dd78d116e1834fd7131f93a160c740072ee12b42132c663887360cbe49b6fce6301d2ed6055406bd794b68c70b1b1507ad14b41e0681198d76d38773592c6fa9c4bb334fb361400c266e3b6b9c939ab7ed6bbd0c5b6c56b43ba0419da478a34800a85a236524fdf386f9e3cced8cc9e220dfd0d60ced5c93638c1a7ab9cf7713080114d2aa6baacdff3edef871bf11cef706dea1c3250c0040d9d7ee", "spend_index": [ 0, 1, 4223522144, 4294967295 ], "result": [ "8d9a8c73db734fa3fc183e185040fb3baa67be526f03b54f5289c32abf2b43e1", "dd2096b3b9dd56a759f368b1e43d0c69c86bbc583eba22bdb69bf0f43fd96fa1", "df608c08ec965201c2a83de9f2034cc59b52867b780ccc276fec845dfe59c25b", "95633cc720202a26d62f9f827fa159c88599567e810863b9021e344c12416912" ] }, { "desc": { "Inputs": 4, "Outputs": 1, "Witness": true, "Version": -1735281, "scriptSigs": true }, "hex_tx": "8f85e5ff000104ffc381310000000000000000000000000000000000000000000000000000000028d09d5afd6201ee54e6f3450342d4c5bb74215ba323767a92077b9f5f7e658bafa016578cfefb60990a08cf221b1e790ee35cc98b50b81fef4bab14a25a29865a250bd5a29abeefe0e1d4b87098beeaa9a54aef8cc00e512824baa5a3c7b6f3b9271cf99da5b946b73f048d67e6cd2bf8ef4a215f94ce86d5376ef4024e11fb258ca5ae1e4296f6456bf39d1cd9b5be23fcbe336bec2c683504ddbd48e2788d423fceefa4601da5d73d9053c0a9e25165339347f1f7e308b9afebf23a65a436b411601c08eaa3002c741ab2b05739ff95ef7e78adb65137b302ce37d8a86bdefe20577359fb4b4c7b3d21c4f7fb9bfacd140d849727558107f7dd8cc49b2d46b37d6e35d6b0c3a4f0d59599a6c65402734c57daa79fe0d4e3c143f8908bdc625d210897c9eb94d93f6eb929dffecfb2ade04ed4855d64994bd7954f424a1c627dff832bc101f99b74acaa50763dd4272d74c9e52e750dda5ecabdc1eb6948d78f87d1735e14f929da1108ce59ff8737e400000000000000000000000000000000000000000000000000000000320cdbc203ead0cacad7b06225f5844900000000000000000000000000000000000000000000000000000000bb5043d788c687a07d2027be6229e44e58d5d12060794ba4ae66bf50a20f75b9f83a634c80a70ccce7650de8fc42762ca9702027aa6968dd093a0ec75d20affaa898e9c1fab64720f09f22a5f5f737e06997e8fd5de8de5d22568d8fb38767f34188dad7c60dcf725ee60c5070b741f14ef7655d44684751ed6e22170aa5b26e324d3bd2908547bd953255e19fd77ffdb244a7f6d100000000000000000000000000000000000000000000000000000000d9fe45da005a210d4b011ec587ee33a3f378c8bf915d96596c5561538659382ed8c9925d717143ce297c3edce55d077b04e066f0dd33c04814ff65e091796355a7571e15e3e299ad1565cbd54f313aba50cc9b83d04b8eb639c78a8141ed1a602050f15c063ccab4bf412c6dc361be36716928d073a7e0e6425fef880904bf6ce3777db0218bb936e466840f1cd30a57b2909d485040e34663c58fb3d29368151caa4c61ed8b759b3d2581c4a1c710c94cc0e535fbdd9c73d2f543a0caf927a9e7c1e05c9820d304312732fb1649a6d4dc4b9d3ccfbce3e48ccce902d4954f49430f625aa8262e289b19ee1cb08a9a1e25b987521ccc4d2461c36be71f5720027f33b42e688009eccd0ea247bd580759c7f8372797a9a2c400a22141a749cae3dc3dc492a0eb83ebf51d62fff490cde1aaa28dfe481d065384b60c98d01998a8b61ed3663b6e0b4d461cc2ce2c8537093b70dd22d5bdd235836e8561561bbd35f941257ee8381bec20e7572389e73091d73ccf67b6a51ea55dbab446795afe1b619a85a26e7dbaa5e50e382055e0acbfbf10d6dbb2a9a95e1a537de9e7aa49ebf77a24675a7e19071a6fa30535a8ac100e9b8a7c896e72913872b1fc11b9167de507b00291020d18c9ac897f9bff461130f2093e0602332afec99e78556834e36134c29cd87780c21bd1503a3eec4a778a12d2a041ac45116683f0cbacac9f06c91a51150fac9d89d3de0501eda7cdd5dea795a0b9d6a9b0654597ed2c63c3019ebfec1dfd02b4193e1bed92d0dfc044496ba50d7c082d1e4af5d1b9d3759e2a8395cca838cd4fb19211b5833202fd1d015de2bce81ef7a464a58b1bfdfead64af9a18256e9d29045b1355baaccc915e8340942649c6c06a8a5ae0c2185ff641343e673b08750ec4f66bca04a4f5fc31ea4268ba26281738d1a5ed7bb3a0e10e3286dd8894582e06d130b4e2e8283bc80b0d0eee98a38eaba530463ebbd4c66682c7cfdc1e48f3188fed7434a4649c50c88b61b589b73944585965132393e5c2c3eb803b1f7139b0756378353c7b2dad385d16502ccece41654d7e33836c030bc00c5912cd5d59bc58df1b9e9d42b7e1693840399b715cd2b257a8778a29076822cf737ca5ef490d70bae95ef821e37c5b1ac993d87f3bf5d77a8324fd7b7398859672fd9e3045ad90f1dfa74cf1cfbb935eb8674838e431c547b7418740371ad173b1c06ba7c007c1c258f8376bfd0c01cf95133eff377bcddc3dcc18e3fe408941d48e3d8ab940797e37e500ffb7a8e701f197983d99c3ccc8b7deef5ba474a30ec5a2c54a4bc0b038bfe91f7cc523a1f977670cec06e500c42519b1c280bd8527c6a97a23772fa8248833e9499b9aef387e836e9bfe5ab77c0d7bd27e049e4ba1db6c0976ff2e624059ae9ba82656a7cc95c563e6027f88efd28f513a145908196236e795d1081eab8591ca98c9a6c8c4f7c0d26c759a844ab3dcafc2dc8c3cd16dc340a2b9167c50049839fa9b24564c1e6bdf2ba8b122515f1923b057362e09685fe4e6e72fab2ab7c78c36fbfb06ed4217fced8d2435a53b24cc625e9ab9916271f367c84dd812787bfb3f5894c1f10e32868e41b6f4205bc78401e81f6ba376baa4d80ef2e39fd4ff591c942262a765b350f0af63b2c62af1d9baf08b4465d1bf2fba18604dd42dc19ea6ee72245cfc9c20d05647755f59bfde7ed324eca0ca9c44cfb29cc5c77b13c7034e5958217c09f23722bec9ab2f6e0a8962b9980e92e12a473ed8fd86f263f690c13d2a52acd5ddfa770674c4b0a31cb05bc216475913c6e7bcfcb7ca29fc5be402f59b4d1e82413bf56d1715a830ba9830dbd43c24cbbeab79ea0237c24b916dc4336162ab2257a2d5599a70e53cfcc5e193ea2cb36619ed612f5d74e91bb267084573d1522a35c97b78752124706f587b2fffd8a0d7704628003708def1", "spend_index": [ 0, 1, 2131463707, 4294967295 ], "result": [ "4fe13a1cbbe51a9d65bda87f260152b4d574eef0e4d0300270e316072665e23b", "a851f99ab09182aa209c3f4fd664792fd0b92cc84c31bb9516e62576788d4eec", "deaf1eff3294114ce43e1aec0c88cc9cb3fc241ce513bf074e38b96540aa30d2", "03f5bab0971c67b25b3a88311a1bbd1b2a0fe26152e6a937f3f259d4df7459fd" ] }, { "desc": { "Inputs": 9, "Outputs": 4, "Witness": true, "Version": 1733870626, "scriptSigs": false }, "hex_tx": "22c458670001096f7212f50000000000000000000000000000000000000000000000000000000062a1048c005edf053e8aeff6cb00000000000000000000000000000000000000000000000000000000dac108e300e5d783739466929a000000000000000000000000000000000000000000000000000000002de0905c00777de5af16a35187000000000000000000000000000000000000000000000000000000002afde50b00d1b9cc304ccbd8ac000000000000000000000000000000000000000000000000000000003a56fd7600f01c0d056e9eb32000000000000000000000000000000000000000000000000000000000e1c4a348003ecda43595b67527000000000000000000000000000000000000000000000000000000008ad4f82d000f390b1df02c0ffa0000000000000000000000000000000000000000000000000000000073b185d200b715cbad589ed0c40000000000000000000000000000000000000000000000000000000099d22a0a00a5a351710493b498540927de59c8f7af8f30d26d6c728b59f6187e0301c522d3dbd8c291d8cfd66ce0c06d1f7732db576902539dd2700663fea2169b834fd33ff931c4a9481952c6a54b70864cf6d4a70ac6f3768f165299bfc2f6deea322f58b3cd8f4c87886cb7341b4b7ca4dd8ddc02f233f13b7c1f8d439d81f6c9bba322a0620eda5e7520c92dfb0e3df4104c37281c4987e360e666bd99ebfd2f40f961d37a098437835258215d2fbcf11888768155988b6a0bb4228a946032c2532dbd887c4136482adf7e361d0d5e4d78f16463769d7f050c423835ad76036c7dc8d0e2a83d8c7bd26c66d65b2084560ec8d55abd5ab63177b7731cfa9c638f2eb3b3503331c861c69a517baf8cd002638b337de905f218e4284768b790557a0775271e062280092e7e5e8d2005126edd91089c2907ec5ec0dfbdf333a956552090e47479385a04c853d24b4d1a859f4a09c8cf72b26ce6a886e4ab2411be5b997651d584f966dd4726af6945559989b33043f327278cdee1f5c3b623fc2b872f82281d6d67ae2fbeca6aea5c9b2a22b7a99e8a532b15831a5f0b1f791dfc4c951ebbea55e4a6a75710b1e05c29e4ae0270c888c573e1a4db07136b031b33af99a812d2ed300ff87240e7b2fc0cda7bfa0c2cb9f6a79d5855080771b44df1cf6cecd7452970cedab9690f97527e4c184517dbb01f029626599ebd9b6a876d80504ac0e9dd175617f716c0e107a1a4e9e0a7a992642e31416c97eb89ebb13afddc61d61d0f5f7bf863a8016d46b48c996f0c4633a7f6280a516bb89238946fb76bc19e6615d2c74ac90babf5a5060313b39edc9ea6017836335eabe3e6f530cdc94bd671f2a418c148a69bae6c9b836bc1b3636f2b78fc7aac56836256078dd3878c7ec8f5135e734df6838a803b49e8e5cd9b2b4c8b1aaccf8469dad80b8ad8c9830d9522c5b7d093e6e3fad572b6a9dd7c3e2b81acd1118880c6762e14fb0897e08df8246088750bb9c0435ba4ba6a15d31b833d1dac5a26dd155aac95e5f7915758db1f314c4d485da9277051904a861b0cbdabc0b9fea084038ec9cf8e379d5df3f22ebefef3ee3940190728b5872b467e40a554e21a8c53ad16357296f2c0dcc1dedcff1f0c5e1f2ea070b093d326dba8ead52968dec413b22b422c07c0c1e5efc0cd601ebb4955d65704fd5a0185f186b4e771955f422f4cf3ed6e25ad78805884225a74782592d039004e57618384c597837e76fe0b4f2f8ad5522834d5b5c34fe76369e4dfad831145924b4caccade3bb236cf6a74fc53d1a9d8bc6917b98f12d4abdc132b22e058c68c4fa9f23fe94033012bdd75b1587c896211f1a1453e95a83dda6e5400d1f0a638a146ef6512058161bc585df8f3e8ebd1df87241b3a10ae802fa1e84d584b6d08f7802177e5ed5b5e6a5c92bdac2bab36a5bf20a5f41fcdea3102e0dc6f765da80f26546fcb1507c5ca0831c79cfdacd3aeeabb0ea9476c1b0502c27032c4aba7402b0851d56fb4330645ff6db91b55129617c84a1f0e461d66428603eedf0280b4060f8432d2d98446d8384693c6ad6fd7e86af5a8cd2cd5594689bb2c7405901adbdcfee95fa4bf559f3be9dddd16aeef7f24b3ea637b1923e78861ddea7a7e3dfedac523c10892b7d8a0aa54d242754382ec4aafdd3afbeadf01150a1755354af291dc6e4d5afdb2010b6b8a618ee68fe294d6604b4c2f97a6c633f1446adf96cbe7761c1b8625ad056932fe99c7e73181edd37ab3113dc1a9220f03879274e5d2e103a8df16ba3b617a47378e000a2e2cc6f924b739286e55519cf6f676e3055efa644e2f7ca6c9785f36c05fa620062cd5f3db3afbe31586b65302cd13b0348edfb5dbefa8ebbd4744df86090c5fd59fff5ac4e16b0b1ff5cb88e1771a4093a1b2e27022f59e4809885b0cc2ec371d394dbb9e4e3e2a8a6c8b1d0c43bf392707fd532dc552ee05f071186922a1f4601e0e06e54235e3ea632b35cb398ca8e75406500f978da6e3380c82689ca48d571ef39387fa56a9c73add03eb17bc9205fce7984b86d4f6087b6d34b6c1b13d7f2808180ed8bc8fefa836da42c94dd1f831b333952d16d06305c8521ccc93c99cd2b610992b11a9d62cfb1b32e0e6325eca20f63beb24aa06aa0c5a3d5d0ee2ca3c0853692289faaa18572054745e4416f786231556a2e9318306c17a10f20b9de8b8a6d4d4461eaf41d458ec6162f55db880efa9e205fa62d52cc29af68aaaa1786fd7fd0547f8144e2d58ac931c1edc5f33b518206f6cf35ce96db6bbafc9434582d5b36e28e0925e991cfd6e019554bf4d69db646e3271b99624f611d9b1eb2d21c4e21c989ca28bf9692197ae94ea3b3c7c2e78b7349c2032008f138cc3f2746b6d572ad4f15bd73753e10dd359d31a86a1df75863699546dffe13c2a3a38c9561636c2dd67a2343d8edf6a90a87d51be488ca2c149d19c1d916d657d4b1ed32ef48ce82049eb9dae9e041fdc10c8024ae0b5454f8e1f92881fc8de84e7a52bda9362d315e3cf2c83855b12f39cbaa05c0bc6302d20480f6004a66765668e98bcb65df066270a81648efe375c7a0cb77138622c136da8856e6b124085ea56ffe06a8be180c8975193ed254ce94ab43f159c90b1cfe762e6c8b5fc0577cae3b8bb01ce9ab7d1a7787e13988c53a732e9be3ff5e87145fd3f983ea8a788b3097a94ed7ccd75f6c5182ca64ba92875e4a82c41fde6df1a724ee348b51d8fa415b4f150222629205be4019e0da9d2bacd21e382b57150d9cb11e11bc9c2ce5ab97968b05b4d19841ffa03cfeefa9dd6505832a92e972bd917afde03e4000387fec5ac1ca2d8b3ac2a2c271753bbbd3ba654a0b82d3fbdad9bc7be71459740e6e6320f3ba073c567e7b8e611398308b5d8b626e2f6c02933eaa09286abf9cefb2085a7f2848b902f9903b2256f2f806d353ada1f098df1107346b4d394ead153f271295877c83e9c41d0dd78e675652e42b085c8095e9a9de8f473b47354e57fd8b0cad264f637fd13014c2d744babcbed7c0c578bc1566c5ed637d8e0f624c79209d53a930cebc2e32402b7e0b0b1fb5c6d4b7284553191b8dc387f763f17d3e85fc2157b40c625572cd39f04a33a7b3c087d034c1926486e20b9d42d1e0b73735957ec0d1d3f0356c91f3e26415e97e4dfcd005f7192c3e6665d070e1d830f60ec6e180e575593c4f4837b390bf0e13a7a82e504e6d41dfe74a576b92b0951697cc733544b76b9d5c4a55d134dc84ae1fda4156694e6b6c336c46e2d242de862d1f0d702e1b55a5a4e01434b200f872e95bc97baaf1805fa72c186ecceb1ffef5dacfcb7365941b24d594fc7d7b53291a478315829bda5c482e218bfef52845c57e90eb0bf2fe30329fdbfb06ed257f63a8e173ac1422c4dd658b5e8069776e55f486e01fdc801145af5a25424e31f35169b218004ecda01b83c4405824b5bd3da11542f0532e84e1697a76461ee5e6d1ab09d9cd80b0db5fe2c6b81ba508bec14ba638884a949005bd464769fae70759ac0ac5427bc8b60a299035596e76f14f7bf63fa7b621aab900b9f66f99971ab5a60059b761728c4f669023a8b9f2098909515bd83dcc06bc7b2482fa39cc0c68ac0774f8644bb6946f64468753d06918e4c52f29ad8ac6eee95ae6abd22a702e80d902c888235f7225634883a47bed302c7f401d476a33e720fefb7d168b656999e2ac698aa87c5e8273277b3c1f42fb5c948be7c2aae2e6aaae98e159e21aac7ce52625a7e6905213dc5117be4c54ac3797fd18c4912d1b6e3c4e71d689de23f77467eed4023325d5c437f6d09ef57c63f8378caf30c156685253529dd7277f9ae03874343a12ca699b998eb8a37b5c3c903c582fd6adc9db5e6896d1b5f31b4cc0865d02e371634246164a0da11c3f22f002db813af2056783bcffd14c97eb2b1411794c9e9b22c4a5a11a4bdd7c3df303b8127df65a5e027d6e58e44a4b988a4c351c899d09533b702b85deff28f1cd8075d039cbed8e4fc61853ae823494f388adfaa021e35a7323782f27781d87408321c6649ea3158f2c66332893900017493d18dc5883869c3fd0abb16b34ca6b899078648b8d371d69a2411efec50ec4acfda6261d73bd2a2091a22e3d4afd678487e69fb18a5a94088715d5bc504ddc157b739d6d3253f7a64c62ee97626e33820d2d90335bbbb09cec8d2ef05db06bd952fadd5198e788e17a1e5bccdba514eb975aab10004fd6b013a9a44cf9cb743d0c315faf6ead2f541bb0ca8f592abd875fb9c99736fc9c1890e74ad624d50026389fac8e91541c7209ef10ff8f53d3435d208a3f1fd866dba4c3df7643a1b5fe43f030523d239af63a932f2a0d92f969c9930c218a57e1735e84748d7e83464463898891a4f380bd1d21f7c508baccccd48a559dd2ff04d7ac1b8088a50cfbae0a6dfa18b673a80b70fba0514265473579ad60714d4b058d3ef31fde93e2cd9b8db8b008d4cc5a1b6fdd5c07ce54f88c179e3ffcd9ba45a5aaccc18fa63fd82c4c8adca2e0d23fc3c5118470bd23fe22edcc45b4494e1a9133a24f0b053a1ae10a9d9000eb191a6f7d7374f934dd7b806bb1b9ef4ff2cc2d0cdf41e2c207e93ad2590b1326b089226e82d573dc96f97bcf35391353f5c10b2c246f31d3b12b3444e133dd84da02eef00ff83383c74463018e0c5f4498fac8c325691e78f3d914283c0db2f9a26b4736e5c902cc06ebe623146baad65e812a66138a9f36486b51467c75ca0a7a191a849a3e1bef14c784d08ecfacc10eeca5e3ad4b3948fdb4c7f68f800422b05f9ab85ff9e5658b863830e8a31800b7a1c8e8a2dd8da6aca55f6f53e7c3bbba823817f4a3c8553f503bcfb80d49cf8ef1b744fc16dde83d8f3de9318bb7688dca09850b9578973d4c51d7779d98e8dee78f6c51bd29f0e811650032e9301e567717df8759d3c0d36e1f2cfc811cef4ac71c71834091693d778d2bb7553a1699348c2a5bd7102c9e96759d6392cdd149e0d25db6f43f601ae86c6858ad71ee9f0ec3db6e647d0fda369ae28db01cd957a7d02cd1d215c0c12a7fa52e1d03cd5c661cebcc40d15bf382204cc5cb2c22fdad68561dd3d2b47f2a98b553f97f79e572d59ff7230866a9bfd7201b32437c819d65a1776e982dc23a99078cf39af67a4ba9b750993d2fd1b2e2fb5cd2325cc226d0d6eb8939a4d09931f6b6409820f85c5e2664bdaeff43b02db7a1eafb67478afb5799222937bfa7ee7a876fc2704778c8fda58b156649e13584d572f3a2232eba727e8e94f408fafa6dfe8dfc317812cc8a1ceddf3c0bd39ae7bf89c84c4cdb8337c98e228dece59e42996d6ff71c615aef4680e82f894bfd62ecbc9e237ee4f4c19f0710f601ca64a0fb86cdf55dc307019a095a8dd8231a311583d2afef7c23812d612bd85d23cdb2cfd8e94e16bf597060341b91496ea2700b637c892b92f0d36aa22706f2df9b2e666cb8dfa5f756594d35952fb512dde04819859eab4b520576d586d0f609cf3dd7a0e67804363acadf85f7bb4ac33e86df9957f753fabc917b61e866638e339c0c055edf4cc46fe778de5cf995fe2dba574eaac60b0aef801344900727b1a3307383d6043b2b682ce861f0f1adf698502c8b8ec7bb3c9af285784c133935c5cd0378000974cb616", "spend_index": [ 0, 1, 3288593228, 4294967295 ], "result": [ "d8ce2e1d4f993d80b93d9956f3c15a5f89316530af085a0cea683f01676c8284", "9c67e9fc5bda459813093f8fa21ab952e96e72e3a04d05d067a39c6a5738da4d", "76e1652b9b48ba4f0a01fac838c9760e726099c5f203b5446e532c36e5a9f317", "e7f5256e07be8a1ed57e7cbcfe588fdf1b70c576bc3b7bd5078571839449583c" ] }, { "desc": { "Inputs": 4, "Outputs": 1, "Witness": true, "Version": 1754886582, "scriptSigs": true }, "hex_tx": "b6719968000104bfe09d86000000000000000000000000000000000000000000000000000000007f415c3b3901b4da5201d6d25f5bb507eb28f25ac0a45e1c60ae59ab6f230ee9e0a8038f669b452ea61c6300b1c5d6e851a96c59427dba1b39c05b38ddbabd990f7e7c0dffd0000000000000000000000000000000000000000000000000000000008c09425cfd3301a8d5e0e291373c1bff507382bae5d6ce1833d8c15e877c107334468aeb6b72c9a09ba11e1aa7d5ef9a9376c6b601742dd04aecf8cedd88994cf42d95812057bb26afc5885a524233543ec555cdd77fe16042d5a6c69d98acfdbf4844fc81133a3414da7024624645b22dc8b56bbd6ec6f34845ad665b16dcbc427f6217d400e07ca77cdf48f2d15282c49f97d92f953c720be235df4c7636d930f72e1d0a1148479de8f7a5034e7ccc2497481ce01c3b0458a3817b0d49cdd68c37ea42cdc4765b361036c9d28cc5e072d1520a417695b9e985dcf00557c1bdb3a1da9ea1810615b005991b10b0dc9cf2aedf0d12ef16b9a89519657cc7e1ca1e24a91d4a0d7bfaea19730a69f10aba757c78c6867e6df21948da8b4590ccdc0299cb73b154b05f408de71db58aba399dbb6bf518e4b10f4ab3a6fcdd55c71b0b05000000000000000000000000000000000000000000000000000000001f993e63fdc7019615afd82fc2b3cd8d062fe3a9e8d8f1fb9b45227251f0f361bb87d276fb98e6f8eca5b3e8caecfc94843582c12214534508bb33f0b2ccd9ef4015da7d972166e41681dabfda8f05c14a0fee0bbd0e6835f5765abad828d3fae2254140ab076ce76dfc627bd5b153b504554504dc5a48432978d289abceef32604e5f1088ea47e296b194e03aae8fac44192915c0462bbf683c1f3502acf15e172c9cffa008d43c6293c5a1f18888f83eaba45ed9f28f7c5510e35dc950c73b67e3e97a2cc30834b2692a3de7d7a24aca97e383feb184e541dc79894b45111a6ef85c86874bdc2034c454e2128af84dd6c4ec09261a43606715ff15de4fad8f61000285ac67bf240d11db76a7944a56630bb18502ddde8c10ceef385764c0586d9ea9f70335cc4efc13f4a90ab313c5a5d1d485c4ded28ae1a63c6840cc8414b83a7ed7d7f794f10df610fdd96a28a3a6884318511efc718eb4b78b0f7552834e088cffabb2cd6de26d651d28a399e747b306eff114f535a0a6cb2e5c50020adbf40637af5aef705c0b1f990037c42e16cb22b397c25d69aa18b20271bc57785ba78d90454c54e6f5091bcc3ae3e254f7324cf5128895783ee7dd0830d58ef45b72e6f80e66e10cf626c23b2e4317edaf120c32450300000000000000000000000000000000000000000000000000000000302cffc34037ca29fbfc7254ef74677d5a0a1dd9edab14430248dee41ee135aa1adc5c3defa628b4eb451fd3de45c412cbabed345de0194b1ef856258b38750bbc7af5dd6811f8e4ec01254685e44c321255c8d6e63d6596548a2c1ae46ee488cd601b57cc34a0821c5c2c70a42629fb17491eab9f15cac1c984d88b1750cccd424e699d5bd38deab6ae973b3caded32bb66aa079bd71f41d12f0c2a631fe211951e1b73be1314386a27249a8f99b476cb681859a7dde3fb7eb39944f4e85968dde8619369aa60e7055c37d2fc5ee61d24d72379bd5db7c9772919356190c8e741042444f242a8e07621e4eea66558e2ce2bdcb835351af05aaefd0baa7b3f74ec2784ab58177fd464a41fe27b54f5c43e045a641682afe78c922502fd7901615845961828f878d854b0f3bc851849456fb0f4b7b4cc5121cab42bcc29c0df4f30b0acfa923a3dafe00ced04bb8673326bf01f386e11c38842786cf06898a15b3b3aff0d5f1d30048ba3dedb31620a58d4cab0174022709e4bc16c815597e6626cfb5291144e3ef992c440233c01cfcb740208f8c68cd8b033f9ee0ed268b7f2d66c0c43f426d9061977495fffd9e34e381c5ff8c7a5310f62b0e44a1ca60435b7f2e3ec142786488556433fdedcdd0bd27496c16e6469ce237e77f2539e0b44ae38a31bd0c489eb9478a282d345acd3e88dab18176e0358af9dafebbd1031e301cae77f14deaf7e2f5e89e968c5c26992660caba67d396449f002cf6445bd52464ed7463e7c2d91d562ab19573b9ecbaa20c513b3b9bfea47b270361f7495dcb01f8cc48a64e12a2f26efd92a4fc1bb5003f6f1b3c96200fafa180f0c1b45b7f1e42fcb729ebd618f7371aafbb383a0a25aec4b8bd11b06531274bb0b99e69e79f651c4aebd6bd7dcd84d87b78b9cb90f28ff907ffbb04efda801e9e298a6283a0d04e9e2b97156ec63a089cac2d886754a842258b3baa9493235b3a5b152b67eaa1c205762d856a0adcd0228d15b40b27c28b4cc6d425fb63b814548b33f8c14644fa9ae59e696bf2987d3a9beae13e80df0c7a1374d8e02d98505fc0653280d6626b212747b5f6674d5fed865b1ea7717f5038e60ae2184d7c38f33a2f1d09256af36006d2f2b8bd7884aed92cbc3e59f88918833a22ed5f8e58af8ef4867c972cd3c1e2fcadcbae449366e597aa42aaf25a1a784a51429046f15bf93c3ab45c7c204e27979b06b921d9bbf158ad15da955425da5f284364150113e4f0f8e984c0d395f20e3b68cdd74a16da57138af2b2b3afea6d5266f1d454465b0a1bd5c99baa8ba28bd0faa8c5a2148b9502d178bc6323a5139211a8e45ca8e17f29c7bbf60e31ecb6ee0f40a833ce368fe76b1226b9a891d025067e52454fdc01d4e15d250d446c9798497111514505dd550ecc1a85e34e4fbe3ee8a36d745c734366ca4ff4332f30f999bb25b75e5a0e6c974afc939745a19e2959fe53332455e3cb177e2266b5b06d7ebae7061f60ac0b8a63a9e2b85dd8b03448407355210ce040ecf4d04ea4257840216c12750535b705938afe6682631872b2f5b5a7fe16bc033a3e51dc8624b8358678113639c8cfed90221b5bab71ed59aac7fda49e8bca12e2798c4f8254e392469a4c707aeb88318108786cef333bff1cc28587d50bde563fab00803bb994522291cb5f6be0734f1a60115e409f695b5ee95a7f672fe89c9798d0e54efc764f09d4fd5d4d76c8d572a94752576c715506b959bf6a97efb4d5816144dd361759626064939eed3ba9f109949f10324297a193ccd0b96c54469a2d5bd03f2802fbcc7f6dec6e41d7232d5faa01b410515ba93b4cee9dadddb096ee7ed26acdcbe2df7d9a09183a7fdf1017ad94f7f5adea6c118d07a1bb4bfe665f56e662b4296c9a45761c3ef964fa68d0ff2acc99b93767bdb84bed5daeecfb876535104cc7d03f8d633a1852dcc5bac2e8a3da14a25e0f2e3ece3fe258fa509ea5736277465c73980dc05284082d2760b4d28e7daf6220fed54dc0ad6569a4388c4e158451755e1da8778b4c719e24e3de8bae3e4a500d025fd7e44890f40e20b2e81e046e97fb4d6cf7d4c0594a507b72f921f1ecc51e526e26931a074e4c886855a60794dbdfbd5347ceb68f920b4dc09dfa95e6937ee50057d176a93107dd79c62fb984c54c0313e0ddb793f1205cc303e2b5cf49508da7d722aa39817377f0100cac0fbaf528ea92ee2ff9a6404a82c246cb64fd512599696f9ca54453b5c289fe2a8c9f47ff06562f6f8022798cd2ab96d80b67663de6926ffe8a167fbf502d75e2cc3762d6f5ea430df86b3a4c092178c8d93d8a17d81d6a3816fddcd7b853dbd6a73ccbaf947046776499c379b32aa61624c4333ec102b6cb9727db72a05b1073ea3fa25c58e7a584b834d843108da493e5ac12852291bf79051fff738d190dc574f734e8d2c02964b26a6e72e79a80ce30fc01307a625f65ff9327611167647f78653b76b52b895c04de7c57c45dc5ab5bd0056ac11ea5b69fccbb8d4230b19e375889a24e0af12e15ecc637ec3f64308029eb1811791cd1e45e8c08dfde401906a55cf1fb1728fbb8678b23892b8106767fd88c6d4daac475d2049602af4c88fc1c0fa35699833f3f1964584106b6eec40035706348da0b8bf80ec902d43b59c9222c4c47b0e2cc583da3782a2a1ca203d549e7a41ae3ace15efce1039d719159630e33c1a58e9b70acb623f836894ed630e56bb1c5f0d53a7c4e5a0cbaf2b135a7563d8c2bc01b109bb7fbb0d7e31c1c1e02975c20d56ac788884602096f119c66a2582c5ccb3b40ac018bf54870398899b1c0f2c8539db367de94dd59d9a477eb59632323e3cae0aa8a3862c02dff0671b774a73ceb065b003b26727bc34a419d3215a9851e606a99f6f67e87681c520c9ab64a357c4193f2992152bd21c82bd7342a9e67671205d58c277973840aa9dc248cfdef8582db39e89b722fd7952469b135728f599f04f50135e9dbf670ce1471ba455af11e9815a644bad4b082a2f0ccb720f160e5a7c99d5708b9cd1100708523679aab25b8df9edd7f3e2b463f2e665f46dfb711b92acc4a2d9ac889273dac6de5b49cf49fa6b861ade01354a090e40e510ef9bc0d3d5f0e81b041d10bc3f44d8c55687ae1b934115739012b8e5986c7986f58706eb34b57cd06dbb081fca17fd012e03435aa7e6cf3ca87323b27ee006ffa1189315d9949d10963107fb2e60fa71bc028d63129abbcbba529195e6dae830736f2e54cf82b5179fc31a0a184aa367f41f288a9fb1cd67dc824ed5872339f1cd62a70e09e900bfb2bc33e6c98f3be2f2c79d514eca0e3d906e4703840612e628e00999e31d49cb77fd535f897bae838bbb82d52ac656b4d14a8c28a360ff99e0c5fe4664690eb148f021b76d34d1451dddf5283e37e53ffdde58628d5f7fba4596ea7ed5de41e558fc1dbb54f59b560f889699763bcd879581915987a283c9b6f48ad6341e960e43012914836d6fd66ea9c40151f26f8940d85644aff50a5f409a54175664954fa9d403d0aa827463fd7044c9462cfe8d06b67db7b5e431e704259c9a2ac37404522d53a018c597cea2c65e33a8c95703887741cd40cef467786c70f9c5ec7abe118931a31a9700119f7ec36cdfcc2a642d6d1eb83192c5c1613bdfb2d23640b962d2ac942064fd357bc65d26a0e5e12b3f176ee2b380b69a5e23794c8858c8eea1a263a8dd65b2c5662850fec717c73c47131851d8e63a342540c395d89d390a1ee7d64d2bb9deb7b8115383a3fad5c9e75f8eacf5a95c310df332e95f39b8192fc4899cfdbe19ae9ca2e0fb037220c94a802745c77f8bd7aa44f78ed2e36ad3fde0fa5965a7bf2ee842f29792bc6941d3092a0749e15359b67792ed5a92eb56057c355349b9034860b82d718f0c0fd677167bd1b2c5e1d47d78e858b22c4f564470e36fa0910193c2b5f64e51a257405334a7554074469ddca9adbb18cf8b75d397c9e73935744410cae8a5b467e3aaa091bdfb57400e3e19a716a29184a48ef3eb050211fd1d0194dff49d0bac4810fea61271d1a7ca7b37aad8a2c1c490558a88bcaeefe462561f59d4d9801aa08b5c69f7eaf563e5b33329348699504ea7227648996c260c74be8cf8d3714cdc06eb743181882330e74e9c421dd820f7d8d2cfa3d5631ae76e6e09620144981ab39e1de4a1612d535f5b373cd618855790e360eea543d2e38b32929cdfa1452149a4228822fc3db30a28132d3502a90802253c9a2e98f4a03c48df241ccf9d1e5bcea45eb6210c2a6f36510b27d516588b7853b22e587776658004372ef9f4eda5e7dee2eca8468bbabfc6ceda592b756eca20d78c3a68f2c0343221be7fa178120107c6a02f112c88526eba614511752d63319749240f937bf2132ce0d7bd340eec501bbd4e8ee4fa7b6da799b38ce0d6ff3f7baa4e046dca81c5c794b25fb0352b63fd9778b35b21425ff6fe3853a88752acdd8b4fa577492b2ae07fb235e8557ce58e87936945a0aa580d784bf8be5e5e0cb7aa5adf3b6872b1497d61167956422b7e05446da6c407cef83d6459251eea4fd1d6f5afc503fa1ad9b8d00218270a238556fde801f36785ae45760a44e3b192fd7767afc2a961cb684b3e8ae7746e7553183c943068357103bccdd1bfa6546fbb74a02d103b58085ff12c40efe2a83537f34393e7b42ca0f641dc5e3485bda65a599b89f5a29d0ebaf8c63f31f356bdfed202c8101740fd87c770783917b0dfcf49a08901aa4860b036c978cafc0be58f7c8e4ccbd7cb70025b6b4e65cab10ec424c7fe165d3b74aeffc7ce13196dce6d9e204e141fee977ecfc7dbf25b2db6a0eb965e15428c2df3fa8feb9366b9c1a7da05f16884fd38665fd6727833e50c64ad2eaa76d86b1c136733e8830b2dc669bd032d22eda3664204b72f81ce4e20184d5f36acaf45b9bece856c34143e296cc9a58ffb3cfd6baf84d0f5bb8d3a152d3bb828feb85317c550a7bbc176a6da8e9580303ac189917a95a144d2437577727284016e8201db43c22e12918bbf741e62d7e9a4c7b5d6f5a88305a6b7be34498707158eb8670a246b30e8a01c8246f2ea410e9fac6e05d77e6e288a9b2ecea55d460c9e7b2cf922a1df2bad4ceaf64fc56dc8ee3f2bd208dca08af340d7d081ac6d00c94132b161104f337278259867539d23cfff7a199702d26d13aa10ced33d53bbe0a144ac9398c1246f7913f867f4dff717abefe0d9357b49395b5a0e560d50c728dd080b90942f8076869c8258de963f3a42a0cb5753ad0da3fd92010c1a9f703bb8c985668faeed360be26a08efe15b5704089cb3cdbdf189334e35fa9fc0980d8500b09f27e826ae0e3e10d3c265b4873568a23f28da2224eb56af4538fe6ae09697171af15639020005d2ad0fd9127b2720cc48f87e04b8109079988d9a1a3dccfe6436ecbb217f1310dd88f6682ba35d13fe3da0bdd495377db25875b17628f4c286fd0b2a1098ce8aeeb0a3d649fdb912b3bd62dbff1986d481746cfd86894aadc6c6dbbda7f5a53286e933eb93228c932c0d4bd3b305ef1e0af76db8f6d2a3914418cbd51e045d34623a4c9b32ed5742f9d78e618de740cf0aa7f09714ea0d97eb039e55ec1859459d89758a30ba7a195dd3bbe3f9602cb8f00ada6436a70d53b23d054c942af87339230f5aca168debd7c91ba671b5aee55052a858eff633a91b2dd8abc86642f723f5cbe910e3314ecc58ca561d2713970a10bde27b27766c3ea121dd5879dedd1a51f0907cd7df219938bfc415a8bc818997b66d96b138d5a28a91be44625e39f742cb0610e54e14fc4363e81e2c1b6c6fe2eddc3c8307059200097b0338cf6172f14fbd2f615af97839a2cb00f9d1df4b1afa867173a86456de48e544a8c1fa136356f45957ee3e82e80daa2952e50d44c37d33cd890fb8bd07a6c85471cf49b5764b18286dee4f590934d4407f6dff9caab986ce96e05fbde069c6fccc88b53a2482a9b0d28a0bb512e8ac87b7aadfd3065dc10b64651564eeee94fe8ee82fec118dab7cabc15cb2ea5af2f12a6eb7a3d223f777ce7afa9377ee4e4bb511754eee876aaf1476481405342c5a795757e05e6c9452eda7b56f4711023e69822ca8047b5e4e", "spend_index": [ 0, 1, 2456065750, 4294967295 ], "result": [ "c82d09e378448c2347aa8b02314eac9cfa4c796916807ebb845ce1c028126a6a", "ed6848e169de1f42c18dcc704df0c25f7b0f4827f9bfa9873e5964f6df654a6a", "df757ba39fb4d09ab4b637e8dd3354131b705e9059886c6b3bb2bced658ab523", "61cffdb2f37ce69bc6c6e8231ec05be879b0d916c970b54bbeb61cee67f8864a" ] }, { "desc": { "Inputs": 9, "Outputs": 10, "Witness": true, "Version": 1850961967, "scriptSigs": false }, "hex_tx": "2f70536e000109f85f992f0000000000000000000000000000000000000000000000000000000044335c0500eec64bf50c1476b20000000000000000000000000000000000000000000000000000000042bdb17500a5bbf1a7c9a55fb300000000000000000000000000000000000000000000000000000000a518288000ae1db2440108c938000000000000000000000000000000000000000000000000000000002560ec6c00ea6b2056e540a2ac0000000000000000000000000000000000000000000000000000000025c2635b000aeae0aa3ec6cf47000000000000000000000000000000000000000000000000000000009dd2a48f00cef4d6b234bd3bf9000000000000000000000000000000000000000000000000000000006099e415002c6e9c1e2120f3e000000000000000000000000000000000000000000000000000000000aaa3a8be00c3405a7e384ea1af0000000000000000000000000000000000000000000000000000000011ebf86f005d74bab90a03966bc38b140670c83394993b41faa192bcc2bbf00e8c84cfe3e2280e40cf1918e7330a675f8ed6bff8c9c645949a01eb2e877b3d20648c4740742fae4b364dba1ed09c2eb9b16cdb40cfc03ccb3346256365923f08b6e3971563460fdbede483a37fe322f85983fe0e80ec9fa1dc674321ded07cb0b7e8053e1f6fa324e70b962914517800a1332dbe56ff58acf7b170cb5345bab32984a78cb3ecb0e48cfe65bfbc0e3416ee22c581fc3976b01d2f43abc52d14d6b3137d4f33c1840b336edc071ee3b86ad436d20f848dc6f7bb36652edbf78e8d655767c8df722b085dfb5d15b04373cba8eba2d0cc3cca8ba3359d2005c45587848dd008627aa4b5e2ad12ef5c6810d4c759f8a566dbfd20e19549cda73ffdc82398a215e1835c2813f551df4b79a06908c8a8e0ad5c8ea7f9ae7d3bda24fe46228edc32a9d71145bcdd916f6159169f0f2e3c9395cdc4d88f0643ff15896612ee1ec12d3e9bea09e3b4edb8bf30a0afdb95a33ec4b806a747cccfc217b87ed3d710f2a37193b24595f1a86a4c7ec7c411f18a3d29b3bbbf0ce1fde4445f0c1d539a78ede20f28bbf4d7726f5b5122f43d70432ac8e66bfe2c61106a330842df487463980ca9530c934e2d76a1fb08fca7c97bf7dd8ccce16e1df9a48a380467c6daffbe488dff8620049a2d58f40a4e3814ce4a23798677fbe0b7cc459049a4e08e03cf28b1aede25dada2c93b55fac1288bc14f3d0e86bb8aa242446e5df3bdd068c2892dca2e7c1de634d79dd045a2c8041205c07287c45ec6587172612c09df05dbcc67c72efa72f74890237b7e4be92aeb7e1930de7e56e587e907a5ea9b8f63276530a64927070491cca1f7f8c15e216163cefa25f4957bd0c6d0e1a8718bc44e303c843293aab1ab86efce72ddebce679fb9127d3c3297f40b7cb621e7e32d7c3938509298b5c93d7578628e46004592970b554d6e7c646928e071e6d64f645c7e473dbe2fab2cdda498945171be258ebf8f5e87c6de412479f85dbb30d130a19002090678792191d41c72d52787f3f60b78feeb415ac7bb76611ee22ce49473a6b3bcb4788e2da9c4fb90fb794e0af9dbffa4ad566d338f6df6e5c0bdb325a3956ba076d4825e4040d0373f5a40fdc648f73ae33baba93cbadb1243d71b946bf5d7bbf32f1972d1c4aea869489a2741b7807c8c805a16f5ad540b6ec1553b9a499128f911c41718d2118f7b563ccf55ebacc740d8b349b5a720a388d8126df9b2d97d8038b9a8c810a9f51713a0a84d9085325b8be5ac6cb4e3b02a14b99ed71b73532e59d4a55e5df1f036d880c594f2404c307d04de8feeee4ee26106288ba82b6de60a87c08b75778de94422562d8905bbfa09c2e8f61e2cd1ebda6ccd60425d66a2be59f83f48f1be9eedb5d8d4bc3671361d3898232734cbf87685ecbe3d5f49e768db834328704978c8e75ce1dc780cd5921eee0feb6e6e3d7d19e842269c22dc8ba860c6ca2ffe1ca6cd2fba9f5ff7b6a08c1ca4ff6f6824fc969b24aa5794d1fb8d91c893ff5cf878dafe7ab0897dbb7c16e1ab3a26311b16bb4f09bd93c8882a1c3a7df054171813ec7ad8d5a744261c6048fdf1bb1d3ccdf80e306021d35f58a51ae1d21b980f21f6642ee562db6ff57480b7c752929fc429455e698edb79f256ae09afd3e3e3fdad5a2bde732e86f942bb022fc93bc6e4dfa38dbad3db45ed411f3043c64a8f4e9ed3ca9925e5d8dd5673f6e51469f7f9eddb3b01e3a9827c51c18abb2f358e5a0e0a8ad82452d7fc851633f813ce1d77d2794d2ce74ae2a97710d80ff41198d054981b9b1fef2eafe5bb66e71d7c0dc7b1c8f016c65a55483dbf2c9e587b924e2bf0b43afc36c854a4d1717000ca36a667e1efe33fba38f91ae3c39b0267c6e65181d80ef636767a63cc16f64768db995dff66a4e3945e3dea78ecc54babd5a0d5b449ecd761577cd3f55e0b81305e3cd67562b6ce6067ebe33af3aa1a07cb0a8faaee604f5639af21acdf9ce454a3d4cc6a464bdbf2508ee9c561cf2f00e2511f0453702c9afdf888d8c4b182bbadb4ad45042c3ecaa3c3ec88f24d00678351eccf9d38f2c4e48239ccf94c6f2a00c6c2fd1ed3dc0c9b40150d4e5a0d3974c8baeb040d9e2c267c6007e1f3522b3524cbcbfbe73119630abb7b8058953fa6f1dbaa9373494804a21cc84b6e1359e6a6726a25c2659a89aea05571f0f60e9e011f33b4a66cca44addc19227ac0fa01fb3905b37d34f116785060ea25f2b1c828e5da49f8883fffc4c81ea3906fbdece5ae3be2469ed2bea57f870f3cf9b0402de22bdfe1823b21a61c1b356dda7beed30bfc3b6011aaafd2b063504d7c858b49394c7d6a470bb1cb76cc89fe94b6c26cdd13611cf699022e5f6f4e2e1aa0a5d9616b904f939c024d560b653e9e7f7207734bcbf1aa2633d161c811df4c88ca27bddaf1f6c80ec96b6187b7807ea3e63d80e0bdea17a2c2bc3c7c23df2b423ba99bbca5f567aff27651cd76987c6f3857e197ac68fef1342cfaeb45408aadd7a47693c14516ed88eee4101d6b1f986139ac0b04fc0467ebb13de1fd45261fa3a72b8ef9cd1f770240e81ea5946c7a3b5594f2d6ef955af638ea0717dcb0424fd9491827382cbb19191ab5d60e87ea53947499f33ef753004b57e59c810eb763b90c6c78416f2eab8902fec49a2d4b553338dbd7e50430a0ba38f8d1ce8c07ba23fa036b0641ab7c26f9c6a6636a3e01809ad4ec629d616c2ee3a468d2160e1fc9851d9b232e366a417634c998a3455f9b5802308332b83e9ed5eb8de216e6349a727720694248619822e0b53302d06b4e2fb3e04a13d2629f5d992319713a5a4a71f9bca80b213592e1ef0a506537ac4ccd84b4f54acffd9d187dad2d7748630c420a55d024499ec1a1cdff7d70aec883e08654c2688e4dc68eef97b774c0af5235111590212cbfcc8ccad71d504757e347d41ae8e5223753368e4aafc12d8233410b1a0381cdce6980045ad74aad209731dde0b53d7c8b8b7d85633405149a62f8bbef4d247f139ca57adc10413c1f5f363fcd18b6d10d45d1f6ff0812a868ca1cffe4a2382b7482ba11d72993a98fa68795838d017d6dd3431346c92e44437d0cd7d336082022ac155d9b8edccba7cacdc3dd51e2ec90e80467a4a23e7abb19e89ae5d99ad66eb3cd024301c10ef387828d1fdbe95a6a987c721aba65f6e8eb0e417f8ace678c7b0261efb99f2572d1a089ebe6de2226480c264b5b9378199f82425fb21fe768ef465bb135a2b3adcc72f732b17cf2b7374f38cf36ccec54b92c905e49c359406c87d1554fecc9c76301ce3a4364ad5184d8ca399609c12716eed4239ceceb9f79c3ee9fcc960c85037fd7001f218dfb4201c5fd81f35cd1b9cd5b12be52d69a070593b7f0f6c07fcc824fe9c2641bacdea9b8f056e02173b4302ede936084d0a2265da131be4a760f8c9777387e3270dbe16864478f15cd1058a02b7dcfd7ba9724a121ea665f1530d725c75591175cf907f30710cb62196b6dc19c10580a2a04232352975bf4f9d2df87029b089f01dc421138a2fb9b52859f3688b4eea3349ea6209b9c23c455c11c7c7c16c13d6afdc01dd4ef7c705253274f7a8dd005bd5292c45830f77320352b44f5d965c07bc3ef8005f047b670dfb25f2410d41c8d3a946e939349dbe26229e5c45b8f090db8d7f555583841bdd029148e65b6e178ba4cc2f663a9cd7be81bf2080fa468cc57539704decbb4c9b66b90b5f336abc975cd0897ce3d63eeb97ea6dff6dcb16efc99bb3426a0cf5503d9cb305231b1b7e06391e403d46678f7397049f56e5ba3ca3667b1d128236aed8089b3835098f9f0e5fd2e345c756b6d42f8517db441f592d1a1130da0506f3ce4a7525cde8d07c028557323b40194c4e5c652670bdfadcd7c7bf69180dcdbae7a3f5e5e75dbe9b1dd44453337fc9f1ca71265ac6f6b46607ec90b0e0c174f18327c7493c9ec89b6d41f9c8421a16199cf6e21cf3c200d17a3916eed78b642b2738ee2ea5318582d106ff55932713f90e40edbbca83fbabf015483a0b590d2fad17666a5b005191d0568f8532b26600e3ce1ac76b5d09b79c044c21aa78c6eaf6549035d77f3098a1b93c9ecae5b71adabbae9fae038b9b93cd9e241adca0ff5cb79077c3a35c52100b3909eba72da0b33d028dcfbc741fd6d747b9bbaff07f57e878c11adc874e0c5cc998c7808ae18069ff512bf7a3c4c446ea1f46927e91358c11a37982603f68f35bdc7e745f9c1b09d63435be5646c127e3c5ac10c6896e029049a7c23cce42e42bda087fc701a2d557a37c634e05f495c870be70c8ae154b53015c0447d198b9a1a6a0e658762d5e79c7bcb77b4bbf68667b20b5282179523965dfba42ddd87ffa4bd1c7830af752c831f4ab8b90030fff792411835015bdbb4c5331bc6e401747bb7a6942d54721eac39a404ac7afe75daffda519432aa89d511ee638d7244eee5bfaaa071f4dfa4ede03fd0701fb945082d31238e1d44c9c2d6d97e2aa5727798743c9a40da6e1272a461dc6bea8d0603fa35b269dd61d007f87065b598ca89d8b1226969c32d387da0610fa6fb410f5166b8bffe9d89fa98d6a75b4cd53922c8cc803c195a298d7983467b818a5a988fd1d5ac4ed797da0f2b412ad5b4256ef1bd36255e1fb2279c4c5241cd9ba165c3a6f41c1b965331ecb3674d61b53488ed6e165d0aa851582a9aba9af23d8827b6e5270b028f2e01c9d06e65a7e9ff731969be02bd1dedf4d9b257582dff87182e3b5c6afe36a76960687906b7795fea759861fd65e5f7274535b13067f18b535cd5fe05946dc0d56673e42bbda15bac7c653f1f605a38ac0b82a35f878858542a7d8bdabb3d64b9bb6b7278568a6ca81962afe21b8e0d6748b3df548e3511c246c7d348b90297cbb4225bd1d6abee7bd0da73e79ba09a05a3cf1a9524f1774f6d4a767c21fa2944eb5605f28db18fa3a78e6700f4b9e178271d09d74f9aacdebea26d1d9d9a02323ce72dceeda95340d5bdcfdceda1a78c7e5ae3f08244c826a8c3ec5110785d1097f4e6c525f61afed882f3f17689c14993c2970ad57db6d08d5a927c4eef41afd7730825f292ddacead1db33c48fae178e8fac562b39b5270c4bb513a9474f23a2fbeb758999a5a8ee3b28c0192d908861a00c53af214843d65731b190919835e49d5fb61abb8faa69cd2dd732df1798e6e7100c2cfe41d1a0a61c86838009d7e72d2ed8902de3e4d691f4eb1cb207516f86cfceee6317595df37601d7446ded069b5e128748b9f4eec83d37ef824629fc6d3d1be1d08acc91765918da6f5350c5568320155c9d490fd1390f6d2cd80740896c2537d8f4b10883d295db035ed6b5c1915523aa1445d175379a22616632f54ee4ff1c74703152884d906997df9ef3284951cda8a225c0c4ddd60174f71bebf3d68866b43277afc02fdea0119e43b0f5b995e3bd061691a7782d37ebabbe6f55645039d85ae6aac891bfc5fd44a389a99bd403716e14f2676e8be1308a5b341c04dff01b231eee21fa47576fe0a208b6166f23934db7af97ac638efd93bdfe3bdd89882cdb05f261e0f8cd1177b1ebf6846fa157c586483403e8ff72ecb917e06699b94b5c8b7debb525b450a9c5c18188ffbad5a7459b459151e8a717be46863a77a09850ccb83fd04343fcae6b38a6145b92a57064a3f3ef00c0441ef2d401b76ebe25b53c7a274086c65f8f9d876849e4e34f7bea927daecb57396ed2c9d0d127e8a9fb8f26f1eedf1aa47f83a599e7ec38a8c9f68b0608a9b3617e740017fad3ee95f284d6cd486bd291f64710c8d1591cbc6d79105748f229a7b75470bfe177b164c4d69e359c79c249da9c8b77970f68ee21e335621134595a705b373c376679a5af132a3c34144e47f8f65ec8800b5744c11455e376b5719067e4bb143fe610540cb2bfa6993a892439f8f60dea02872ae1e1c84b5114284b85d0809e30cf8564b8e6082bc4acd8fe0d6cf8520f9108d44c468b0fe90e5138be027061af7ae5b003edbeabbc71c887f7283657e5ffc4eb244bb0a87e82d45434e9e738012493eddab9c1a515e7964250eec0a31393ec4e1f04f302b0d5b52c5ba189b09be8fc3ec9c77e1d9044753abbdc2472fd55889945893183a578a98e582bdedb667c652e1523ce1b4b39d17522cb092e54b9e85cee4a898817e09e6be76c893a99d6260b8befe99f47bcb84248b0682ec4e648db712762d5332f465a8c17b48f52b02b3f9ad34b289cb46456bd22a31c9ed0077844c73853d9485418d348f91c2b72f7e7e6acf86dd0bcd6ae480b5be027f44a2314501aeb46bcb874106b7f1b1e67fd394b203d5e80604fdc8015e38b5f452a13177c96ea1d8dbb09f24e77a75f581e44d6804cbdc6e11fcfe9db27cd719498f59c3c593a3cf5c90ca7cf69ecda45849fe5e42ea09b344e4018fe14e8bb6e1a690e8f9f70d0c90ce8cc0d409dd5c5c3a9e377e01bf13d7f7108a74f27619a8c2ffcf243eee19b4f80f2d8c7a69682551e95da57b6d4fa6cc98641ee863b69a0b3b939bca49162a4b78f69c43c87390709547ebd58a4e1c7b9060952c333026883473984e64682bebfe1d5fc0395e97d3fd9784029dadfda634ab9606a663c2efca19c8c7dc3c45ca6fe4162a4b354c056ac468a65d62b17c0694471bce90db75d471ad38dfdef1b119ed49dec8351f9f8abd790793fd8bee2c7163bba5ffbcca3ca462bdc6ffda7413be2da0dc8017a08909591dbbdc255f62eabb39527fe21de79a8318b93feff109d941a93f1608768365eef42974f3ba832ea06a99c23f9151bd29a4f8011f6a813549e3a2225980dd99865d7a2c174cb50bde4bb67c34fe2ea5b91f2921ac2f02f8181b1140c9f280d137b4787c1b47282c413877ce7c30d38c06889851d3ea5e13a0a5a07b3aa4f1949f9b4e59340a260a7a8331859663aac5e75eb3d579df201e967ee6e69940ed719f24d8bc4ac4d289f0cbad1ae8285069917b8a8f1e2dac42a4a8460b5cf96768fc1f18d0c6551f77c5c530d346c0a2c5b9eb4daa0c12b8a2d1f599e9e0d50620af8e88c924461b388fb5a48269f026a7d7d85b0bee6b1db1f9f9b97bb51ae2fc53e76443a235212a0f901d29f4a01dcda61e32b3153a9d59a4837824cc8f6df6298fbc352f29c962282907d6782443f989ca5db3f5fe46bb80a759efb916c3e8b173fd1c01df03e1edb77a8984e4cc3a8d3d1ea3e7557b599264bd775bfd8a95b57c9a8db115712bcdaf73aa8794d61d3c93e328b4c141c30ab877837d8dac20883e9920e63f99dce69f9a39b47cdc4fab37caecf1f004c70f949320d0ff1502b9c933d6c5c821aaf2e8451a2c84e2e3ba448960531a5cf0a74711f021e5dbb406144755bb01f8f8150ea4af9ed8459ebeaaff6e0c622710f1e5294df0eb77387e312e16de21a6eb4581d6a030b3a6500f4eba9eaff5ff987d824b1d544e6c19a102d8c1d987323de8923671e111aac7997632f702265622bdc77253ebe8a021e7fbd92445a3c3ec72af0013275625e5354cc8b2f1d5fe2d134714f23c6dcf89b2ec2ff2512ea30c847f4182a36d464370557a54c322957404eca9aa27bbf94c50fd2a017cfbde7175b96a6e7b1d9ddfa38773c4ece20005ded28ec04b2e36f8bdad2eef76b566122273f81adae4da7562221c198ef2e7718fe7b453fcaca3082dc7023d4fd9ca49af0597559a157d28d1af720de30c05aa6bd41a02ac0e2abe46146f4e244c1238e522197c3130187a89b3252d4463272479be53f195f5dc4ae7aaa2198ecaddc12999860317056fa2d40323c15f3d127a6e24d3882b40b54f7dffc2dc5c1a58e1e70215f9941f18150674a12c704cd3440330dbfdac013a5eae77f1f160c7c0df60b938dafc8abe82f0cbc9916183b9a014f8205af5d06b9deeb7e698979834dfdd9a93bb62a829c02533bcfc57e0f23f29ca7cefa2ffa34454816571c336bb50284b426078faee677f4ed67e5f67fb3eccaca9234e7071755447b91b786c694ff647f5a45f8802be1135d28bf851dabe3584dc499d4ad1f4e0053ce41186ff37693e46c0e218cf4f4e43754983e246213c24c2e64c48004dd2bb96d4f00e5bb937399f57a28ddeeec97fc5e104d3d0e50e7bc58c8dddef00bf90de90215c514a625ac308abb9053e1cd9189e37a52e03e0c06b981679ae07659a4e61492fc5e34ac51822ee927bbe3d660362d20b14feb6f452f3dfd1579faf884c51db2737f4ce64afe841069b23ac721a851f24ec37620fa96a493ac06842d9544f7f67c77fcf23f0483730fdb901248e6f589347b5d7634040ba889aa39fea76ab845e18d40273e9e7c3a5cea74c3cff610bfb14b79683d51b4de6cd888145c69f3bbf013667d7457b9f8065617c3de4acef80126d9c17a4f23fb96691d399bc152fc89d7f75a44b8b8854300ee28e02ac0a1fd77103caae47763268a92b437fef204728fbba0790f62bf345797f2686262b8c3e29af8ddbb76d908c8084e05f53893290308c9bdede17bb82d9bc4b43fce3ac7cd855825a1f0338d0ca28a047f8309f184823aff0690d9d34ee0ec0d25cb98f7de154f83dbcf2b1ce5af5876f6ca657717439812b6fbff35b5e5f5716dd31079a3104977a9aaab30ffb1bc9f655f65a48c882f86949c45d7fb39f7bfb14953a042ada8d9c0c5e50eb54f365fbc3ae91529697bcb8585dd490bf47a2f69270df66a9d5e3c9285a963554a16b4eae811051a2a80009de0b239b080f5aad76192d5c62209c07d3c56e7f432aa1782b82afaa0b38e8680fb33eaee7d762e7c28a21e30a02f3b0caf31f48f476c53d5ea179b16f211c5ec187a3c98fcbb511d764d99861c1727dee1e21fbcaf7c84227bf7731995e0a1ef9cbfd258c582a7ae19cb52a6ef046f035a54911591542125d1f6c4b2f5ec60442eec120ae41b37d02c075d891de1ad3b2e2cab012d685d566bd06cd06d36783e954e78e183c88945ccec4c6189364a66402c7a45f255e37e66292e18ea1186ba3d413fd7a01b8b42f6c952a5015341cad5df625e47225ff316637c3678106789fa1c3c49a2f3972b6534bdbd913756a20e25ea03b960408ff617fd5f4599dd53c63427236fcfebb6ac7805c8737d33c2b09f72ec2110e82791ea303c3b608b5b13eb15771c9051cd9da70ffd41cdc535681aecacfd88a1be42c04dfd3b2803387940e91b800275714c591d40055f26b3eb6b942bff7c347c49b51f565a9588ce6655480d621378214a1d1cd4a6567451ca003603d1217eba5a3be9376f48d7b1bc96eb21b18c326d56f802c45f52bffc7cd9a40adea9c94f8b795563c177f281b8ea13e453e84cf816fd31a96dc59b8dab3a0c1acff6e6e28be2b2c15c1c89d2dd3bb1a92593539d5279d881306720588f9eb73c9541b248a5e34b96b445f59d8f4e971b1c0d33949bbafeb991e157f57e233d24bd153ad167c2eda39901a1f19b00891218b808242203653dc6d204f81c2423a89ce2d05fa82cd302508f45006f0fc490dc255e74a4232530bc19ebf241764f68b8901c0944f7e141a643e9cfd1201946f96c5efd4a09b7fdbddce6a0a2869c1079fd447f4180c10b0161909047c4493338f3368f7f21cbadefb080fe3bb27ccc9d91509581a1e1ca5fc0fafdcafecbb69a93d40354d8925cb7a46767eed6bd1c277be8bc36ac6c9b79523db6cb834bf1852e3b0a35b3561e7eba16598c3e3fd9eab7abb2f39d8a4f564e17b54f483a305580a9e3f879c3792a685d7c62c923c932ef008c756c4342d467f29e5948ca51f6bac2331cfaa5a05ac94d077c53f0c95fbac8224fc90b5b8d6e011bd776a9f081e95f97db77d60b01741aedada47ff51b9c318e639db6c668dea90d1ba709c48471ce1470c931646fd1d64c6b59b175a6107144ae7193796f480327c9538f239896e4a475ec30a29a98d0c2c940284dbfd2801b4604c746bd9685a0ff9091184bfcd1872745f26264db828c9d705f26df8f733c58879e3b8fe128511668b6dca673983e377eab0f9e44036b8c16353ffde6baff9a148209cf0b86fb74d54cd613d89dcf375c70bf1ddabe97fe855fdd49a768703e20b84e1d15fbd85b221cffd6894cdbda6f21cc0ea6b72e2adbed8023286d1aba504677fb0ff3b1eadb6549aaa84c00285c62abb9f8bdfc0f69c169278c22885fc6bb6ee5c8805bbbeee11472a971317b3c51a27ffe13c87c38b880c166b6c10b856c4d406355f32f557c7b5ca2404cf665699930bac5c7850bd026616d7ae02cc65035e602abb4f40e0ef971f7c3e11b91791273974426cc13d2b981f213d3cd37923ef2f6d75249eaea1c8079bfc6212f4bdc9d5578dbbc1c38471f306c6c90a5803e65f090302aca9fa8826c786e9cd9c5bc78626ba51011c6d2a741ac307e4f9af332faa5c81aa4fff22b6215e85409091187e41dcb551c8d62ec6725f686857529af9a214853f069429cfc5ee0528bfa9faa710ceaf4c0933e83d1cb16354be246d5dd563960a1cf03b3603c24eec5d64649fbb69587903f06c9d99caca7ae5ccba4698417e6fd17bee08237cf8de87709acca4615f31d7c1455633c527cc25371d2997adc65584343de41053f4f23db27992fd00013f69c079874a9fc74307d9f25b863c4dc660a000b8750a875f61c7be16862d8e004c77302a03c292bec3f7e8cb904cbeee85f35ebfb998aed94b41910046c0a959b82719a1fa17bae366e60ccd76fb622ee089431e865d2efea277f170bb203f9e3dcc1de6999e6adc51b93ba9d6aa48102051f1acefecab1ca71b4419964b639c3d07c0f13fcb88a21ec6306d41a78161e24e8ffd910424a313f89224d6dcff75394b51711945bd5087239214c21dd8f22fda18a1d7189626b75a388b454a7ba8061854c44e824c30e45bc25e0e70e9e47d43d8fe594f333d254610d9781dbd4fc1366e7b28dbd1903e6f9de267c8aacb99d311d325e612918adb813c0a863ae8fa772f", "spend_index": [ 0, 1, 3276246661, 4294967295 ], "result": [ "827214062735032eccfb319cd4d6b28b02bcdd985d6396b5df909dfa96a81f21", "6631ada9d609bcf0cd52644496784a814c9e6c79382ff72681d1cc48749f770a", "b06d98da0a034ae6cb6e4525d057bfd85ef972c253713fd615dcd84e4bdc6cdb", "cd150c050a63027a78fafad232300fd1e9fe894d46bd0dd41c8594399e032cf9" ] }, { "desc": { "Inputs": 10, "Outputs": 8, "Witness": true, "Version": 540583660, "scriptSigs": true }, "hex_tx": "eca6382000010a1b2959370000000000000000000000000000000000000000000000000000000058eb05befd5e017416f0a12365fa7a467985513ad60df24f5884a0c5eb5c40c0c006ddd6a7ef321ae6bec85275ef9a5157ddb8cd9b1c4bf1a918ecf553bf01542a3909e266cb4b223ce3f144d145f26da57bbe750253a496d74a60d184fccfb7301dc703a3d418550c50a31b9155a2d58071fb7b79a1ec9c20bf6d8007ab34697179069394ac08f42e30a3ea70f74579bfd7a183826971be9f7684a970368cffea328b678e9858486d41e8a9b5fadd2e3ee0f46a7da925992c345679e934f918a3d7818ca84790e9c0775f876dcf258935cf476fc7df4fc127380fe218b1d6fb0c91abf43a2b60269003c3da5358785b7a3f39b16a213b31040d68078c974c292b0fd3e597c18ef397e44d15962c7285fcc107987fb173e9de70304889bd6f7f0def8e99a93c949495e4e08b7435b424ce55ae705706dcbec5eff75ffb025a09586e28552f4ea2b5e581940bed77e82932f0af834d9544d8fa62787f64c3e06263cf9062f93381b20f6642af6200000000000000000000000000000000000000000000000000000000899dd342313c445d60085fdd920549a80fe1a8a076cf71f12fe9c2d8ec62de672955765ff1be6ceb495b7162687f718a4abf41b06c3ba73cb19378418ba90000000000000000000000000000000000000000000000000000000013708f5e701addb97535fda831e8ee5bb8e6ba211ccc496fdf34813b15159c09cbb57ecf39cf1f251dc1a95798957698f0432d3f4caa636cab418ce6f04bad622fe714a283e38e178a8be62c83f4e92dcc829b0695851c08eeb98990aa3ebff22eb59f9363468b8eb0036f7266d6a2018a0a82a1e419a47142189b9654000000000000000000000000000000000000000000000000000000001539f2b8e5148b502f3b0fd8500c36adc49725b119e1dd5ecb3ed6435473d648b66adaf502681169af50887e28a0c608218a832b2126c193e4739ee8174fb751b3c985fa10b8fcd8a795b73b1ddad338e7d47245c78113caf2e40985085b89a7ab7a6626d8b0c991b3307c4192fea89278ec121fa6959f9ce84f5ac16493564eb43b7422e6bcd30d6e3ed61da77453529014a8f169908a47c2389e0b8b238daa8c464dbbe2c18f05faf933157340eeeac36204b5890d6012d58d43246094616c475abbc006ca307cd29220606cfe258870a2ca4b80b711dd02c5913efeb24c7ce465f0d1c2bb67bfa42cac8bf3efa6b4504b00000000000000000000000000000000000000000000000000000000dfabed5f40a981079a2ef0b439503ba5c642b2292823242c3e42fde01e048262438c59e53a7f6840b34e3365fbdaadadc96129dd8d82fcc280a253b8998557259f4969949232a6ea5e37c310d700000000000000000000000000000000000000000000000000000000fe227dbd10923aa7ddaeec15337a8a025546993d83230bcce566316fc20000000000000000000000000000000000000000000000000000000014ba700f00f2bd0796adf9ad84000000000000000000000000000000000000000000000000000000002578775617c09ea50d01624ac11d4324cc923091e3749ec4d85050c5763877dd198398a50000000000000000000000000000000000000000000000000000000006f28e9e009bbda5a458555b77000000000000000000000000000000000000000000000000000000001a0878dbb130b621cc86fc6307746f66767524d3715b546bdaaebcb43c655a0463443213672fb137d4a269528037611000fb24aa0eeba1cef92a197bec1bde6170969688b3427e0c35715b97250fe3d7009606b39c730beb3b5b771aa3b1ec49fe6db398af5ef121e24328e9723fe2e673b91bf16be49a61ffda09c8192269355541e0306ded74620a80c54060ec16b38752be1b6e119ec9c6778bca4b9b8283481a22a67ce32f486790c1014eaa4328b6d6b95bc5ca4a4bab26085c8a8a9c89047b4bc8bea712a0530956d1c54a2acfc3004eece4887722ec632fd669c1e9a6de47a139b2c32bf4c0ae8a0fe867afed261adf40b2eaa67023b0e50bb099463a1903b5acc86e57908e72248744b11efb4e044f4bf12eba2c255335ad9e2f19719d21b340fb298eaa5c0529772f9fd3f03e2c9e831c2617f237597c3dcc19622c40b0cd80d4633671bb9cbaa53a29730c2a7c102d00fbbccfaf728462b5a361db72e9e837145e0113fb8ae94e62d66ab5c5b27eeef73b8d1ad5896520a8d7ebf63fc99eac362a465b38e43ebf1ed0b86bbaccbf16c829a5374ec8ffad944092058b857af89b79672f71d3420e0695e400857b6b25bcedc31e3efc5fa648d4e6026d6b184f90ca8d5a67d350e849d0da3fb8e4e205ed8b7aab2470a9415a7a4e89a15bce147d063c53f69b47ffa2527a4c4e4d5bf505589474a798b9d708d50bcd26ba315bcea192a97940704d4c13947262dbcef9a3546da9be116b990e93d32aed1049a1e66f62c28c70cf0a570e79fe8467178d7c6664ed39066cf263519321d73930a63d4f85e4cc7481685a12cdc90b77d21b22e49091d2eb33cce3ecc974c66a0b0b2ec88ea628e076980aa17a99d0abf941a9c4e980ed588ecede7a33659df5f9268c0954fd82c8451679c88ef6eb7f4a8ffb49796146560750b0cf58e6fd00dc917474447af20039283cc37b6a4f85fcae3553cb110d10c052367099a20e59d25a7f6e0f0f373158c458ee9282302c549c4c48f0c261b3b1114c279bc6912dd5bf91ccd05710abe7b80750bcf9482062cef48532aa866200d5c62bf93497e97cb978036de1f3e76098ccae2368b6f872702ddd3a852f6cd13917479cb9bd1c6312cc09855a7ad5b16c0682489dc1ec8317f146c8bb52533e9b04cedf3427db2961f25e9a5b0607426e68f5acea2a9f20d7416d89c1eba5467a7141962d4d8b168b7756774729993f5f4ce1bcfc06711141dfa5bd44884562759a4ba1741b3dc216fb937d945c30bfdea11569398c095669ca7206ca8c1aef50580fdf6453c3d30c2de20afa05de9aa82086631d8d7edf225a342c6caafc59efe071e6f24ea027299633b6edf0204d5cd6b59d32da9c8095239ef698917db2d56b06e5f8f8e3994cea95de12c2abfe5783d72104a1c6c581fce3b89bf6bc419ca607c1938bcd2462310672c8dcacb0b8d2cb4183854589a20e32f6e81dcba5303ab663e924fdac9f9d8b9fad9736cf24893a401a75b33db2ca045c329b8a17afe8205ba61d6d27935c15274497b4485fa5a7d6c348b2303649c4e3df992942fa416f1b883e6e704331e1cfaf08796cf4b33c2895499041b365f52d9ee1299a90811aa06c2797eb74691e5fd1b38470c4da04e5dfbf153b2a84cab6f34033af85aa8485d1155e005096bc599586471913c9c894c16b83c8dedf8de6e7c9be350302edb6d7bd3302794cdcf415b0afd5db683089530a4b23b47292ac2bc8b4c1ffc48096aeb92462b6c4066cd6b31cc03213dfccf1936d072877687866aead5366e3bf33afb28d954e168c0f0fd9feb0c569f97baffc260d6a82a50177e6569ab96208023c0005773c3c391680f3ea4a46627541a3d4564a59ace01e4a4e56cb62a5c057f15b4608ec83b71b375c6df25ca3d8c975313a7a5ca6cc942aacbf1c4fc52677f7ad28fe9792b7e60d83a9dc4dc26afc70cf6aebf12b5357d014ce0ea09bb5d8f658389a68f35c34a577450ff1a11916e5896090dcf0c7c83136d5bd2ae45f572fa29f717b87a2cec448c8e7e937cd20f625c350c8cced19594e84212a81ab3f9fee28df481022922b278a277e84011b6d178a3ac145789a017fb6bc5878286d37dd9763ba8526b3c0a90cd99a9c37b965ab39b7df931ecd8cd40c40e5595b3afbbcaf2f4e05232cf1767185fe6e9abae7737581a06a360b7d5f2067ad6766c304b5744ca283f5034407cb93167ceb875b4355cc352dd9f02289dd8463ddc1e2e1f31ac4e065fa3eb9f570019fc29a0b5584133710cff01560b484b7c99bb7104ce2dfea25e01fd0a2a41a5c9728caa92c497cf52d5bd04b509518c8090348aac975d2f4674edf90bdd3f5d923e40ebb3848b11c93eca74105874b80169b79406f04d33fcd625ec4119912f8108f40f0936fbc9600d6a669a3094a35f1ade8296624df65d4c94168887bf1c3c80eca6c70e68162f567856f5be14e0ab8dd80a534030e475b20a00cf157a69314b71706e8f40e6e1ccc1162d5a243ad37214ec186a6552e11853af4277bc8aa4a87532ba47163b690425072dc211693fba20ee91fae2100c85e4cdbf042ebba8fb560cb1b2853b74ac7d17f2b16a2f57c0e33c10d244a7101db2eb346c84419dcf70f7bad2fd7a5c6f6aebb45953fdd40d86e537189b591e42dce0ecf67c37b2f66e218d26c7f1756c28e914cc652f8f38f4bc96bb04985ed55713086d15d3bc67313edf497be1863d6455d998c7ba6710123af616b194f910fac6559650777058d3d85fbb828bf537bc1defd59bf50d21242116995421235049686b68a173cde85475835082b0a39dc515fa935c67876c233901d6967449c166b7251074671f706e3039e1f58877dc2049a9a0ccbbb5cf1934b6b0b18e22aa570254978bd8877c2ee99e758d1fe5bad4e60c2232c71556b6507d401fd990191a7f99349034b90cd3cc58bc4537b41d5231e14330a993c734ec8848d6907a0bc2acb7dea06ee8cee593e984b07451e29ff45b4685c0c71e84471ecd1da4f1d4065cf9fb5e8a755e07e701267e2b2acf361831f3c04d836369fc7dc8d75acabccb83bf78687da52a6fb91da04e6a66853b3995120664d74f5eccb64e739b1339ee0d6b898b415cfdf41edd5966c71d2d2fa910f4369301d874475aa535112277f2df606125b8b932da903f4d92d818f31591b48ba8d1e90cca8ea989ee563262c63e799a1f3f85f03cb82566f6474990282f39634a7df688664482e6a18e05d751e56b4874d90208b9d2fc07672fdb16b1eb8640fdf679096312da8603dbc68f1d9f705cbe156f503da93d2606ee80cff3befce1831d6bb7ad20408dc7f2dd634fff562c660711d8ea945ad551f5d667f225724141425bff0b550cd925e36869c989b205a41421b7752bd2ea8ed286f33224e701d6bced64dc97e660ed89eea434676f8749bfd428f30ee7c4dfd2d9dfff48761452418c4135cfcc2bc1c071693236c4b6c974591e76f48cd71651a7d9e6d91a99afd38e2e804fd6501403161f01b785885b809146a5594de87ebef0eedf391a9ca80828910b77d08f26f47cda7911b0814be41116670401ccc9a4c920a990fa00610ba84affc18a06b0ca3b2121c8db48c00b841ed858d113afcbb460e7c218dc579bc6854e86610983436e26952241a4b20d9c7b90ee1dabf1c5702eb46fbfa1b0070f3830066d8e9f1899def0cd7a5063c5c3f5ac3b5713d11a1c4c5df1514cae85844dc781d0708352da70e61df9d0e5076e5a6ccd42112f0b91b4599214952db80accd5d46e1796e3851c9e9cf9510e1f0fa273ac037a8ef7439546a763369c9e539f1e8193157ba9653daa58f99376b37f485915a6da91651768e94e3cb9fe8cc7b6a395c133c230b18d5d5e03fdf4230b06a5a8c73e012792152df55d84930855a4f7dead408e2ee2880fcab4a8805082f1ad8e085f4b5290db413fe63f6ea3c6404adf76f1bf44478ee83118af2a93b5f2a0de313157ffdfad9ca22e3dbaaf932c573a570a8d807b13807fd750102e0538f3001a0e78c73b4cd7d051213a868700134cccbedf1a2f642270d15dc890e6c043eda2d013cfbfd5a962480bd7ca757fea13d19a8a3fc14aef6ffcb326d7616426a5c6406f8bd8a760bc12509fa508a3592cbc82c729823d2f1cf0451c34026fe937e396ec41eeb93b2a656353d5492116acf5f29fd09c09f6edd9cccd15e731b990e611c323c6421226f6f1d3c4f2b234d217821646b02b8455b052048d65fa43201d7503f7905932696bb748798e6546ba9833e1a9441dc17b25a1acbdd9199f7ea0a80a9ea101124d47a0552ead5dfb30a6822245133f13ea992b04a34bd877c4dc5f2ae7a1ad26349dafc21bb37b5b9a6e273ede1eb7cb2b3901956f8aa25f289889c4e837f334d3c892535756baf9775ce67479f0d0114612e2910d2be874acb8ad30dfc4fce3c0f5093e7cf1815cff422452c16c2cc302d35ed0c3a90df9a39e3dd5dd42f3c7ebbf5bcc369b2a9da6c145f18b10128af116773cda9e4af067e2f5302c21c5daabf4b89bb02fcd2e5fd680198ca14acf5ed677ede8fbf224af0c26958fc93e90243aee7b8f678f029259bd89a6023d1be5c7aa4fe9a91030ba4aa78eac12ae36be61255145add8390dc901fa478ad9876e489900a7a2e6150927c32bc3161a8e7ea455b9e2d7279898d0c7b18349fe400ae7c481608f80d7c7c9d7f5341e41f16d1830f453dc07d951ca85ba4197f70e893bccaaa31c75a72c7bf5b0241c39910399c93ca6f1e8dcc95c41b5050ed7a5c89f2429315c181c672698e3b269aa894bd7f862107c76f0706593f2c403c53a6b22ce88caee9ae628d9a8f3efe59a6defeb93ca8cf40cb12a8586b8ece2fb625fa0d97c8ad742383c074f4d93c5dd489b27481f521f5b2fe7011588a71a1f0d43c9f128ca37396d31e65eeff3c612a5b210a1fc6bac607f56fe053ce5397647618ea8598c22ce4533f9b36ade39f520e0ce48c6fae61365873755303a3310d9292cd747e72609518f9b014161784c0502ffd9d198c1966c3fc95bc8443806b026cf2a6fd5001f6c7247dcdd6f46294ebe370717b4283802a01300e57f071dba14cf2bab2cbd55fc57798463ab50d0b411be5c675f02187e735ec8d759fb9cbf05e3a47d7e028ac70edb2c26c0b3b3e11742b23b4675e4a59c35c1fbbea3f9d10b8c4a92a06a071c6bc244e4ba2c246dba5a9d7bc54a2300df6c9b1b7ad188ad190140d86411b861812887000cebdcd995ccb93863371d3d8fafc77509c77335c5f91ee36da919c0e6e0ec564edc275cc5c63ec525cdc06a286c67a8f5993c8fc4feb87f3aeec61b4aaad5e6cf21ff1607b40bf0895e192c0e2e3fdffb5159b53ee2fbf64c0b2427f9fc2d468d289a78f4b52bb35eb98f385d9834a6331c8ea11fc37cdb9d6bb55701d0d52fb48d87e7d7bba0ffd17ddbcae4c8cdd7e3dc399030eba771d5136aa4d63aacf0df8978fc955b778252894e3e6c8c0214f89d4d64c8e5ed77603df7d0ac8608bd8cd7e0e9eecb51390c00a03eeda91417a187f916bb403fd91472f912c53d99c36dc217cec8fa487f7e758da52cf76266d4914bb3b098ce47b415b45a9c972607bb9286442a2de5b800db31c5985728dafa867c68e13f0d46881fb2c8f4776f369fc29b59d7e2b9a402b8ec63264ef6bab1798464814b377fd41ae85a4ad92ce7287eb57f2b9e5ff60b0dd2be159ce653e2f2359ad9c0ff0a606ca37da3ea43e8f5ae9c5347a385ff3379539a4abd6e4ad417eb18f73dd7c2be40170d3b92688280a28e3545f65c97440bebc4e7fb1e79fb2bb9ca666a62ce464e75552bd6b2273c7af7f4a8a1db6df2509fa555d48dc60eb3c332834ad23e62911bdacca0da95910db378c7f0231b6742c488d9cd986667f6b424cca40f646c778e7c0fdb3190609f0d6d2eb4c1d816f1bb244daeda4a109315b40d3bb41d297739e0c4abd41c518b8a6d8697a22b7d51be1b820bfe085e48eb71ac8fecb0f97cccce09bc4553c178568d1e08b8db653d35fd81ab3ad51854c8447e62c79f6a254ed65b61c9b677a37f674c40542a7a6347bd876db7e862c579789be482f2f63cfbc25cf7ade74351cac7eb49d6672556c4defa01fee9bc5abfb27956298c5fdec016ad62f9669de7650791af753320e7e4c2cbae887422c57826409263a7303977def46a0f93c766f8bba5bae9b78bfc44bcb331f4ce2c244b106c54667418bdb651d636ff6d4097e1dd4b9da01e9356ce4f9e8f5efbdd017b80a44ae7481be1482776d5e354e20e6b87034e85ceb2b60a4c036601e6b76f25170ed5cebd184d99d8f3b52016333ea5ec9ce2b11c984ade37ae1290ea48c105f64499fe5ced928a10ee54096ac29c9a46138b31fd7ebfb616cf9919e29d7958b635299817e2a6ba0ac4de2f68c358d01ebe2b00cf836c4925fa5b88bbac5e8521affcf2c8b0c4753c93fb23081e43aa162075db6e97ac327367b0967f30426efd6e11ccff6c9f10652489362a9261ab97603c52201d0c5ac75bfc7efeaf34a8044d22eae8efa46952baa6095acd3aa3ed8e93a82dcc2ad9ca16c68bc78d97fa7850607ddcf41b4ffe13a9361df48beb0cddd380457699ae1f30097167343378c01f739bb56547643671ea9e76058396e83b14970fb2df267a8dbad6cae5a5c4552c6276ca84ee93a221adc1de879014e2d5cf8d3e5d4c8859feff2967696ae0efcdb570fb2f2fea3460b3adc335d2ac666ab75bbace0570dc3aa0faec0de808df6b355ddc9e8b6a7e282dd09d47390e4deb7c3c5f6424c069567ade23e2f73335a3b4919704d14c0354a13e968f8c7c62e0dc23802fd3a018e66397d222b7ed9640899095ca33db4bd5f77b01ea123b78a2d2cd0839a2529e20faa40547f30ebd35d136bb470119914fcb9f2d67df668c4474cd290839379caa49a135556b1044fd92e5b190fdf870ed019e817bba3df8f442154fc0dc6ef6eca0c2a537a418703f68ae2ed9bf945ebe6228a4b2fb7cb4de379bcb0019e7e00c8f47fd83614f71ac3964f96dc505d549ce5099ecf519f394876012859a922d641cfb874b80cca867c51dc4a993ce3a41ec6eb77c4be3628f8b95a0d4850d2ead8ff37b2c8f65c4fd518d9db0050e56048021bbaf8841f0d1553a514114e39be9e635de258f2ab3d1cb4f4b03785f0be9bd3bb35a924a8b6a813c087a938faecf8d421e1a2eaa30dca1e1de99ea6fcef7eb7134dbbbffb43472f2391f35741cd16e2dd7bbef51989e2c827a997c763339cf6f7b68ccd5653c5fd2c01841752a81c856ad4f1d16a97877cd5bc22d9b92250bc741b255d71b6c802a6bb697a4cc303f274ff0136e613d72d20f0da7609a05e448315e15443eb95459d46d348a40a526d3b579d8e03beff7e4dbe07d729a69aa4736119d6f38f45cc64e487e2840a1e7ed1cdc26caa44d1822a80933d0f2586e92cc540444799fb2fff9c42b1b460dbde0c812569f4f9dd001f513a47fb2d4934e914283f37dd3ec40ac45f6c3c81700eb990296245e0a75d647824d46a4c747cb63a8a0d167a7edf292c44a90481a08a49cab2c7fefd413e7a95cf49798b23a2367b7a23f47945eb562fe373c6b3117500c6db2c557a16dbcf0e24f8ad2d5a75c005e14c2e8d420fd682c2867571d7142a7cd460c1339dbe6acef70f55fc70689c8b0b5d235c7d9619f3f8c98f871960786c2ecfc79b02fdb7016dc578fc7076681fc7dbdd54f3391e563af31515bd4097606460678dfe38bde0aee6fc74b7ce15a0d0cc6b1326d935b00279af62ccdec1c45cc1fb5f4cfdfef8e94354e391c47a00e160dc5fffe1eacdf728437a1c1f9837fb6abf1572b653464f1e7d13484c36bcd4131b5f46eff4d7d9ffebcb0ae4f95ca07de8d448649150273309ee4841293b3028bd7a41388bfe7a8b6e3750771f8977fb8a4a525799505ea70a40a8d04fc77a65d1a8b687dff1ae1e718273436fe07c01611437cc0da3a9d78ca631a2ea61e10261b2c328a714ebc2a6344449509c4bd30cdcad5b35c5ce431fffff438dea481bb623b6362758a25ead121d3f0189bbb2c0873c249a7e9d4790e8b67a7d02b4654cc495a6bf4e82e05d9aa40411b4b222d89a4ddd91d03c8259fbdb30700c7fccf71f8ee0a84b87c96b6130349a230b56cda052a118dcd25c97560111fb1a1923aae332307e29170f3e3f0f6f708758237caa52cf887ab6d868990e8efff3b193e58e32631a68927b44acfb5ef69e8f3f54a274b1b50a213bb911e32998e39fae27c6d8a21ed160eedc7996f000c182d3f9860764512c5cdac8158bc04f365fc83b3e8aad9ea5b29ffeed3a6426fd32014198cfc593a8fceb45f35d4522b1a40c35d1797d583ab683453b696169f51b7cc66010ec636141d3a079e5ba1e45d4dd927396262ad604c91226f1703f4fffcb5bbb6f9dd102cbfba053159c1d697d529cd3b135fb0c45b9bfa9d7a0d21f2a999c02111de9126921401ea2433c857810c587a6e6045eb3c585048c0d1017ac1ab316e73ab14c0fae2a90b8d0885371b25d2b4a4363780b73ac28f7303096c1a7a0b447695a49acd43916c41720016ba7c28b722b1b60b3801049c9d95fa2abb11961d532dc8afd1bdda644e45c08741e4729052200b2bb830f66fe0d2b5ac4ec7cbb1e74f06ec89e8a2d2790bb46051c66477bae3dfb3e78b486a26ee6bc120ab39bf162bb0cefc18b22b388308af39ead97a9c26224934d0805d5f0e4c89502076a5cc2b0cfa586823223dc2465f8fa946104fd35012432cf5a954253ee24d33d0711048d520d4d6049e1a2ef952ea5a45e892ae556561592fbc037569b56d9161bcef7855df6c4b61df9df42189b7337e8559b03bd0057a0271ba6cba36a93338d3a74df074b56c919415540cdf3e14ca306ec593b374ffdd54ec5c7b43081ff93ebf877df74d8c93951013b32a31036e3a2b2ca3ab313248ebeea7c63d03bddc7ac1b004026961da722a6ddae8f1385c6b0b070d2a728c6fc378cede984b2dc75521dad85f6e4f5e8ffeb854ab2ff2b185bae7fc034cf039c3be08c8e4a82eac1e776471daac51d3017147252512810a1c643f71a5fb170c7ab15ddcdcd7effa49e9fb51be624da65385ea8829016d97f2e32b833ca639f7b65a4913c85f51bc099e605006102d52c9a3318e997dd8c0d703d51f0dd0ac5204ffdf0af1cd506690552be501dc67d4f93b2b04c5a7b41852944773eb0dd368cfdc5348ac25807ce2ff6c369be85fbc80c34cefacd046055e8024b04b866d8c13512f0a32927d4ee1418715ee16fa271afebe484ae13cbc54b08c194a7f59672f097a54073edc26ad506df819494a3e2b8412bb553b430aee57ec5af7af3898b936054867a3b8858592b22edcd015f8c6e82789b3de3b43476aeb18a271006e55aa7bf9fade88ab41038d8d78501fdf474e9eeb6d8d4bfa7efe7c8378a33031b1911674935976e5975935b4894da051e38b239395f69d161dd13d9a2f20151f1a74c369243093e527b348cf6844a3d70bc7a7b5d4e4a1fed3fe05afc417bd1f7a69b955a087508e06495cc39e0052f90fd0e7ce08d1ad17cf47875f12accbe1c5437d32d914e4f5a00dfe4037c966b697387820e658392ab4fef9a4f16a7ce96c26c8a2653fa6c0c6dda5e9a9737cb01be70e99f1b04fd8501eec86a30165049082f9c7c0d2471f47af1b0f993543bdc3819bae2efe30b02e62cb4e808ca022696c85f3531d5bd869fc2d29e77415bc623026aaff0a590435b186a557ea26cf2325c4b78f381f8b3d9efcf900fb59a7d1a27f2461130ab30a651a3a80a3b75fe03ed2ccaed5ad089ad9b30a4fa8347e5aba26de02d86f6d78615e97079d8ee54b64ecd23f5d1dc899b3788a8ccdff2ba77600806c231051c16c0d8a4bdde4da2ff34ce6581887600665aae4a275b2d6a73b72f5fe71ef7a3c8479ee0964df412bc1d9cf1c51153371acad1a66cd75bfa0da9b787a10df89453e350a0bb6a5db94cc040e5ee878ee05c2e79620d0a7308472ecef9d695403c8a6ad6e7475aa1e1c3575ab6c2a058b080f3408831c5b7a748c2a6d38e82c2fa8119ebfd09722fcee42451d27a7989d84673e0ad119387425206fb536a1b40aa854a5f8ce70b453fdac63b49a855586b646720e29f7999bc65de20da89a7c4e33f0aa0c8d35bfbc96bdab180e55d8ee1445c0395f6dc3282244573acbb29b06abf19d13a01485aa07fc1d90b3e6256e75c91d77fe950f207dfc7841ffb261df8e8aa35ee38cc642cbdb1c6f4ca18a5085a81192fa4fddc857d2d24ecae4e8107392d8cef006900f67eda7200a0c01a1cee45ea0cc93d81b53e5159dcb87e7576daa90569297c73d4a75132871611c399adbed987383e9f45712f8f0b026d8241c0c810546fa81397449b3e930bf2c604d16fdab584b4a01062ab3b7e7d80d0d69dd6dc07c9255650666083d57aa8b99ae2be43641f6ec6d0371e6a65c6bae641ef43e228e6bc010d171cbae9a951237b17b75e2851777cf8ce40a18c0abc114dde6733b9ed4e15eaa6a7fa65f5872f97909986c887cbd7b8b21df66b5b76b5c11a9d79d572127d9f77b87c589be1234d00932d91e05f36a87f5f6b105001b83a2d3f9f2ca6697a4798aa0bffcdad22f553c2b71ed186a249fd77df788b51bd1da5bce6591110fa5ad953dd24596c7a111b044d7150d27755f0935145e239113e7c71304600004d519da8", "spend_index": [ 0, 1, 2308355850, 4294967295 ], "result": [ "241962a137765351217d9ef8c911be846612adf3f60c4e6abe9e516f9368efa4", "902f0a031bc46def0bb073cf755834f92bd3cc883e79a3081d5f1499058d2945", "fc9b00664a458bcc4e9d3c915f076f6fda75e00bf928bcacf7f1970d8f236068", "914a0b3690fd8c9e420babebd7f72782bcadd114292b323871e9c909039a046f" ] }, { "desc": { "Inputs": 2, "Outputs": 2, "Witness": true, "Version": 512812821, "scriptSigs": false }, "hex_tx": "15e7901e0001024a0793a800000000000000000000000000000000000000000000000000000000e46dfcf20003395607149b029e0000000000000000000000000000000000000000000000000000000070a5d5fa00352252f8023ad76c595589ba51c8def3f6fa9b8e0fc3116656d3059d39b7bd8de921d39fa1fd4bb67d447eb67325b5790855dfcdba5d4bc505ff9e793422a619d4561c30313625fb687f6e66ae2d8cd9f79f9232a660db6e4235973e74a0c71d6762709f55255a9771abecdf909a0bbec7ac4dce3e30116e2b0597f56a2749237ae4be0c7264d1d7e2519e799d4147e1056cc9ff602bb174e576dfa07922a33bcce25ad81528004776abe7601891a8133cbc67513b74d4ee4ca8f2a8b8f474ea5a081d62f40b29a385884633e500455b2fa0a445b3afeb390ac9ccbd0b6fc869ad7a66189972db43728f269ee1f60c08fcb15dcc77c95595598f09c187d53586a2342e1c2296988a4ecc0e7bc9899de252a960a8e0f0f6d0cd3e4dd64d63fc80a7dcd2c218786496b42f5cb9b06cc42f0dc9fe99656b83e0e1851446d481864e3d5ad0c4f9a506e58be09ef02c5152c80497d7656b5b878ea523d58dbdbbf526001279d339cd868b1386560c9b3caf22f09037d6e3005c0e0f89850b11e71253e6d69b5a9f8157bf5c6ebe32ddbb7f3592c2fc4dc2cec13670faac1516f1f61f9b83f97fa634b701fd2901af28d0d6af102ccb678e7091497ff5df19db99f80545e839597da96f2d45d0044c09fe069bc9d6b3187a4b566fd7adb1194d7a1a38dcd310e1abbed51a0393bfc4cbd2f2f50fef07b684bd6724d974c9ef13622b8c92a37c78c4c73c991f041daed55c6b579779233937cbf07c8c71af8e467079a91cc8eebdeba802ced5c3f07d8c5bd49a1ed9b7060032e2b8344d8d11b1ef57702bf61a3a0a90c0051c55e1002531ad86cbbfa73dd029fb0a378c452e5979059400b5a254e73585c46073ba570cddab3c945186183b69993cdad1efe8c8c5b6e0f5495ac446185a669afa53466c3cec852703ee14530d493104aa2cd46d28347789a64321bda4869d77f42a72b213c9d8bc478f41f7b826f98180b5d3d0bf5a0138961adbee8de726a18652b90693afa5e70e330e015f4715c2700eec9759586d17bfe29115ed0b4f1d985b55fc70433ce410ddddbbe851f7b9ab0a700c881eddd74fd9b535debf7044ab164876ac2b0752da7f798c6b5a906b814ea3a87354b1bca9d57e864caf4cb4e05a957e09b825ae1456a9e9607b49e6", "spend_index": [ 0, 1, 2378452061, 4294967295 ], "result": [ "f3e2c3e73cee226c724bcfeafe2e180f662a29f7b2e546aad385f4464aa90075", "4baea604d850efc9d770ef491e5c32b0eeb260c1f869c91c3f9ea955db773cde", "eab6991e813e0da4acd7ee0b43034b85111c9525fde3d76e8f5a88c45c443fae", "f775ddaa1ff9358095533c708e1fb1d4b59a62c4a4408f8da20a8c1e35474f3f" ] }, { "desc": { "Inputs": 5, "Outputs": 4, "Witness": true, "Version": -34418595, "scriptSigs": true }, "hex_tx": "5dd0f2fd000105dea0b0b400000000000000000000000000000000000000000000000000000000d7b8be27aa0467d1c01b3e20179df275af2b2be933d594b3f1ee3012b531f19fba4b8206c2c4831f55cbc3056ded051abdb0951bb3bf86434780a6641286ed94c0fe40b0bfe008644bdf90526e0acfd68ea6dba7157712a29e9333aac123338f5c0e42d8c7e35bc1023a2c38374b251de13d77da8c6084ef2baaf0e41fcc000a2e2c2eb4ad7f0643b5905d0dbc8244cb35939068eca8fa3032e3589e88303f65bf21fe992673b1ae1df292b397bf0db1eacfa09d65cc0000000000000000000000000000000000000000000000000000000000631b7567fd75011fb4b9126b828c61a96b5fb508b52800529ecfbae4d802020d68194fa39bfa732e996d430004f87c18ac56575f6bb65f50cec46a7c545719d4c52aa4e7bc9ae5c97b1abe8d8f4934d846b5ba81f8a1ddf643bca6f695f8eafbdd1f844fe03ce4ac8aafdba6433895f7af87f297c1e75892f48e44bfbbe69874379ed157ea5e4ac63a21b6f5d054a44273f3ebbe4d8ffc69883cf7cbb70d3cc91a60660e6dbef32068b3ef11c09824d4b6502da46f3c0e26d48a6df4c94209729691dbd3a42fccba99755f076301cd3855cd2f5944fa43536c56935a4681a6437a6ae7816752986e280b215fbd37a020c1f1486cc217b89a60d71f9b92c79e7a254711f70190dde6465b2d9b7b513988af7d982afb5ecfac13eaf75a7207121e4445b7453347761d44d5d8f351519a0a36c9b3a54f8ea8df077c3e1c49ce6d382e45f8b7fb99832cc531727d6e22ea4c47cdbba7b4621e00bb7095d23417fb0a26f9126ff5d15dd1c9ac15f00bd92739d86f9e2585abe9d2b9f6b45ae79f4a27b323dc1b000000000000000000000000000000000000000000000000000000002bc0d170fd5001bf3b7ae454bd083802e76cff30780326bdc6315708705027731894c62789c6ed32e6b63a2ee135e0da4790f3dd6e314c1f422db3d62c34a40c3c92b8e9434782e01f6550bd48e63de7f410bfe49264e8dabebd9022a9870b99f1c9409724388896e14de887a475a1fd2e6f8f44a9df2b5383a3b771d5ecc8a912f2f6ac8991fbf70ee0a3e9730d93bb65ac9eba4ede14f10aaf5334fb3a8bebf5d749168d2b3505aa629a32f09085ae05662e3be6b40ca9692b6c298febd38185e3fa40ac227a2687687f99324f5af277f5b8b6aced53036fd6db237ff1940360c2a6a6390f30c230d0071124ecf0021058b3743c3ce19bee9479dbb3b93af8573a05d6f470798c967b741c77215d1804b45c85961b3da943a6716c0f2d26e92998d848a94e04c77896d39e38ddf4192e0205683d1a15b20361302099c36e04325073459e9e10741dba07b5b8a1d441e667cbc4a8cbff1eb456f1ba401bd000000000000000000000000000000000000000000000000000000000118e4304fd0001a0492948a31ca464437f8b51dd653e5a8d27b3a3cae80ce3a237b0b08664120a8d0054f7284c27e2e09ee5f29f2098d83a1974e07867446f436446c99381a2f8b671e2836c64ab761dc907f4fd6a6031cd9e8deed2103ef187e94a3e52e6fe8584dd0a1fabfe13d164d2969172029336bb9117cba93fb531d0a6149ede0a1c230c389e71b1a0e3d4210d57abb36dd43245c8938a413d6849dfbfcb23518aea00eccf19bc491043684094ba550ca3571ac254d951ee7fc9189bbf64c4e05389326110de944837cb6016682aa23becc69e523418600f2fe4df6f1a84c5dd836032aa8e18b15f2603aac0f243a4768a8a53901dd9027985a6b14077f036712b13b1a61f44fb31eca4d0000000000000000000000000000000000000000000000000000000003b2e502c00ff64cd4c04673bb7df80bf5560c8d0b6f3d54862ae8092b5897be0c7cbbe4cbf1ce9fc0748f41108429cd61f8758bd1ddf191f967200d5c381e6a4acb3cf174dda433be118f9c5a4cde60970b7645a2b1cbe9db9b25980c5f80583d79f3a13bcb05adf6fc22dbc5e005cf57190b75230146f43e78653c41d0206abb9119c1c4f54943e161204cf71088176778286d9827a438f322c86581c3a6db004e1b5bcedfe48fd1a8da4442284a44c5cfb436b624c008e95633c4d36220f0959f31c037cd2ec3e70c70e1dc82779ccd2cfcff99fc40cb26451aac681606667757255c8ee0950071f736d4957b49d3e03b3ab6a65e136cf117bbb081d7678a4465e66a5c3fcdbcad3fe98d32d21c68c97400190ba19320e0f8154bb9a9d98b577973cb2b97f83a26f4f86ff82634c544d9854da78508a158ef6937a7a1bb80081365e7e18005c786a84bc69028aaef5cbc0f7b0a3af1aaef8c296e1e246f4e46c15780f51fe90d85e02db41ecd99e4c4b17950998f9d498552f006409c67d475627adda71ee723e1b9bc7d31a08c609ac8199cd2797d0f71134fec05c4518cbedeca0438fbb4374c57580218a0f50daa487bc2dc80bb9c1eb6c80bce8a9cef47409d6e3452b06c34901b1bc4f804abb3b4f0be46ea6514649696dbbbc481f949e688c81ae5317f70d3fe56166784b124714a1c4dc07a1202478c9ebadfee8a00e8e0891a954ee20d284838b5b8c3b26759a752704912bda1815748492dd7f706448cc744a89206fedacf7ef1b447a89a62f2cc944694d2e11513cceea6c66f973c320a6deeeeb85322113f45cba56eedd5acd67596d2e68c26ccb3073b896ce0f51b068b061b29bc9bdd1af51e967de89654884060b5c79ea98464ea137dbdf33a8223e7cc89dcb64ec22aea7e3ba608cdf4a0384351ae4da6b53dc1a6f8b1a1e15b27c8badb706540299c41a6bdd45a568519bc794d169a4008123da165c0eb7b40cf8bf96b1a3f9c025d73da7711b450ea122f480895a66552be9bd8832dd6f4e90676f5ff8da0735b2fd2a04954422c93fe2f25654b353951be53ee09378e1c0c9e157a126b727da271ed2fe66c5f00ab2c073494e0856eb6d2467fb4dfadaf1cea808a0fb6305ae498d1f935482acb505e369f81a6d0832fdfdef02a18df3b753668ec450835e7a90c7c45b03e293eb0f3fee544af59b1e641e588de3c7f44c03a15ed347d45dfc9045ebaa72859eb6a2195db9d6c8784941df9086ab7744571552dcd4bd1a401ba0db2a89d69ca1c0338597fc7fb4723f6e001729f65306a7a96214a4cb3a78c4071221d8fe75d6544d63bfb34c6f6555399f5be39945ddaf7898537f79b73b51b2e6378de128223a99ebe3784606150134f8c1d2c06c274ffde7a3e0dd53088160a7868332d628e319577699738a9303d71c552603b78478400daa3399d7024ce23a910857da0da88d0b43ed425b8adb81f478ebca71c9c1aad7483a2605df1f38a61bf627f66b81e914f02d66fe31df7fa86e7e5f0871214c4fbfe12e60b9eeb9651a84403ee77b326df29ecfe15af0cf8ea6b4efa286373d95c5dd33d7f9dc5dab83382a10545e4309af493ec64b2493db4ad7fd38d6e7e4a47a15cc775bf3bc473bd23730809aa8f6b2432537b19d60379e64baef1975e763b41c2e8e2b1bc333e07380703410ec08c907af0913e1e1f6dfb3ff95d1ccab1e00d0f97cf04532faeb62b8aad7df53fe0d03bc21d9718f1c0e57203b789f49182c50199b6a4919683c4e6974b7e0c09cf3112f483991a5622653b2852de7546e81078b54c104065443c33a76c09e95c1dc1617b97249020cfd2e01a02a27775cd019c4d21eebccf3738d066749a4cb2b6fc08347f7758d9e3a9c7ae3a6e12b963cf83b1fd672c129719211c3fc7a8f2ba62f1adc20cf4b18c53423f002d5f59cd3bd723eb49a2372aaa32a9cf8f12220c8ccd090dd85f9813862306e5a21e47392832fb6cd969ccabcd940e8891500e8f576c235bfba2df8f7b7b089a77e9eaba55f0ef696f7db6d5cde3be41a7a9c72053db92f57b29eaa77724b2525b6255c833e668fee16af35a57cc0da04070d63f2ce39bef0d42311628ab1f43ee4aca178783246182890d4c4215aa34ba506f6c941ea938b956da76a66536baeda46a86de0150b6b7862df3e3e214b00af8f1354ac5c8eb6a21c3e7619203219e698ba3e728764a1736e242a84f93062039732f3625b557fc97ebca48cc21c721de585cf5f998967e421567b04fd9a01614adde856ae46ca685ba073ce97551a4ed879c3982bb8a0c4c4c19758cc2164831a346639d34906771e573954500700c925b2f6a51298d79e789d6480d798fb7c853652937ce105d5c3a49d26934839955210780e919ef4774f96cee6980d407b0fd44b3f13b9ee4f5bd6db93de9587db2c15f0273d95a10d7840295cf4141d08f018fa727a75134929ae41fced1955f654d1bbc29469e3618bfeaf2e1745fe3925e3e1271e3940d67c96f03b21befbc20d1714dddf0c2ab5626645da21bdc47befe70ea38b4f804a9fcfa42be3120ab1ee9c94b2dbd40b651115d5f3357db7ac3cddb0b6397a6e4c86af2118674b0a284f29a95e7d2a51be7f51518550e6ba6a24634a69ff7892c00e0b605df08087c6404ff450b54158d4400989db051cb2f581e5166554cbf9480f9c26701ab4ede8339fba5eac8d41ebabdafe80bcf4aa9a4b474706a6ff39c994bf02286c6b4c1d22ea790aaaee2e5117ae58b34065c3cefe32a8d8c35fc44a52ee602bbaa28f681d04de9a824186080b078596fb0c8e1eabb7c01cf5f8ac9281c4c2a9bf5242f72cafda2c807788c702fdf301d976807e557699b6504139779edeac170108ea49bdd01365da1f0dd02ad17bad83ad390a598af18a5742eec870192009541cc4c740ce87f434c853fed03530ffa2c0fe254091469cad1ad0d3bf64485ba651f8f3395d75394a6b6e3d18a7b349869c68296154dbfb63adcf5a78d4e5ba7fe5fd04b7f3e8df84dbcd1ebe242d93e95a91a628410f42a1da12890ca5724e9d02a290ef2b4a132173f7961eba3653889e9a77c231291c34504a2b41f4eba0dcd7be74c8cf01101bf8edbf1d35a3cbbb964ec39b6c450b662aa056310397518737d28bd7b8f2ea919bfb1191df5bd7b7debda7789b51fb106fe52ef13a1199021407615d04c6e5ec748f930d24abe34e056cbbfe3d0644923cb114325207a72db54fd1da854d13330b58994ec176f0a22295893976258cf18b267ab3f0901783ccef446a50d8b1d579e5a9a2230d774c859bca4beca090a8a80f633833f82545acf797756e171337b9dfc938a4ebe6555bf3eacd84c3735e9b5b1fbaf4ed99d2d689ec0215ea5d9789a25d1a3d59473f9a3abd1aaf652bb5439c98331383cc0fe88ad63ac15d38ba5de539dddff619490ea1835503dd292a3f5d6439de6920c9f5b2e6cfcfa29beddd6f2725dd51e0f454ece859f783db160effcea252e14f6c5c05653e5b5425cd66643afef1df2bce5da42d1a2a68bb57fa1f9e11cbb2a8a89a96a4b6f22a0f93b417e0f211a77343a385378534923a783820d6f0df5513e0d3d25631fa3a827d3b2386a861f03d6589991c5104360511b5fa70ff8ed3af7621eb33a0e164d26a91c4833b2671c09db0da7c6485ba895601fed6b5a12379db12a4b85380fe047ab5bbae82c1c95810fd2bcc0669846b173824ac5df7b032f4fdff539939f9be2bb4be31c61dde7fabd7527178eee36cde414eb21b1df81ce8df8012388b7a08fd7101655a6d4bb9beb590b9055a7a39ac3980d19e8d0508f17fafc121ddc590971577988389f980b6794514f6d376276ecc41de2d1d22550596f044e1e094f32b5928bc045072b62547c5715ec3f5d3de18ef8a28232b98653e3a170154e90307b0f672cc23c678c4346cf270c4c31f1be14980b013a8fabb17570b18dddef48d28ddbaea98ff2421bef9ad0ef3b0b63265a65dfef5ee7bdce736fa61306ce38c969071983d5a7c0a7930e1c0776a52bae2caa03939e322ecef0fcf10e2edd26c92178fcbcac25db90bb33ac0f9ded141c753e46ef02876d50548cc3bcd03dae3ef6e5139df0e95b38c2ebe69751ff2b87e098903cd9921348bf7db8408b7a4e3989f3714a1bb4d88dba4dcf868813db4fb367f3c89bcd7131fc857b2fe7b745dce2b334a27e85d329aa0ba0ec710f6786e1341b7cecfcb0feaef3f974edc80f45bd08a8c1c23a6dc28f59390696f4baeeff9b4fb11ada633dcfd7fd2d00e7f2a8b09eaa2695b66e91e9e015be81cbaddcd5fae04fdea01957892707e0dd5b1dcec761df13fc5689d4a3a1c88c4a532aee371f11373257bc0e5340e0eec96e3c9ea5838da777edbccf467f043bec8d5206511511bfb9894a2fd731dfd5865b0db1f44577000da3a138eae24b5f9f8cbd0f68b88c22f8163ac44ff4bf60358d91cb985b90342316b372696a993cfe91d7cda2f3d1e86c9dec095ca4c2d85e5ff3fbeffb0ab82f0412980175a46b5a7acf773868762d61a614991cefd7d066aeba33d5e2f980912b3fb7d6a609757beeb5a6c2b8690a21449796103d21d20722312e75aaaa02d0b78f2a61147f853c28a7eccab5908c0578d0837d4f72720eb67d0fa9b26fd614ce56f69f574aa5c21d63de4d18384c0812c94b4d4d31d4f7262166bb8b602e400d4ce7d97505f44b0cc387c913e76cfd07c4d301a5f9a9c8491f3094e72e96cb682b914f767a83994f329e45b101a3a09446d8d6eccadb46d2bbadc5520cb0b8daba7c147ca18b65183da689dad812d1e3a19b853129de72d0937f95163ecfc32d5d0dfe99d9b9b5a70883c80db0a15caeb7990d58942391b4e516410e4436eae55b7b21c982c61413e5c14f3fb674fcc78c5997f0d84f962d597784d4d5727dd67031a80b6cc6535a9179040a0b4cec004a82bb0301589f22f158cbcd696eee7620679a5dee4c7b1fb19f94088d563bae0cf3c91cc8ce4cd7cd3ba654220a8125a46d72481a80298792386c1358973672a8fa065ac8a9db4c12a11d50995f69cfe5d09c4b7b1aab94d176c6f1fc6fa4c8d7213dd9c480ec3c485939d0cb623aa615849e2b5098fe561a4dfdf72dcfedfd93b2eb83f597242a707b52543c74f24c5fde9012aefece7564f60f70653e47a8afb3dfeb5e59d917b10be274ab0679da1d0efb01bca06e7467d59b759b9097deb74d92a3fda1e344855f09cd781c34ae1678201e45128d3f61c4cbcfa7a6b0b73961e65c8d7d7d6135d7eab3d9887d153a1866a62fe31063ccae983615d585853825d9b699325f167f150afe9f180182efb7fefd203beb9912812f787b73732791128f2b989e6a0a97d8b16c0caac0deeec65aa3c67efada1e3ea75a72baf5433e8e306e1c21d6c88556d23e4439d25aae69355aec9c990bf4b3d6763dfec018fa206b82ef2a42acc7cdab33da1977053dc6461901b8f4c6751f949e9a5bd38ad97ec95a2907c879226b0d7259dd9a215c092633a85d97034efde15a55c671b3439831a0a364601fc636d81c0c8cc8472fe916d47138577e373d2407527ff4b969cc24505da541a17adf94c1c87d21a6f3e96192fa1148561297c8d7046a88608b15549c0049512622983fbff9c605fd61d0ac016b124315e6303963ad5068283ece43573a27a31b5a76e227230801cb9c1d313d1c512e6d9c8422b367708818e6de2606540c3427921eaa51a15035e5b2c0d468bfbbdb11ebafeffd5f9f71e6cf78d4b24f6c82d8cbd83d81a145e666c4eda94a6fe8250cb7e76fff2669282ae0fe912fe6288eac3edd39af98ce67503d5cd159fc6cba2d1e5b8a698fd4b01ff61b99a491a17f05299167c6feb67f18c2832fe3265719cbc746e4ee8e81a7b41926bf00bf2cd53c50b55f332e19f957af790c83cdddbf46679e9b0c5ee2b3edc15ee209954e968bdf1d89ffb00332552de9a0c9ba40bebdeb96dad7d259dd833d76db01cad7644d661063bd8acc07135a829b91193fe9cf57e19d5694d89a976ed58dd81e5468dc44172ce77ca5383984f63a2e01cfb03069909510b604fea16df0f85e9ae6fb5253fa26bf95d8c362e3f5a8a63f89b89a4f343c08a49a626177c330af5e6dd57efde3b8a48b79a510df3f884fa74f5b0c567ac044ee3549c204f7cbda420d326eb408d3463a0beaf65a43c7c463cd6a5410632e0b00b483fc24f005e9abdb38e2292f08bcf55679e9e2e249aff0829c85bdb15386ffc98bcf62872f8da83d5a998de9d0d5c415b8f628ced24f3c6d4b35f4e01de471eb6ed449900de544dad8450b6930001fdf301f19627e2e6ba4611cd1160cd88212ade6eb28e59ddb0006797e189c7dc0ec2a532fe25f9b94fc5a7499cee0c17df82e13b5feca55e7d2906b21f72f10bbb38d846cbd3e546a7c0e8deda3ab0cb7e66c4c4ca17c2c94bac37b0df07adf949709a84c053eb30e67a2fe40a68e7195431dd7b05f78442652d219dc6e24aa3812e25829b5243b4cef9ca45d17d125f2ac2ccf9d1a48f65e1e116bb0f3bc94687d7b7722edd8db62fe28def0eb98918bdb4adda6954f62bd0ad3171f775f34a083a987c2e155633b6b5e1c2aad0c7983cba44879f024ea1c9518fd0a87182cf6bf2cbc2998f9d44446a0c20b640cab5027e70cf3a2824f217c9bdf5646b62286ffbf3bc97862a997fd105682085b7e6dc5a9059a060449e323719fe2961513ffbe08cf7dc043fbd1d1379839d7af98114b2c8d4841f00091a3aea14198e12d2eb551c049138e8a90f9298e22f4fcfc205460adf412228814288e47e54ecb30bd4bb82ec50d04dded7755888343fad7e0e105711ea1be72cf304f592fc4d5269dfeb4599d10a5ad38413cd9e522b5cd2fc139a59dddad0a95bbb6e41ad759aeafd9301e06e551bca8eb12985cb65a7df8a279ca6571a7e3598fe4823c7fcba8fe50e42f4f9723e678cc9ac04fd6086939b1b438c188bb3e9e716e6b66b3b1b1196aad184ea9dc926b26d5b654cb6363c5d8123cf5991546fe711", "spend_index": [ 0, 1, 1543102608, 4294967295 ], "result": [ "5b2b6e29a48f11326cad1fc011abeee3774099b11784271eaccc608924846a64", "b9ae761287f0265fa9c7ec44ad48613bfaa37d60ab947f7221319b40359bf38c", "6b37a42dfdd073178aaf1edff909c6fd6480841fa506127c46bd89b5f45d2d00", "32b1edbd1a8238185d53ff008f0cba145afd7ee4361191ee9dbe4a72ec5cb56d" ] }, { "desc": { "Inputs": 5, "Outputs": 4, "Witness": true, "Version": 93911642, "scriptSigs": false }, "hex_tx": "5afa9805000105e269c23f00000000000000000000000000000000000000000000000000000000ccb851b3003ea045578f9bb2ab0000000000000000000000000000000000000000000000000000000036af826a005f3048a22f7bea790000000000000000000000000000000000000000000000000000000062d6b1bc00100e8501cad609ab000000000000000000000000000000000000000000000000000000001bbfd9b90074538b74935bf13e00000000000000000000000000000000000000000000000000000000e49985d400b3f878a004504771dfe41d9601c86ae4ccb7cfb7170446c8d7bc7142c0a69726e6f4f9f06c296bf0046dabe419538b539ca518332da907925bcc504a40c2bde6d685bed6013f46eb7419a4ba2528e4160396ada59aba43dac62ff7aa7be8cbd88451fdd2bd461bdf48d220065db522399cd7e0e9d74a60a2fb2df85ea8669f5642f00c9d916689aff0cafe0839209a5d9921f332178a31bc13ba7d25f35b36f1754bf35809a1a724e21f34e2d630ae8d3331b59963e18ff39208aae9d1e03908dc28e10e29c0f7199701d9adf990955ee722429611a408dc6ba1e46f2a14c80eb28e7d1b6dac273d9b34d6223c39e27fa92dd0b8cb032f9dab9081aaf84be41e51f43ebef13312c5765fce0b2aa69da06fb557c2ef30cc1b0325c73c91aaaa9137e46f5b70a857aadc94569480bb08a2ae7a1edbad52e5c2ab4a78d6904481dd661864e8d4b0a95cf41aaa52d952ac6bcdab61883a4ff31d31166ed91716ea0589982f0393c3ec484d9ccc714feac5038ac6a19bd38f0239bffa61b73074ee8ad53576ba9411e2cbac7c5bee4e7e02d9fffc8123e2446627888949f09df9ccc831ba1892f2cd2db67412f14920cb61c86aee7a7441dc81daba76e6f0ee845f044c349184a4f8a2fd88d4f8654c35ae3795f03e581653ee61a0a02b9e7148b48a39faa2c9f7330f77d56c4fa36974aa5d8e1be5c3868dfbdaae17ebb6b3cde463c2af6ace5dc7018b5d131bfeb359477e0a5b6b31200568ca848ebec938bb931aabc8ee98c926c9b5e444c1ef84e3eb9786479f0144c46c7b155007256e0702ce07f1d74fe6c9aec817d34ce162ab03bbed13e03c8368ee6b25b42a295412d94c1b6dfdce8a4afb0c56f1126a3c9cab1d94e7a7916aac0a896813e3d2edf41245c8ac7cf83beee8a6c7abf3a179a62ab5f8fd89a05653052d0e3ee3e1b71dddefc8ec41b4bff07038943d5c0d9fef44a56d2ad7878c9d48a05e61d5ce5d619fd2a267e8a21d5bc88ca910c19c272ff5468835fcf10d866191a95095c9a14985903fd9e761a8a18fccfecaa0fe9182b0abc84ab4b355d22b47e49333f4d8ce8021eecc07cf84b27bfd0255c1c68b76d646de5a9c7da90d17386532e7a592d62713386154b5333a7ea6ff3ca08cebd203d125a0d42471eed75babd4e194f763bf19fdc5df9373eb00480a033521035e94c36c0a13a0d3a2316ea4261fb4bf3a34dc2f2139fdce8822b088943f4f8130b16a1f727ce9a2c179a877770b315e9ab587fdd501fa396128de67602e34d9a1334abfa3aae0e3eec17e123a98f26bb0b7e24823166459ce44b1f654ba4e7c45c0cb60aa4bdff01adf81a3d56b04988fc48760d676ddd3899d4f56827562252f939951f658b05c9cad596af9f17d75d58a2d5f1a34c60402757566353bfb45c6bb31582d07f411b6ec725a6ed47fda76be854ffe12a604ef251b5697d545f4a3fae379e2dda1a9e296d7204bddaf801b6069eeacb02d744b1406342821c164dd8b1edce60111160a08a85ace46d8bf6c5759473b3503b029b9eb0349cf56ccec33355729915f39b17a62f75781f586aa18b1036ca53c34804a3fa2ae5de9ad699fb9507381f7d0aa78a4cfd637394a7e6d6da6ef5bf03e1a7fd4ac1eb848e563d50b03fec50e82db44729a4e0564140552623f84dbc64e59f70fa37cbfb0f1430ecd2a3a730edfad8c3aaa11d97256e48c845de4a696f4be2d8ad0d513588defc78145e5394e20e78aaffe1443c2b7778a281fee4ea351aa6cb304149c7c776849e46bc0937388fa22e6d09e03f69d4e9441c67acd816557da4b61029c132b4b90a38e714ba0111c0c6296f7c8ca1a93cdf62e15ccc7d8a572aa5ce40a5e1c4f927ee4cb1096bff11d031a01c37ce0129c9a53eed44b6bf2d509142e512d429701b2fe83838a149359e8fd9301f3c6766880deda87f1997feb38d28c3c097077b5e5eb9743e6e36b9a04cba38c5095665ca77c3785cc4b682c62006b8c192d696a6961423770a79446669d9b87dbc6f3fb299369e7d3886283fad9a338126dad2826e1a3db01ab27d0dc6554111618f94970583acb30de6a37c38c34dd19c86d4f42a0947f01989be98e8d5d3fc533367d394076f02155803ca7bb8b654ec7badba872b747a043a3ee2391dd1d0147a56130bef21366048570022ff120441dd753392a10d4fa83cff9501346bdc815b4ee57ed8c08f04195857727763db23fe9a4e2212c3358143122691a98fe48e7744edcfe24a3183b4bd1fa3f20fcf880ebc9c942013d741078e29195f063777542ccaeb9737bb4a5ca1f6c7fe137b20dda3c292b4332140ce4892ff2c8c2060c932e7ec1864a4e1709201ec364055cae57ad9f47b69667c564998e89378cc2dc09369e9a9221a4975314b5a79e9709aadeb39af5344081659a73a03176c72ea9e42cfb60e16c904e474ceb5aa92959f2d5b75950217c9df9045aabddc2a1b0b0d21cba4d3d372805cf7a5e1a939a98f77101fdce01bad33e99f5b7beeef3c4833bc10ea933feb47782bd340b3cf6d3c21bf590415bc51530b7e132d661d9d7dcd6af66612d9b4157cc9023149a2fb948cfcd0ec74a5ca914f5dafa335984ca628f17bb46855ccdccdd058c611e9b6d926c6063f326a00bafe8cecfad1fdd2d42bb125e6c4e6bae218dcff59d33db4dd97c73e7e2179487fc04ff5c84886c645056495e64957aee87202c23c5e8228466291294dc6fd231b71c667bb83209b054e7eec4fd1091cf27698d7c45f7c4b5f57f6eb5378b4f85e051dcd800a71b69d0901b59efcef0036615bc1d2041cad428c4210c1108d2d616c94b3a34c950952e40a8cf6543c4b083cab9186e921317530d13efd18fcbef67448103bfb76674338d72269bff3977b5a65dc5f65455db12ceca39ec4019da9726e959fee6fd8a6ae79c76fe0583e54ba349b378e37436a0f66ffd09760caf056ef37e5fc4c1d86f64cb964cffea5c58b6bd2c019d4bdf7ac0658877e6f8cdbc2a48650b9857fbf1bed33f77ee9b8b3d7af95425db12b7f9ff35181a4425958313722c1a75a86feef228ee2649abbdc3e643179b212d14c381fcb29883e179e8e41826e06af3faa9fb13aa6b647f9ef16ccb6a734a536fcee05b881bfe35113291922f2e87f3ba6e4b76a0023aad951851d10807c12089223cf326736357ba6b28dbaee80b1a45d1b50a149c2627d37da01cc740ace6f287cd114b4720a7acadfb64c3fdc50645fdd1018db5d8b39f86de6e35d42fca912d865eaad758e6dcfa45ec03578424aaa39e998fe11ae3f2684be3fc2cc0d6dc4753f3e3661bae67f3fcd6b1812716f207edd2803c5a9ab742e062dafa9d31704175873cc24e2a1c6248f3b62e5b234a11a0de984d64c47557d866b006bac7793fbcd62d8fc6f0a007a70bf8ec9c82228906a9e42ef23634454ef7c0171cdbef163a98c6a748d669db1c3097c703a4119ac4a38c2279f1406a134660967ddf88be127f7c0f8f777914d12967c9e1ebd0597efcf415652cf19a04b889dcbb4551d47b225a36c082654de9f7687a5ddb8ec614c0ec204c4f58c9c969a2195b97eb97f2b4376dce0d0d3ab0d7ea5f82324ca45fb82b488a2920dbc408589150acf31f5cf7afa6ae6c9691e828ea391670582ce68e05bd2043be3b1774710188c7ec657c799f6e4c782ef995c23cdded2cc438679e580133d438cabde6a7f00462a7cfc8600f516d39910c616e495d1c93794c6c1bba2594f325c1c3d8e94ede812cd6add68cd84846dd2e6ab8c2274a882789fbf578eccc830057d51bc900c3efb36f3bdc9b0840290c4ab1f3661e734410a56183a5a96813ae98324ee5febeb8a071209bf87c78188e753dabf641ebd692154656f9ad51d6c4f7755f673f17725768e967dc01fdae012ec92ec285a8d6e7e81bc5e6c1fe449eaa227926d57ae47ebe8ca4f27751ec5311069c2e66ea19f1b5d98bc35f35cd4e259a85ca38bf578d3620e04361bc8e44e1c5b5d6c8c5c786adf6727cd8fac29d8077feb49b402e846796cda828b06cf91e19e9f4bbf4b0365f0ba055f96ad4add4363bd290dc759fbf7c8889294d5580816a7baa01aa7e7c2d6ad71a7c8776d0c906c4dc06dbeed18f133e20c22505676446db35764cf518814dc0cdb9fa2756e44f9e25598a3792882c7281da949315b1f651e9f615867b6c516c5942a4e147ba2e0c06a21dd9fff4d1e224c8750b75544234d6d189b0c7f5fa270d0e7f35c8b736f430e0d5293898f9bb5d388fbd1cc1fef5fbe5c276b113ab8b436ebcf4ae9c6832119504ce5cd8d5b504bca91c10ec512cfe0c9b0b5da04fe9ce7a9fae1609023cfb571143bf95dff1becc292ce2d895ac19df295806c466b96944bc602be9574bf29b13e5e65d2852a1a61e75b80baf53ddeb95cdc8668ad9a28e7a2896e28e5d0231f1c7bcb1ca11bb2e0d091766ee47a0a7352cfaf4303ba2503bdb4a4e8fdcf608d38d6b29571aa8dddb7f02cede4272e29fd8f9cea210d968c503fd32015a7d38417c57ce3b1d4fdfc328ac96b67af3381e526d38e6c502b045cebea35272bda912cef033ebb8642f93de209de673feda40822d4f24edc8b79bbb29e68b989e3b0b27021039126abc5e6cf8451fa8b367fb290f4eb2917fdc27f2cd931db0f19e963bfb17303b9bed8e91164700614afc164a02e8bc3ef5583929fd9995dee226f28445eeb189b0c25ee6f8c23e52549fb7f3fb3662d89955158ce25eb6d650f58ca5b66e851d9bae53a8b3cc6f5c8bc40fe177774bbf4d0da3b17ee74f616756de54cd9c7481916e8279b9b68ed50a6083bc08ec5b4abf994839997b233e989c7d594bdb4ce15b19f4323d8b0fa750bc1711cfe2e4acedd1939a0c5e8a4ecae95fcd791b7f2a74503898a67f4b27da167d83d09c41aeb0a68404166714858899a8bc35d72e7c6ee98a6928f3a585ee8ca67b3c937b020cd49fe029ebda9e21bc57b4a29258bfb611ee44b1b217387e5d3adbb4a8c86fe1ad935e9277e762f0dd74e90f6357152e28ac243e5d2f43afa52e923ff5a9966fdbe2d4092e803644f90864206bfecb96c99fd7cbb16e6a0aa84be2a33660b869ffd470fc21764f9d8f38f26eb348eafff5ce13685b98380d1423dee4b5809ab8693d9a3dfcd70b4cc42fdf37e4abca5db00ad3cf61418a656b09e4a0c8c3fea0dd41091834f22430033f4cf1379c7ace6966eeb165e0347a9cd3aed5810d532fdd736eee8b4f4c87cee2e87530cf708262c6ad4225669dee6ce02968fb7f03c860f0f0ed946c605360bbc4e65a7cab2c134bc15bfd65d1023fa7e1f27cbd32a7147787e770bf5282a68b111c10631e1abf4381fc1211731a4c6b6bf54b3fefe4792f17e6a7d3438fa7dff58dbafaade9c34b2ac5c10c536a2f4b438eb9ee1d801433949cfb44d12ff8ed14264448b814cfd89b2cb0a39336e1558276243fea9fc3", "spend_index": [ 0, 1, 2559694887, 4294967295 ], "result": [ "96fb3611b3f78e908f7d83ad1b1c1bb715a7df79eac25c4cd26bf6b3d86ac5cf", "6ff033d5539ae2d14bfd8fea0e0fb6a7e93cd08986b6e1e280b41355fe17e447", "e9f5a3b36f423710c6a5129175c3833f12833f58465514a72e1248e085ae2537", "e256c842b390333db3bce1ffaf711d4da880566e07d174797c25ab5a4224784f" ] }, { "desc": { "Inputs": 1, "Outputs": 6, "Witness": true, "Version": -2006323668, "scriptSigs": true }, "hex_tx": "2cee6988000101e90702690000000000000000000000000000000000000000000000000000000088d88eb3fd430138ed6055729b96a415fc37d0c94dbb2dabd050a388700764d5d5018466a45455ac5bc5173ccc9300ba1b4ec66e713b27dd9eb7055465dced488ab83dfc762a9871338e0eb2ebc2cef93de3626e52ad88db0774afb632e51b71bdab859dbc740887e1a9d3fdce12cb18854505db1bf7f4ee153f21acfa6c305c421893374908263fb3e7c6f5297b36b8a7684d2ac49196d32e9dd484eafb6f45d02ed13d5d30b2c48b03c0658ea25af364447dbf7c2c76f28f650f220d2f859d2279416d2661434b75b834b5bd09829ce8748dd6b7233f30d5cb064fdc420fe48217669ef48160586a19ecc3ad97d6e9de4f5f80c9aec4b60d10fcfbb08778f69a978c3768a5c3771b82960c733cbcf6b09eee9e793a5c9eea0c57cff7157e0232c26719a9045697fd9f25d81f9b31d803fcc9857e57ad9e55cca9f71204ba39d651a796a8737e7711eb0bef9fc90657c472509a7d4531c81328efeae5f22623e3aada3a7b6eec583b25f88c219f51168c59b1836824155ab2c159b3c97237a9ae12351db57fb562dd838ad79fe49ffccc55aa2031398a903dad86b0feaaf3f412e7031ca99b29a1d9bae48be733f54259eb121ab374c79e4fcc7c39bdacaf8104b555edaa420dc28b4fe802e10f364e62232f0150b209b5d2482a8971bd4e422440f77658e77535e77a8d0f51a6303e5650115bf02afbe0e620aa148b00e37db3514763a854eb2bacc8379572a0b9aaa8f77d1ac80be0e192fbc9310bbb3c852b01f593fed5fc1dc8ed44137e8d50f34fc88f4de5026fc9ad62c7ad7b92460fa74eba35071f3e93173df1d66ada44dedfdef4bbda06b746b7169b2682e5e556f9781a87c5d878b9ac6b79009f10d6af63f85c3c6e88d2b96408751ca1d5de40f5de149c362528b6deff838052dc627189ff5a9626f795e2f7c0b99927fa1c714e7150390ca2bdf64998812576e822e02865855558d004da9e17c35daa41f998054fc529097d591dafc255bd1328f0557fd3b53dd7fb35a728f47a24cde169bba46f35fa4c162aa8b7799d5a1f857516efdf7ef5db967f263ac897089877f0f96d5846026feaacad0022ffb69d5225c66d6181e336cbee778d5f20cc161092d6c28594096bd1acece57916f6abd1941befaf44835f0e63d59ec1d9321158885738c7f0eca5a969f7ed43d593207627b6b9ce623a57b68a4fc2fb27d8291232b9ae3afb98f8f94a4d5b721632ce4dd762a9402cf8a911c46f73ed804717c4bc31b99e7c48f1d6c4b3c08fa8e54ac68676b110df189fe931e0b05943ab0edfdf3dbf2a4e649a8e3f76bad327e22eef49403719fe07ec40f5c95abaff404fc3db21baf2c7455e7bfc369e26c87ae646dbb033b2b1fa657aa3cb8352b3bf46835f44a03529e92439e3d5069141f44dd98bea9cc8234d64f0ad0b321d4c4960fc269d1dcb9135d7ebb2205f5e33ee33b6b2bb201410b3e38992a00a4f9ce5e06d065769779ec2bd47558bf9b7689fac920d0ff1b1824c1edda6d3b28ef8ae00c42f1a67531d713eab9a1bc44412c8a3cd9c521a44060133ae80b863243621bcc7217dcefcc28267c4d0698823bb61a0fec8f468a87266b57677129117da7c5e662a8140c142dc45aae2683094a033fb8c140990a28aaaf03d7a47f93410c82b2d036c2b272df21215a172010b819362ed6b220292d8d8ebf707571a022e2704350dd68eabc833a7b666c99709874a3312843321d632f047f8d411873a3019205cd749824ab6cefa0cdb5cdd537e978cec566d3e1539ac2cb35799b2c4f29b127f3d4e58deb5942353731b3c730dc86ad91b074bb27cfcccc3f5da1c78ca28dfd15e83410e23f5aa08ad4976bd478328e61534fbe3eca40c73d484e2317c596ac5e6d503314ef76a7d1845035c84683f557e59e8ec80167caadf608d7aa21e0c2434fce3f525f69253760c66536e05c8ea5153002c90a8eec3872fa5f9369881d3fd0d212fb0e3d18ce3fa726cdaafa261db618faa8aa8478a3c3f8070fe033778641bf86240df7062263142151b7dc4c662954775d83d673129dc54d4b229f4b9ea84c32b6d4b296d461126625b8639641da1da91e66f9ff08ce6d1f8980325d67ca57088e96b57a9859954a9afb39f4b6354c4ccb96ab2f72d2a744c9dba822cc3595cad1bfb685683a76adea64a472f37f1a7a998570aecebf629b60197571b6224343f60eee90e27220e08eff57172d0870e4ac72a6a03fd2b01dbb959a12d229e8fcc06a9b36214bacd96a0e06bdb208533a23dc4b90f2c7f92c0e5adc6c8901ec64d6639905c6aa38544f0b1371702f490678b6ad225a977ee7f6059fc6049c5780c99fde6837d4468f242da97a5a1f780d28f39d05e72249f6a8ced5a3ef41ad22780e1785c8988465c0e0b65bde6a873008b112f98fec76f5219845360ee6cd41c1e01458bf073513c6d09dcb7ea09d52fe2773f1dd7ed12bbf00e76bf6c96f68266d2d98181c55da440c1dd2af58fc5ce9ad78a2aed3dfb055da9ac4a8893b232b334e8963800059ae80a18bb082d69b4a50228281d36c9a22ea2488e9467de7d53eedc659e4715ea994433e4e1e858cb567211132bdf6dec0983cc5b24e41e09932333bf393ed818932e7093679804aac34a2c8e97d4bd445671c58c2c786c862e09fdc601703aa3eeefc83e891d93b698d865cb00b2e82ad852780b2ab1c0203aca2cb158c4701a0c9c29015efabe1d06ff17f52fb193c93cadeb1d1ec01a229c61aad2904338844ee7b469a2187adea212c4b4fd277ebaafa572d490bea72d2b0f27cff9075fded06c6750e3c030d5614d37d9b2b8b48811779ec1e281cbc7905c26ce112ed38d4090fa48979df1ff4d3adb5c38019127ae6e5366ead7d2fbac722f08546f82582d56a9f79407962031446250efe088bef4538e43d5586a3e92f4239d8a425e2d476c9e67f9d949517ba6eb0f603bbc78f4b36eda40a68015b7f206aabf0e05a6be5c3d63cbe07d08a89fad2edf17372aa4fc5dede966bed7947f481d6655a273e9e22d145bfbb21f7177bff75a7a5748440b1b7d848c06eaa584806c3ff5c999563924c4c5cf2512f320d4a918915139ee87cb2f77289dba349a1a3194ffbad6ba06947e0d6afbd8c419a9621653809853365c3a8ae25a7483b13a593f801d689245918fead3ab6668c4a6fbc3a2b9c0e6983c0d25700ab09384d04c58f645678f05aa2ec4ff4b153d9cc20e06e44d14706633528ca00a878aebc7ae7daddf529447b383c0ad84c925ecbaeacda6e374dffb3b20edf4e93f885741948453b78f0a32cdcfc7b01117d111be926b368cad8186ae2c3061ca912fe930615b28aac118c70bc3e611aaedde8ac79de5df508d45d9faa0b16e7c6207555cf0edf12e1b26076343003e8377d90ba1f08c1c4c35e114c0307ccb7b75d13c4bc79dbe644eb500e1e7490bbe0a2767c3fc537f184852ece9189b61cdc65f14d0cd90c9d02f4d5a7abef11de334295c6321a4d6cb8d61f8c7e5716e5725d53e1588a2bc36d33ab76d4c10afede9177bc08be113fd45e489b4ab47953aa7e8866cdb4000f3e3e640dca4aa8f7a977b647baa8d08848e1d14f8bec90526", "spend_index": [ 0, 1, 3336449762, 4294967295 ], "result": [ "35b7d911fc9f0b8597b8b0d671719a4dfd381320bd593d5d8db01af2d4e5681e", "f283f9f2988a5ae806dc1a41450b96939fa6e9c953fb6e7398945abb8c3ad93a", "f8bfb30a4d452ff4950e0d9bcfbd5f767e1c035b58105647a6b7ce7e79a0b092", "03e42937a554a7413e4d69a1c9853d185ba04541fc2cb0d14f47d51e694cefbb" ] }, { "desc": { "Inputs": 5, "Outputs": 8, "Witness": true, "Version": 927470719, "scriptSigs": false }, "hex_tx": "7f1448370001058533c2c300000000000000000000000000000000000000000000000000000000cce1c49d000090f653125d362700000000000000000000000000000000000000000000000000000000a074705f0011270d74f05bb42c000000000000000000000000000000000000000000000000000000001c7d646400a560da53d34cae8f0000000000000000000000000000000000000000000000000000000007add3e500a6a2e2c6830165e1000000000000000000000000000000000000000000000000000000009f76a13e00272a2e5b087418670bde018a03c84ae2138e6bebb37de8e931ec0b26447cd365cfa52fda169fb098488d761b3c84e6fe2b0a1f2cb7b87ad7e7ee98c5c90e7cd22aa53d0aec01eedacd85ee7a40c56dc76b302075eb52f5a165010ac54e9ce47e64741ccfd6adab3706b71abd4400a863b6f34f23ac10e3e0ac3ab3a063e9ff98e1cbd59a5ac7b35a7bfa3bff1a4fe56421cd655d75a09c567d09d072a1a4a60211ea931ea1b6e99a56ca238131ce6d662c41c678e1f2ab2d21b017ab9ca65056a392ab60919a5dc5c2c5add0ff4b0985690bf53b92aac4a62b10f4b3de1bc8f9995db1f08935c9663bf3b2c27cf50ec9dc7876e1d53f8a33f01c714cbce776ec7aaaa692885854534e8041e923f0789449d7ae7d1e526619c4472e5796babea68819e6199418c57b3ff8b2168c55c4752f86e0cc35b44d9fbbbb851b769f7a1df5f25968fb9f1c293e28b6501bf6688dc6d9724a75c16f699297f3cc92d762cc9eb4dedd0c846afd1aeeed92c31eb03270d796df29d5cd480787b71038099345e71d8e8dc702732c5c6b06cecb48f170f8003f4d8857334d4f35ace0be136172fa465952ee318b230f3f39f1f2207ac889100e86c9e553a938162e02790ba30d4ef79a77b25a6aa35c3eb55a9f6dbd1c96e78bf4bddd0b450b9890efa7440a6d279ce2aa3d2c504b5811391b3157cc30c1a1f889621d9df320a2e3a145feaf15207c92410fdb82fca580e0833379e330e1b883e01757ccb99b89db7af2e8a783e20327a2b83c73ce13e5e209bedee8deef0fd64125f3aedb486e1f7f75d156fad00dd73f88880ff72f383bf208f569c84982914fc3c7afd69ce611a3e13be66601eabed2690b2ed2bf3a1715517a33b2d55d55ded6aa283438a8b956fb471020c88ac547992874716043d1deb19bb61c618f7cd13439e0bca823d82da3566cd0192c36cd509dd5235f4d612524a6238776b8936e80bbb1664657a00a1f0ed2a5175615d00ec2515467bbcbd0fd32f7db1760acd45e55634054d7229924a19a198285030d3090d41f33b11b99e684823275313c3e86af60b567bcddf7e60af4f0fb8a8c83aa1d4611b032fcaa5a8a902bec0cef342eeb67887f575e2334022843435bd27a4f26a808ff7b6382605aa64abfede133f96268878592f26a7d0bfb9b2dd7cec681d03257d96ff08d3d2812c459c8e6d4ebca99080c3b44b73666589606cd70ece1ac29c921f4acdb0aeb6ac827d3d1d72cc675d63a3db5ade28b405f9eee7e43692f825e77b018c30ab2c42fbf303cfbcc717301cf10f474e02fa9e71f68f1b1a6b600724dde7bd02090f6f70900470c0f5c18dfe9b5ef91561c946449f9f0eb4f2d3fdfbb4dba6d56a0ccc7fb77fd26797b7ff958cda25a2fa435ca25678ec0c97512fb5a171212ad545c00dd63a9e134a23f168981bd3a6e744d1ac6ca36d5ddf401b27601fef6bd524dce6164a375380fcf67cf5302c27f412c35554ac854fe2eb1617669c5d379220cfdc36fa7e77985aca7a9baddccefcff50e2953527dad07a7aef5ec37518762f21361971f35d06934b4a6cfa965eb9daa32bf7a02d3cbe71da5b02f4ecd1e002b708d4accd13bc5ddd27a84d792159464259d6775714f34cbf09ab20458c95505865acdde8fc6aa6ef30dae6b60cbcb0a07d2a7e0b13cf035062f590b1f35bdb5ef9a552d07e1c5b3dd757deabe23b44158ad1ed72b860fee4f25d71938efd0b0ecf89542b6d50d656c6e918b8a6746c3501ffb725a08ef51d0eca4c563eadf395da17342c832e3adfcb3a3c272625a2fd7ad37b75e194b9d068e41f5e90e89be73e1fa1d47237ca78ba1072e7781ea45836626d08221ad3d14959b4eb4bd5829b9515b5540b2de3181c83f15924faa547b75c86a079c592ff1cc73e12c46271df825a340455a74fc4319df941f7e342e9501e87f9c52d71719353787c0888b451ebfea884e7b9f7e1e08336220e8ee987c09ae264bc727bbeedeb88fc9da6b10b36ab191a3e559fafd351f3405016c098f4429ee97c1734d347b547ca90821938551a870b7f4315a31b7e1c64d15c787daf61a452ac87bce0cee9daf0fc3ba011ff3319e57417ec77756bd178f9dbdcd9179333e4e3a49918918f1859ab4aa6100322ebaa879cee92ac17559547c9ece339ba495a2e54a392674a0f01e596df37b92ad5319ac6268fa4e34be837aabf20c5aee8eb7faa9daca9ccbf498c9ca9f10df74937e0c87c87c20d73385da74ebf6b5873ff01e420984dcca17a688a021bc5d4f4a82e43e80bc215a9ebe502f03f9aa92698b848426876fadb90491e4d22354c42be6873f5a3099b840726f59f2262ba1275e50821f871c411e7850016324ea2332a0f611ca730f8389f0912bd647445a182e9a18065575727d2150d6e83b80c683824921cef65022b057429adfe0484e2e3c7ce8e4779671877f9ea1999295e1f9a8a01598a4485f369023ab24dda1e175310f6ce707b976bec4fa7e2ffc876a03fddc0152d77caecea97bbd0bdc11c92955051f1295684fd8f0e1443d55eabe1cdd098ee45fbf672d4b19285da0bd404eec4d6b88bd4ba5b88709ddad97d1868a517b7ade6e5ef74343e5d4f2fd4e49c3f16126543f96ed93c1bed35b8d73da03e8641110c36d46954cf5827dda61c54c7382d7cde2597f4d589477cfdde573fb3c94e3a83dd500851484cf0ac41e7d267ffc58b5f842b644ea36bb60ae97f13e6db7f1c4bae4548d86373e1bb61609da84b9e8562046959f23365fc98f663e646f1b6df6a17a5e0643324aeedd6c96829881196784d99b67f194039f76aaa0cc082fe83c5c425d9daecfb5ae2044f44b958babd9adda321fd329f2d0dc85c1a8045d03c1fbbb4a59c8f892d9965eaba3e2b26e521371b13d027bb89290346d6de1f4dc098b82f99740f2c688dee5fddd02818ecb850ce85bbed1c74a7147989143aeb0e78faaf3426510b0f57be10767fd9a7e764856255f897bcb2b02583b06de695907336f6018b9bf48b912b2354b359563895dbe6b292f2efe5d96d8c7494d57bb41971df50c0e4c3492be67539236d9bfd261783718b961ed7af3c1bb66b92e882687d90916fdaa989ecfce4df21d419b6025ac3d7a0b8df5e986d5245e09165d4c042e0ed373bf2c2de094b6a98ebb64a31affa752f226066b76d3a1818af06411d78a0e8f6712cbf41e77fd0d491332cbcfe03ac2a42875a2afb3f3602de6cf540d11f9117c5040508c77c2e8de0645750eb713f9c2daa86f70367950c2beb38d08dc8c62e4775258741fae09728590997e7e7254cabf3bcce7b53eacc8687a68e83fb64b4f60c6031d4558a41fbe0685a011360ae175ef58123ea07a6bfd6801330a7b938bbc46e900c34c0c6283bf727aa4c5a7b6ebc956a2a73a34600ed7ffc492d822e3e6799c1d218840c8749647a7a3e32beb0de784d44f97ea4bc89d30fb6aa60c202bdb52dd103e0c92106e731b7a32cb927b31bcd658eba282514223db9e132e71b42655b1f13a58c9cee6fcdfe3cb74ca8b20866a2dbe86712ab0fe2f5d83b368c734709fcd071aa109d500f465e30d31275ff725d66d61d6389de4288b7f16b9596a80c8a0070ad17aaeb2585cf30868e98480021e02f9ab582b04f775c289b228eaa0797a4aaacec3607b9de993d5e5428649883d8dadf36c570d531dcede705106fd78f8f73fae85e96ee23df325101bf5b5f5362f8287029f56102366575e8ae261d3c5bdb4010d69f2f554438851fbcf53bd4e3d5e5b410f36bac7d4a9a8fbfc7599e85e5461835e0788b6eb082604107a385290828e56fa4538e21c42e8b2d2d461ec4c15f1d34b8e76feccbab6e7832e24304dd0691f363019c70649e84a7afa02fd00018a6afa7ad8bc2deda6d7a77a392ae19e63663ca2866a5ff3d5d26df8092d1909c5c546d29a0cb2977c49fcffdcec848fcb064b0fec10012506d87227274328f0fb1357ee9645ab7610464f2ebde2f70de3695f80999fb005326f581b839e29c17b30bb24025881bec2763283fb5cf247ad5e2ca72a25b4aa16a7106221cf224f2519ceae0cf8c617a49c36ff0ecc2b847a05cd8f7cbf2f10e1b41774d7151b5d18a25b6f626a6495eab19cd432b4ea9ac757a586c3f3a68cf756d5eef3ceb5d92834c9e7ac0d43d20a6af1eec12b095e3fccd960203a06318c4f8261c576247dc24dc742e3a2e839d88f02addb1660133de1ccd693473919b0a1efe680ad1ef4fd89017e43180811b13f0690e4da19472e0aa0bbd502c0b5c17063d8f4d49434c261704baebc47c8f0415ec33c5f44a0eb189e864a5b72f31f1b9189f4e2ca6a0fb5f02e7aeca67c32076bc312e5c6c38e55ae959746540a4da5958b459638e6008376c4f02c48a6585e942508110c7d7f085c953a25d25d15190fd396185b06e8d6593363815a68a33971f9f6c80f0d5ce251def60037c16d49ac0b1e106a48be2f320fd29b7f78349aa64a7e3d922661543fd4ba4e3e2acd70e8a04a22e2676713dcf60795af6bbe0b62343d5806ca4e7bfd00dad24636cbb16b7e3eb9d08bb38d67d18719b5dbc19486d4a0de9b36748c472914e223402b8f31c647bdd02a840d471af6d3e021726fa7028d6caa14d164797cb9a30fefea445c35cebde590a337228e5fdd1bdd6c720b21b9539e64d0a9a0cb9d5c9274c2d549d48f9df1c471fee0de8852a0cbe1cb7ece1dc5dbab18c80f1bb8e5d57c1c381fcb6459caa475849652787bdcf81b745751423a1caef82a5066ef7732f39de3725aab74d2cb5891518e0514a0bc76058b8e02fd8d01ad79f66e18d236c9c1beaad88887a2d25d2b7127e907c5444ce7e4c16e852c08c5025c9c37897f0804ef9687f6e15efc12d191a6fd6ef49d2fac14552261668c959d37a1680264e19a9b301b88fa4e5757afe371149d592f97005ab7b5e1c5acec9faebab1f93d27d9dd5868c76fd004a5ba01c2db2735791411d029f86131e77f11b2df1998396676c5f0fd71327a681929095f84d9d7751b45d12298a84799c77ceb3c20ee3bd5fff4c31c81d6888565880518fad5561a799b2fd52774624c9c5a370bcd495c9cd8a589d4d83cdc77f5e807882c5d9a869f5bef7bbd778a9606f4670f9e21d587d3d4e106a1035c562ba276f2828160d92a095b932245545c15c9ba57bc5e3139b700a83d3d8f4edaf4aa80bc4aa1583169ba1833a716838ab855b146c05cb96773d1d23a26a86859aa3adeb213af7b95117530729c756b052d7b485f8d8cfd9d524e3353cec87a3d617d3f75f52b81525c1347c492710456fc19f437b89ce4837d29f44fba6df0ca58efa9f8cdea2a8cae2484ecfd7d099519a0279d21b55f4f5086dad7bb6ef3771ffe062186f2b9ea918706928d020a75da0948623fc34eeff53e2371e9495b2e25713960dd0b7328682c0f74282b700ec8af7985b10fe49014a70c6e715180fde1d533676b68bde54acf0eaffbfac407dac2d5431c1c10608ef4cabbeb83390a136776e041cc509bccce8eee0025c80156", "spend_index": [ 0, 1, 2627771845, 4294967295 ], "result": [ "d7b1add885c3702cec9a2b0b84eefd49a406fe71ab6945d4de040f27e09bf6e0", "eb8e5adfb2d19bbb1a6d37356313d462d192e088510459099bbfa85d604733b7", "270111c35d939a116777e92815053d91a95027ca6a0971d7d0ef5b6f534666cf", "d9431013d0ab2f6f324386e5532e812d599b582ac7716191d1d5e589ce688210" ] }, { "desc": { "Inputs": 3, "Outputs": 6, "Witness": true, "Version": -1061043830, "scriptSigs": true }, "hex_tx": "8ac1c1c0000103448bcf3000000000000000000000000000000000000000000000000000000000c0ef03f8d5d292809d1df6f8069d0392f54a00171e068db96ae04cb26a4782a005f5313a171539b47fa54553d56bcdf1f29f642c7e299c871f46da2ccdc11ab0c48fd89d3fc7dbb647312408f733e01af1812c95617b107eeea28450549d27b1c6815fce518d1ee46d7380dd9467262581740df0ff8997e8293bbfe51631635210f246f3b9756986a0f2427f7a735a7cbf47a71f160866ed8b4c0f19134ee263c4865449ffa1b797893bfe0171e3be1d7652b23c6e146763e942516e93720a964996e753fb5c51f133631e725099c8d23b4a0fb439293973677b69f6ed85963808c30000000000000000000000000000000000000000000000000000000093bdaf16fd4801aac47b52ac01c9d563cec02c54ae175e6d2a354d206485791b02de510f39a5885824db12577fa6e142a3d46393dba53ef60b115b0bfdac85c82d26458716d4e58c7e2da2a6dbf621e4664183950e637cb68b6f23ae65ba6996b843b49a0d9874de0c9e8d5e6f99322699db90a9ce8377b5abee3b724cf26982ce9b7acc2753b64478d493b4b1e1a7ea5703445d0dd8386e33bee708145268af68b2c7f34d4586bfc83ee582ad0d345dde3685ee04edb8c36560d0f87aa8aef0f2e5d9f6c1fef355b92e01fdd8d1ac72006834ccea7c4355ad13dbcf929a58052dc69efc1856598eb10d9bc1a80b4f72ff45b2ac3e3c8430983cd19a72da5f098639cd8a01f30d54e34bf88e74d8aa9805b17b720257b10c13b61f80e63768a071dbef4a2b423ee4a34c28cd70f6032243a2259c11d3ebfc37f0e7e9ce7af6dfc768fdae78c0e4b4567c93ffb082b5817b5e44601af8ed000000000000000000000000000000000000000000000000000000009bc7ead5000ea2166d06aaead9f88b7ab147c87caced45785892c612353aeb80b8ef429fdd44b4b1b8fd9f699d480b51c3ccdf6e94bd947e78a3b5921330acd805ccd5156cdd6744729030b63241cb7a31caea3e59ab65d23172c5c7a52c6db5fad2131063f5cb1418e1f406592a04b4338b418748218f0c6120e9d6ae55c6ff064569b03eb32ac3f8343d6ac1a3c6e95d442d36e237ebb5fa185ac9ca050da73830c70646782d4f15ea97ff7ec047464e015e5837d80df308118abe91629e1593f4e6d422ba6accbb70a680969f4bd00ace22013fb3c886c2fcc49776aa044ab8d261c8feee059dc6304f6d71e23d4b0194bab447e01ac84700c12f119d0500d9bf867eb3180972322af8e2fb4d3119edc5bafcf5525ad5dc5d6de140dae4da6ac0a452b7f0900a2b30bb5e909c4c40aa395d765873af357305ac2f940b4e1d6422eca4e9e2097977a305837efa1946b6752ee25720b2211cb6cb38c058336713980bf15ff2197b545d1d05fb2dd5163096506b1e1c3a9ceca0e41590920d1cb179bfd197423fc383bbdf2a2ed624a04d6729f0b33f2faa1ce8bc6b3b8d5f8c7050ab7ae43fdc84ba6a8ad61cfd8e3e93d6ca1bc8cf701743ff16bfa5a8e7d14a662d01f0283e32bfe1eb420b73d85e69b34c3a935cef5922f8d581878f15bbc63f9546f1c2f0baa102652c94058b4e5e92b5ab4121d374b1f1625edb0d0856a89eb0809c9e6bf77fa52257d98c500221c733ba0ea9b79a83abeca65b50e398b91d4222c0e2c842488650c68d9df4a799484f009520f57be7e3b490c7c92f021a4b686e527031d9e67c6739d40d1c3105be206427670afba6ee9e61d10db44481032618492bde0200ce0451a5c17a9315159f0e47b5ea9c32aa13c12dcb53b36d37f06875c89dca149fce846a233e49d9e018182e2cb662d90db0b2da6b76e846ce2b969c67a699c86008ccd53111720529ff22a7ec867a746a28f18029164c6c1df506a2c3d2b042fead11e8c9b38acad93580b960818f705d836b2c15a069451f24317742465bc0df71b6e96cc46fd36e906780838436d8ce5ed1bc6eed9f6155367075be6a93abe1c62423dc07835ece0030a813b7abda518b1a2047e1b834cda8020e17609985beac3919bb5d6b5a072fd0301780de28352207ad660434f74e3f86114cc25421d1451b2d059b0878b0fed5c130c8c3a9377c862f7f357b0cdc727950394e91e7a75c89aec17847ee500ccbb857c8317647a24e424fbf410e484d72f2766366cacfb7767b24d17b1124d3608c9c8efa56b6db0a8c4dc77d3effd330d46c465b529a419213cf6efb463c8b23c846985fec32d3d15d84aa3ce129b507b34c0e7a5fea8afb00ead26e9e1be1d126a46865fe7ff979943b106de6def68c3371e36024999cbfc81eee23320d67fe4741a12ecbaf5ddd1573ceb71ba30dbaccc4fe7c19caa33a5c0de007236164e0b96a75c07e00c08b556265400c6c7c9cbf8e2dc8b91403cd843652c20b35512e7853f3eb7b86601e1cffb21e933dc10a4c214633c92bf0378a09d5860db7e941a401be298202e1d148384e4a5c9777a37df4e56bbb7ae071b5577dc3f90a4a4d5dac281ec8a4bfb241c8c8764ffcc0276046162c7cda5934a2090c6c089848fd77b5c8c79a197006740944d6d3ee06b0b963f81a7ee90ade804724fc8062e789e0743864e841a37bbaec96dcdbd4e651472964480f504ef7e36be6b9864c9cd3093e436cceac2dc2fd5bbdb156622c9d6a23687b56c8d6b9352db6eb03fdea01e0758de3a88a4cdfed10b4f2c7edb91b36f5069597a16dae55a582fea4ed1a875d79d031f9aed1834c37e16cd3a6185d1b8f49d9ffdf99adb3f425fe6777c9c71da677fe16c1edcda8e40a68b3893d850c8189087212d9d66dca4a7e4bdfe04b7aeeff979673a16e630a981e89352b11646dacc8add3564d49669b0368f2873d8423f1f14c338a23b004863c42ce2d465d939ae92b9d83adb98003a7b89418a26ac848801b05211381b20e4f91aa1cc3387d41dff60712b4c73db66205ef36638bfb7022fe6966d43ab01e93ef66ebe56e95fee5e5f2200fbf530a048c692d5ca73b4ffeb799b8cc8f9c0863d53fdf35dd8fc9da6bc7c70060bb079d34e0dd2f6b90c5f8446cfcf2cd2367a7f67d699d769580a432b1b0e4a0dd7d57e26afe2055468819ed536307ad1fce6c5de4415595aa499cf351b8f7fcf319801cfb479f371e9a04290e5f3d1909bae740ad61784fb136ee99828b126a0e9a7cfb7a9ba11a2f26457afb3d50666e763b0c50db6541ec85f0cc5ee9ff610bc98a5d4b0d45a85bbeb4519cbb78067212e54b70f08ed1bfec143410fbff00c552f071a09087df2a3c4f7a475a66981203d766a7ce6ca1ce48c98522ed302274030a2e3b56d3f4f8a16c5c776c4662e0f3b00899b279bec631cd0b128ed2748056a30b6d3d2a743eda14265a56c87590fdcb0181899a035d41f080150a233392c57f886a1e8f56e86ce186f50c0fcc002ea90cbba51ee9e3f11c4cc49c4f352efe788954ff4dd1096d67c65fe02fe5aa34e3409049264a43b905812139dbb3bd7ea2097e3564ee96ca3be71ca7922565fc8eb5ebcd387e53478fe6431ad88a9f2ba3017e6e793167c379d60fb6c470fc215f3fed6cec1309bd54d5d869a19c0273942090b5ed0c9c80fb00da664dc7cd6207a6725ea080d0fa59d14faa064050c9fae9cb377d6676b925815f075d3b074bafbf75b0f5c8c80823e634db6cfef5c88c0b5eee2c09dbde344233c6bae1d909296131ebb902f70df34f67f13adb90d006dda45bd482c931547c1db41f63637afde5345e2276dd2daab4b40e77c472c1ae4f9c035a8eccc870625bc5dd415ca3f1ae488b820928579fca63fee3dae4e8d01e8e95a8c3422e854f022799096538cd55a03113254e869c3e6cf7ab566daace700aaf5478770f5f0c3a95770e04380c1f01d76a7b1dfcadd5322c082b0e2fb53b42a42b06552dd5349702a8ab7dbb7f20814357d388905ac03c56e5d0f475636fdd04b74820f76c742660dde2bf4985869d05a06fc1b6810df3711dd2060d74b6cf4c28dc60a5cbdc2c033490e20d344434c8de3a30a831e6be4a5885a44f58c74fdf64b0a2cae80c9b96d24bc555fb40d8f47a349749a89b45cfaddece78617740448ea61e8aca5b62490d863596ab6c2022c84fdfe6ccfa7e3330155d9abb1d5c43e259c7d860b88f7916da09959e51f3ce858e4824d031d1d9bc514100a4c60935aeec2524fb3fbbd8823b64968f5e6ada316fd9b0d76cf2ff7f1730728ed8a500007619d1bd", "spend_index": [ 0, 1, 1560890374, 4294967295 ], "result": [ "07f23b994884bcf10b13b63dabe7c1f388d86ca7539fc22f8952992b123f124e", "dcbefa0f06775ce907448903dd0dfbe3f754fb64909fae87115a0558a412ba8e", "1d0b4bd141ae344c8cb6943699dd2c9c480aa343d4a27343c73fa002d7d3920c", "5a7c44ae6d5f5b3494cc1180f843fbe60275377ac73334f35830c78e7931e9bb" ] }, { "desc": { "Inputs": 2, "Outputs": 4, "Witness": true, "Version": -1889566180, "scriptSigs": false }, "hex_tx": "1c825f8f00010274e974590000000000000000000000000000000000000000000000000000000049412be4000f1fb9d3fb797df600000000000000000000000000000000000000000000000000000000690b0daa0032f54fb904adbedffff142db4ec8a3b25bc516a8bcc908becc67d7cf8c699500b29c7d29dca0d3a87cb678c9dd16f77913c5ade4f21431402f9110201efbc57b65ce926fc2b2be7de3291e53715efdf70323931cb2e43e86ef1d3669bdbd9a9084a9b6a3b6a4db8e4d7fb26f69b68ecf3f09970abd3a4c8e1f89a50aebbeb9bcede426234d385d0d2757ec18f740adb8117b7f685d57291edb424e3bb190f991325fcf2f8212da9aae593bb625ec558fc14cd57d23523b9c2a7ada70c7549c628fdfb5ebe897b7b5ccfecf6337f1a29aca0300f9bf48a84d6ae862cd0c30c808be134107352f98ff57a0b45c42a1a64ad9adc2d7109663e61e3d1881ebd359d54c67d42e1e7b85c9d3b76256cdebbe619c4a3a51bb5d953087254e8223c37a7a65795fe131177faf2e900b2cdfc0a406c734f8cd89e087bf87cd57e47e173f307246f25b4be62eb85822b55bbcd6c043b913b486acc7701f6b56c69491451364c458bb65633a3df4175b63c37881fbed88f27dea76303d92ccdf710855d483c50c69e09284a9c24857a4995f613d9dd348a2e003c602c7b46e6f85d0cc0731143bf5041f5ec6282823600d27020e65c83d8b659d8706e407f465463e77b32709a0b07668fafac94ce436612e38be1e80c7d190e58a2bb132c88e0ee9722e89e26f5dc3bb573e2624aa5b2ffb736ef1ef2798bec4870e2d347f8db9a859c8efb4980ff744070a25030c33095443e1d068acb2c38d9e4d279b176f0629fbea92da1beabceb7c9d184de51dd13571929320fd80ed0ff06e75ff4f326b140c0e8243246961874c0ef5c8b2bd5c1d859935fa66f563f9f15e6d532f6e1a21c10e34a409edea41750baa3e347fcc7c4f39fb4f08cdc6ad6cc947a33925c64dbc373419c8c70a730062688e6566998919976125adf06642bf69696ef0b0c4b5a445507a1761c37ab63f5ebaa8b2585424b1f687b105a5674e862b25666a54d32f5eea68f404cc6cdc2925c40a4d78fbf4d7f8f903b35ed422dc854cf60257d5dd9cc55652a3725bf7f4be21ace11932676d4e7947de73aee3af5d18dacaf4b497fe5604d005540dbb639610911bc0d5eb0017b8e592c8f2253744c4be6bb9cd786b8afe2d2db7badce4648546188af776f0c0f65b569e43501a891046c13910466ea05a6d3af1e56f8e9fffa301fd8c01cd406e0f988ebebc8c4b8003fddcfc481f00cacd6136c7118eb05bd797789cbe4d0228467aa539b4e3b37eb3641aabe38cc824d801519ec4faec0b2f11d8d1e78b76ec89d916ebf908b51232b703c39ba302e47cf8f890cc26fe29b52784157fd1b72242eb1b22d28bc6322e97148dbfaefe659924ef185ec61bb98328932109b56abc50a5e365e2e9df712c20864ab3cb57eb20609ba488973f8bac01ac558617b978f5de900bbe77f4cf3db5f18ce820d374e36f8fd6e7f0d98c600bb407889587f758fa1d8ac0679b5e97521a9daf3891dfd9e7fc23773bec088338d940f8b873a5d4fa1780cc14d0bc0e938feb740ac086e471ea2c9788fb9ba6a7e2614d52d07ec1438cf1a2ae252f0e82239478b82216279fc94e7840f05912e29f9bde5a1aa02960294080ac8f96ebf0254e8ee9dd9468685e4f82354b4530c0140d9975479a0fad3b69007c606fcdb8c8a9837c05b07e3cbcc8d2e50fea37984c31bf5dc7f42ebd9bef800480d86b75666aba8f507143570555a77d4e1afd103cca0a840fbfc90d84806b4789396700cf1ad61f", "spend_index": [ 0, 1, 4209932444, 4294967295 ], "result": [ "18e34b4d95056dba2f50ae05129bde6f55805557e483834bb948cd362e922b0f", "46eae96e40720a47888c2495a3e5eba41962ca54047c14e2b7e77da87059da6d", "36b23377c481f92b265cfce6102e8c24e113332d45994a569b38653a649953e5", "0f87b0636a601f0cc0adfedef7f48e0a957350e643ef946650a35f36fb4b3af9" ] }, { "desc": { "Inputs": 7, "Outputs": 1, "Witness": true, "Version": 1968100721, "scriptSigs": true }, "hex_tx": "71d54e75000107b6d84e5d00000000000000000000000000000000000000000000000000000000209c3bb100ef9f0118e299bcd400000000000000000000000000000000000000000000000000000000b3848eecb8c909ede6d119103ccca4dfbc2e85234c5d655a21345b43e7419c65abe63d4f4d80d60ccacf0cae717b9c9ed7142a8f406bf33d77e9098954946bbd05afc7759657661308bc4f793995fb6bc453cedb1e45d6b6a52412c8ba703166d83aa614ed3d2f7360a89fcfa21293d18852e4ee471195a07c53c0e0907cc4e352decf2f75d6b2e7624e83e1afd8e3f8854403cdb106b9552f76564a9f75e007f66750b32ca3ea9347780941d94597e3e34de11353bc021198f6940679967ba1bc42ae387e000000000000000000000000000000000000000000000000000000003857dac3fd4d01174cbaf6782b012d2b56725020929cce9952ce0475c67ea056287e85d95780e79327050683fcd1bf105d7468c584e61dd086c2783a09c3f8aaaf94164c3bdae3d88659612edc5fba6800e38ba824715b6237dc96ea8dd84b8c317c84563ee3a44295d902921a92c626459ed528fb26c7b13926b6941450866a4d98ed32a33eb4beca80fcff508a93c5769f62cfda1b4ead917353e22cae84425d60ac61e89f48b7d3e1ed8548f8383c8eb0e64cc2c3d85d4d52d5ad94f8c2f2b275166cec72fa62df15a1753fd0e3a39ecfe1945ca72d967512455ad1b872d6ae7d0c905b0d27b77d321c30292fee3126853fd7d0921db9123c8e98b9daa62436bceb851f4f1542328c830588cd7de028d7dc91ea0a302002dccbc3ac900c9eef3763b3f6967a539655cf86d78a89ef7022382bcadb2a51fa64e62a5c8b66bef088aea6b9d686e0aa4568e29e28ddb2c0e3bfa768d02b4990c3afe30000000000000000000000000000000000000000000000000000000018de6ec1fd15019812e1c2b3e36f611e30deedb5a60d62a2800a5e21b293e85f6dcf66e3cdbe6210b3470fd0ec3ad1feb250b087f1fe97a4a36da4f55e5bfda3feffd9c9a87e9adcdeceb26086b802d7109ccc4abedcdb334263b93646c22e87c7ba0c412600dc5fb55db472c21b594509e9ef110a0f10fe0d8a7276cb192495e8177ec228055dd1bbad401e14b981a3bfda547441d67498a492571d301c7c592b8a05b2d5aad3251cf3fc0f0b6ca396ad39cdec1fca93ad87bcf0c4cb1e074d18bc2f8d64f6dcef9335427ddf3073f2511a1e6e322ce4ab9578f90827601e436226a725c99412e93d8b4f4c96cc421fe766924cf82e5c639bfdb80a826a448edfd9281c3e8d99638458b5d0b0efbc9abe15c1a83f0d92a181d19cff190f12be38c67555000000000000000000000000000000000000000000000000000000005d1ca4d6fd3d0109d0107054af948a2f7f1ab85d80206c2d111e52a02fdc52bc6f438f18ad58fe4979ace46950f8cb12459b60d0cbfca39bffbce5f016c5c6916c63d21e2987a76dc6b291bf2cc1362b37eb1cc81bb066b77302eb73839943173b983b1fafcfbef5587433847eb10cb06c2a55d2d23e3b92930d27552e8fef6690b73d1db5e3f06795775f0a07a776e404114616c470ae67e6f074845500f044ce63b531365edd47802a86e0406069506fd8b01927ce03ae3ca0b8b1e19606d82f0d0979131a40514a3b3304bf50eb6896473e087370e6813abf68d67ab84042f3612f94152f1f4c8065d4c5d8350f9386a592c50df9f5bce6010e291ea2cdc86f391b1c5992f87ce11c8c03f8ede96e1dabdaca44c23e89da04e7ca924e59028b5a2a18b001b0535a4edb3e7485bd053d54370601315f7a0519eec10b9ef02eaba51f597020b5733cba26e10000000000000000000000000000000000000000000000000000000042b02f849b850a2f4938d7b56d85d6afc0db9ec0c0c23a6e0b9321a37c333de904dc8e2e88d40327af86f64d7221baa92a580c8fbdec96581bbbee9733f09c1c623dfb4ef2cb4b26c0bb42f4e3cf3320465aca67be99e48754866956d86433ccfbced928967204531aa3090ee7f588e11a458a4dddaf9ee7f5193d56ae95cbba955d4dc8e22d6ab098c0153f050fcd795faa8ed9a17a56fb4d065c36a09f11275d1e9ecda8f24d4700000000000000000000000000000000000000000000000000000000aec8e2a300001fceba016321f30650e0a147c8dfc6de4f7d2bb7b3e8e0d40a5f92c8aa747d8df1670c83411cdfd311acf234e3a9c56ebe4b214d0c9b99ef0cb3381c5f318fabf034c92f8ec6cd2cf6f4509850a584d131d38a6ec629bd10bfaaf58f8290a74f29f8d490e62f4ddcfae07b59967c7962ace83dc4fb4506e16441507e7c8ea92c9a91af6be770aa3649f2c1891e07e5e73fcded3ec6b6762274d6c8eab55a019c0d930a8c70329a424f51cb8ac41210aae262f3d5b2ae273110e2e8f6389a43a9f783bd2896a56c4ca72081a8c3a954d0cb897c2e4a0173888ca3630787723110096993f898c03a0d51ef7da9abace3c182dfeccbfc542750c4142bba5a161ccd0a93b5b693c9754000b917a05bd5b79270a7c96c2a9a4d0d12fef9b8c930a7ac6308532eabac983d07650d15b91fe358b96aa7b7d7f1a3aad08f2755baf4d0e02c791fcbcf8bd936583204fdae0116c24d8d9e5017d8dae77bb97c3b7e073c66096981277f18fe865a7270b8a636fb0a32ffa86eab5ef18cb0280fe6542a5ce9f944411ce8eece59a01f73134524ca062dfdc004d7e783e84628276816240a245fb038084c33265d9782061a5dc964e4a43e1ad418bacb19bff83724379d5a0df45b2b17d5a3dd8a6b434f7a4950f125ba58e8fe492ebc89a35f5fb80e0d587c148959a897df99a87de1da079a15e811da711b4e96e56d75f97ebb9b13e45002a6667618573a5b8fa35291736a7d9e8f2578d596aabf95f08c0c0fdfe8a3d31a89e734c692d0498b7051d5d373bf74a4d804ae34eef159eda2dd568b179c82aaccd864854b8c98388957ea73075ce6c68c681e3d9b40b2a86c224903a886084cd7fcbcde506247f8db1b4c5656c02c54d37f9d3ef31d1ad980de35a692b5134d456a1741a30c6cb121d2df7b1f78157739a631e8e583903537b1e103f567c2cb8d4072b04b1a0ba7bd5fd1e4e96b938c863b660569ad4b061cf292dd308074897300b23d2f7729fcf027e780b89fae832b5dcc236ebc64d878159f9fdc4e6592c5ae07a43777be86daecbc6643326b58dd9e83481dbf74d42a36a90fe9b2a4b2a5abbe6045e9e2076ddf37276c614d371c7f1c9a0ef95292ebe0457971fd0dc4e3f37c850f587164eebd76ebdc0786e29ffd52c12b6db9388bde3831f631f2b3afbb0650cf643cce5f05ffcfb789960ba6e4012fe598b092ec018b34e8171a6a1de3df81ccc979cad55893761e7ec70d89706d5660a8fd3192f86039a3f20708d44d6dd7b726f247e834aa5648231ecaee97d15baf9ba09f333195a587354e168d305358ee7185b16a10cd3f2b651ddfa83b65f632046aeae8e022468a098a353a995cf6cb69527914396f63fdfef1059e939d6c1f241ec1d1ab4f90f61d253defbae9090bf5fd1e01c4c70b19ee49f7fa40d03b5b93645f249475af6729c1117698c52fa2fda6c8a89083bc3ce83b788a4e5c67b92682556f1138261dadcf568a0e03ed9d7305e1b5b0cc8c6b18bdc677299ae62c4c6906a92530bd8ebc6060015cc3cbb36ade11d9c98b27e7a551cc83e5246e08a624325a7a5a8b9cca454e94cae68a20f10ea4b63648adf6aeea74ad764199c2ceb3a4d6cd2836a8e8782d304e5b5d44cde8fada642fc49a18bc5d7e78d1e6113f9f9a6c0b5cecda95d0d7e0f0026ac8f3a7d136701e3670ed036d8570d5108d517b291ec1779e49d123f416dc3855cc609641c6ef4f9b218d01e09c2ddde5f35e8146713bb2bf637e50357d6d954545671571bf02368d464f3a80d7703b3bc45a7e518c8bd23fe7b31b14a1933e68617b7a268f63cdfc0615cb046799338b2a8937369532885130f728d83472d17bb7a9a2e0e7f025473d6a04fdb7011b43ceda5924a8c04138707b2e813e05b977d30d4e38a7d95927ca232bbb5ea1a023f3e046eaeb230c247a51f22a0789d1f67dc92fa2dc0f783c8ace067fef686615396fd2c27a177f20ed4bb4c88355c8d83e0f51a9b31406f84c4a2a5ca668e86b4d2e64f46568473aff4e33ca21b7d31ae24c9509151331cb3e1ce348bec717db172bd4010f2e536c9d7fbc48a6960379a37c75fff53cddc5308deccdf38288b2f0245244b0ba1b45f0bd802870575b38dd1a8c9346ff2ad47eedd54115454579e6053b42cf38de9722fef7180b580cf13dd100681ddff75e8fdb262af179f2f11fcbcc8eed0fdaad2e6642c877fe19d22ceeef8aedbd460e2cda20afdc2faa27aa3463b2ca1006cba996cf5883b9b780a45606553d51a7050d512a06828ea9d8c97e5c7c3154e1fee1306a7ef6c82e344e334e652819253c6718265b15d83cee6770d585c313278d25e78928c83c6c45ad32ad8de1bd665a762db5f032088a3dc3b300a574ecabe3d872f4f77d4c1a758bedb646114ceb8730c7d58eee477c1038d3dc2dc405282f677e26903cb42b1ade7d55fa1ed54aef58c2886b8940924165ce863c80e99beee053072ed50a997edebac7bd30fd4b013f6b503a0891e7c112040930a235d3b311dd8cf81c71a6cc1df44120974a40521d685762d42260137a332a9b35004c729f5b2a2233ea6bd122ae8868b96b57d8d537a78420217b12371e6a41d53570ad2ce6a29bee8ae4b7852844c3885869ebe29f08db97658f2fb1e8f522fc64d2392cec4dd554bd4c69c7210dccb7d386953f742d63797370ec2821d1fadda679e30c42b30ebca43cb8634b2ae9d5f647acbe30d2c7de434695e9e0f9e939c8cf6428dc1fbe94a08707158216d326855b47de19704c0e1e868d575668d4a37f8bdf3037e81a676759a68327c801b292b42868af3301d66c6a53aeff11c8edd5c3030d9e9d27cc9a4c4850837aba26514ed5b35f3a76d6402bf54e10735a6877feaa47c74a65cdc4ea487f46ba65f4adf01800f5217949c9093835734fbc79479fb19a522d67566d42c19ec8089559b1f77068809edbf1affc4a57dfacfd4f0129353c77435bcda2d01d01f9d07e489c31c81c3138d95142be2b4a501f84231efb13db822f0b85bb5d46e055505f74ab2e016245f61d2a036ff83acd8e74a7bb5b0f299db3f0024b0755ed4151584c283452d67727403c39ea1f68ebddf84ee0eec2557b6a05dcfb5412c71dc94ec8e03eb393378ae853337465caf98903edd34ecbb34022902eddb1d125378f4e8d6d61e785a80e71d6ea6c5add25b19264befea329757a3948da8ad27c50e742d8a01bdb3c7175e04c8b8919ae46a930372c38c95dcc533ec2b02968592d31de64089385401725ff042e979fdd3783d54dff6ef9b4ea1bc210a8dab8ca449d0e205288850a0c44af79c50cf7e1b8bd36b4ce864d70b965eed7219214c324b7e378d7430cd9fa7b69cb462547e0ddabc889cb767d83d03153df7c405cf1bfc6d1789376bc542a5448a17568f1736da8ca895eccf15c094a62448966470fb9773edbfb7db4303b6d72ebfd018d6b590cdf7ed40c7abc80df6801a5e0a56e006cdcdbc6da5bcecf8005a3c6013645e49d33cdf10948fdb88a972ceba920a72e82ac0f3d0124fe55588137604eb4f2ebefdd57aeaed44f1f0328e90526644a848b548b16947366473b628431d8a80b661f5d538a9c15ed288cf7d40e144efc89f7509297533d3e0032c7b99ef1929956272ca693f76a40a9f76ab7002f11f549128380cc7204b80989822529dd9307153da4ab5712eccec3e4b2b8ccb425ae599cdbd7accd00355af6f190490f9d1551be069b7e6ec9d77fea777ea86ef74d61e19ca22bbed8489bb74b47ad8b453c173c6699e14b66b3f7775e0a859a020701d3c4ea36b04c74691c563f7e427c755571563d47b80f008e6e8ae96bf6355599f455ea68201e9cdda8289f48e516ab90dc8050691c2874b64110bd4e899169e7e153c9c54e775833f1b09fa70d026259f607aed8f35a844b3843afd49294cab5cddbd20e88411e17b3594cb350cad5cfd68ca304c6b1cf3d9fc9ddc714328e53ee6e2d0d20aaf604662535335303b33a3d9b60cf4be9c82758a09bf4ef8c90e9cac028d32317c51eac0690beca785c7c4b96d817f01fcf7ea184a2481edcf910bc098c82ed52f491e666d55f59142943cb667a35013ec0077a17c1e519a7022d00afbffb18ae0f6230b06049515c90846f8dee5e8de56080a4c2d4d053f8f0924000b34546ff0929693b484ef7fa326d096b905401aad28231b3cb5dc411fa5401b04f6add2268955ac986392b825185f5652007aaa3530291a768fd508ce9cf934819c50cf6bdae2435a5d09e323f714d83e6cedf4c22f2d3a040b89551a27153fbb967eaba61b2c3fc37278a6853f25c392f16c607e945abbc173cc0047165666e4ed2fa981c85cf61237e4a614ef09e84acf4158f581a1238ab4693aae877f1c969113c549275f12ea797f2119cee1ac1d73e63b81e2552063569a8e76e95006bba2f31", "spend_index": [ 0, 1, 3326047036, 4294967295 ], "result": [ "63c91fe826d7cda1eda1c7ec22e086a161351c0fedfab39a5f0511820aea00ce", "265f82de40725e29612043afb653e7ce4632d49214912d25dd976906cb8a8072", "54f9ed49686c92db01923931ae8ee4459cae5ec800a04471f91b3c8d6447428d", "4bd7c3490cef1ad26a759ead29d2be88f64523010433ce1ff13c1558d6f96a4b" ] }, { "desc": { "Inputs": 5, "Outputs": 6, "Witness": true, "Version": -316499655, "scriptSigs": false }, "hex_tx": "399922ed000105c1709b2a000000000000000000000000000000000000000000000000000000005181be300054c54e0220c16d9f00000000000000000000000000000000000000000000000000000000828b1c03008cd19e08b34c333f00000000000000000000000000000000000000000000000000000000930509150028efa61a5dec5a4000000000000000000000000000000000000000000000000000000000f5e853680099eaabf38cc2679f00000000000000000000000000000000000000000000000000000000e486812700ad935dd906ff2a3db5382ef145c8bd658166ddf1306a4d978cd229a096de55e63bf66f42e852fb94f37c68996efeba07923138ec6ec460e3f0d6f44693aaa89ed4b1b6527d84abc0bb4f275dba2758ccc4c6d7be64a6915e951cbc26c95a299dcc30a6651870d8f188e93a863410cdf0b66f8dd46c5a8f3dc08a0b0aa84a7b20919b2fe0f2a374e7c405cf24ecec3d00faacb82b9c72c7fae68c417c0cd6ab1b8c73a56d5e5609e3e1833ea4740ecda2c16866c7ce70abecfce5c12adb99944ead985c78ad2dc548740c64f4bb24d2539726cf4b4409e4caf865d1c8df26c8d01d6bd79c32ce0f8424238d740a04cc9ac3e261a41c780ca438343fc633935f44106a580f85209317b135aa84c12789d4b960d00cc57e041f580d557a993ddf4070bba3bff4b1279664338acb6790d3f038ec6cf1fb6ac921180cb6254074cc0ba05ba08f18b24668bf44afd9117df1c97553e606b418ba519db256dcfa6d48f47912e12d4eb471d480ff7dfb3f4bfb296d1099636ecb2d9387ddb131967bd86e3e5a090a90e24c0b10e7b2cac7fb1bb8b2e2e148b83f09bd837354f374ef840bc56edbb73e8c438bb26d2acf56f329c8cb1061e5d98898ca7d9b7259cb51de0fe913db80b314f79a7ad456543b03fd2b4d136f4232db804ba492d4f8a6fd9bc3a615971dba48eabfdda968e7eabf52caca7c0ad845d88ba3336afe1c3bff6a95afa5b65987b25a0b1c4f76bd336ed2ac16bf4cc7e8842363031a611f2781f679fd6d7dd92e804ac3bec96bfb9ce27a5c1cbfb2a03e478cb1c9ce4f8be188744468ac7b70c5076df6a4584a657c7d89c776ca662b6e42a48536f8f6dcca708c8620a5b900eebaed0f18bd8276e1122e926f26f8caf693b95849d257abcdbb204fc8832eaff01c6550fcd560e9766ee226def7b551c900385c586d24f3f98b733a24f2bf2d90fbefd5af2ad4f4abc72efeb4c73d287296952c068258a22f8d7e406f90cea5343096cd9b45db89de96273a991e881147b3d673c380b7a92b2784bf7fb90947fac99cd32b9eed14943a270b62e846a3c6cbdbaffb572b62cd613e3d34fda404ebbd70d6491e6e75547b5ccf7a2a13b411c67761b875b938730500c3827542e6ca4960ab78d91ca5b2cf8cf00f1d517601f1c96443bbea4abc2b9dd1ea6ab7dd2231965fdca577c6f1cc79492dc815ddee4a7e2fc5c96c8372dd3a24f84033d166a62c9becbfe4024aec470ab9fb9488a86e7d0885bc3777712ce0e3e4a26068fd57d0efe01c04712a9397f4f02e096368f9491ae381c063dcda252595d37cdedd3005589d09a4f3ff41682b2853696f83b534fb0760f4f5b46baf4cbfe9155c866b1f7690299f1ef2622af2c24718d36386ce690c8bbdb72fb292561c601a863cfa71d0a7563ccdebafd34bb41168cf46c230141345e8e8fffe1b2b19e7c13f0623957e89a0c9cdae2b16dc336bd13089f40330222282ef009cfca60d26c8523419558bcdea5af03b7c5e5035e6a1b4f98691a8b531fec14a794c60679baefc4c2424908877afae1142293bd03f4f6c0c79d6a7cd2c5034737ee3e407cf3c170294c18c3bc71a295dd2a23fd4de738547574940229a974c86ad8e30030cc9bd3c0016629bc83f579bd2519d3241f034d558e2997e20fd4070fedb4541af8f4feb5c9506765539e06efbff3b85940bf62f837ad4a425e6ecc67d35d15aa9dc7b2cf0072216e87294f49bd7da547b27648cb1e124c83521db271d9fdc6f1d0f0e416402ec6049e404fdde01aa5b1137253480a4f3cd4c1c7b46a72b0babceeda57b63ed0ceac604ec313ec117a0b69759d96e5e81ce048b5a684f7e2cc3170cfdf3470064e110a3948d4ef132fff97a9437d6cc8797502dc05f412ba792b048d620ea7b4353610619db1e6b8eea6ba305c6da1fadc46a7698a4027bd56ff96a7e3d0e34266b9d1552e51cbdde5d1fb3cf8ee93120f2eb68b8ebac2ecec6a5b7380641dfac005ec21547b994508a71b5a0e871d091a6dae6565fc79aabd13b18594617c3c30959a1de1835e4ca8403c8c3dc4beedae8303a149a12e49f0ce4cfe64dbcc90047157ff5a03061ee1b6d6cdc1ef27f1e75b67aa2d0d08449c16bdeb6b42c793b26c3bf9b3462b62cdcb29db21f720a0eb4669cf69d345c0da6d25ab70a989f2b2144991bb1d8231cd04e3c351332da12ccfad35363e1fcc1c1cc4551be2ee3322d07c6475cc6b793be7cf463733811cd88b487d9bd88a1cdf235594bf2db268e8d033d2d39e1ca2f77fa9bd27a2aed1a76a0e85138a685062b88bd50a0d2873d33559ac12fada26e98299d487583491a251d53a1e0906883f0ec513d3991e9b9086154b12ecca1e2866090f59d464571ef6d6cc8b11731eaf20e82e8ef563a0ba77f6c8f564ff1828b90179e83fc41e1b9979a42f0282c328adb5ea63d49da65964eb02100fdaa01a45962b4510a581eae99064fc0273ac5a1498e9d59dedf4688b37b0fecea4c50024c8a702de7dc9d473aa223b268f2a61ba19fcda6c51fb46d8d3fad2c0315d9d315af8cdc31b4c3d2dd7289d15a4f646fc93b7010ec188820ffac7403a0cef0767068a58d8a9ebfa47eab5135b622350445656cd880391e34c1d77a6137219e5455d222ba1e8e3f1c6361445c57a7834da401a616604de44e95f9f5c6b5bcf9cb9d88e7df9f2ea03372faa4e0a2df812295b44e719d0d39e90c047cc0d1044b1b55bfae0e9ead6479cce7eb189b538657e8355fef4f16a27ed44d57c0d86f957279096696b1a2e31ae1c61e1b743e434e8fb5855e7edd756e05787c016547f9cf658e2b7f4e0eb80a170bdab8dfa9eb756f4d6cab3a316ab97e6ac56816449640c0358eaf4c9ac033805b53f110669f1e6692db13c326e12fae93d0b4f00f843f129ba8d16484e7e61d57b3f10981c7fbfac811ab8cf27fa0f98e665a4020f665d5b66c8daec19e5b1a2e22b8cbacf66a708860d8f97997c5d14b0e2061426df76dbeee273199fedfbc4f2d194f08f47d9332a3c6d6798b27afcef2dfa669a76e8833917da247ec1c83fd4d01caabfac6dec16afb8842e9a6cb034173972133bdd7c2280a4cb0f7518fdfff9c4a32b413684c65a6852a5690c040f549916c1e7cb775484bffc5a35917d5505201b3f21e009285d99c71637732b24862f3c3b73e3e6fff9061719c72c5f7e932a0925748e10c81292f30bd8657d078edf359e55706cbc850495173ae199aacdb07bd0462fe32f9c9b7523024742c4da7ae42d67b7a699d9fd4fcfa4d430756525fd4dc78fac49c9dfd34085bdb4c8bb32b8ecf7fe144368e55110c18f65e42fc85c80035c61374f5c17681ae01c42fc16b926f6964052676e8919e124e4992c7da4af8473603487115e9d9a4924bcf7a0719e1f62c8f730d9d7306804a236f4cc476a7e4041944892ff1c8dab2cea3e8ebc13ce450d9b0a9927d11f63e62bec62fac208b5a35a43837486b8bbc4388fde307ba17feac696d2dd932fb39d8f78c8a112f03928a818a7cbeaaf875fd33011f77269619cd185e58c514df8c688eb1caf658bfdf1b47cd08caa126c278591eb34353e85a2130d75de2f482ba1beb21ab3a33021dc68a9930d169dba4046879da7b6497edf3bc48f436d64de75367e86588c057e399448ed5944bd8acf59b900acad0e79b293221213963eeedc3cda833e014be2097228d668650e9b9eb76767af829cda02d298a2bcc1af6bdfd742d1bf5b09b071393f3d18b461c0df9f468207c7a96f5d3fc08aa2707eb82569166870bee193cb8b9a460167f292bbda2cdaaebe3a0b42332ee228452b843f0a83f45dd6baa70e193288fdb15585eba9f8d54068e28b4acb6f7b07edd9ff589ff3c30e51e2dcd311de6343c27e2a8993334ce4def6e55c5f439131ebc913025bb77608d2d3c19abcc0304717ecceb47fcaf64947e6e37e076c20a2649c0de4216a3133d1802fd3601e4824f69db342e4ccb2913e45059653413ba911971b243090c175c06579038971e8dd31e1159655bab2329bb0155ec5ddb4680a2d886d503f3a893148202fd1ad1365fdbd4813b8a25ea87de955f027cec21cd203a78ff4ee9d905197b8d5cb6550ab0df4ce595a80690f28b832b2ecf305e6b7ac47a511fd3c60c9033d050b750655b62a87d133a57cc2f2b0804516de42daeb6a37f23b294a4eacfd6a368af7221dcb556a9ea0962419e636e87ea7bc58617cf1db6bcf567c80c0d07fb6282c175507397c9e513923ed8f799f91399cefae4d6e27f83270970eddcd8638b085a411d6b449c8c9adc49245dd5b6fec2f96f9ba406924086e8f2bbf228ef9f805e1a4f86a3740b2a80ec1168bd1d58a695f3a3655f1549b63f3e06944981c188f2978e71d4f98a16e1d0f63a4ef46b5a27fb40d04abefd480112f3aa9bb4e3db53c86500b150aee6e7dd4760a0745715baabea6746ff7d77936f95afba776d79ec0bb1e240df2481d13d96f51e1250e9b2c9cedc700359edc703cdcb7c14de860f18ea9d7cc78a94f73824e0bed25d4c9ab367c2cf8c240c3c9693e87f2f564fe03d5b9ddb8a8852babc1d52dc5934056e1fea8ae5c9c979a296a2dadea00c70c67e692e44d4552974116a3ce9fb6152990fa99ae3cf15bd3871684073f869c4834f1acd4c8b66c81b480fad93f92aa56ffe2d182f6d04d09205b06679d5bcd5f8ee6f3c32a613f2fcb3ffa17b94a521f69415568fbf5f8db20a61c8a768fc6730159fe88f634012316b568d4d4c720c9c5d67fa336151bba71a1f58818eece6ac3ccb3438c05a5a2fea8ea5b1663df1698389d4b5c92646c1dcf0c21bb35ab469ea47cb0e1ae0f03f6cfe14ba4f9fe7ece7571c2429d161f23054fdaea9bdc71c0395b07ead43163412336701b0e795654d21ac24d58ca14e0506f1a5ff07837881a89ab01b6fa6d51b2bf76fd292ceefca1bd9785e908f14322ed8affd8221ceef519edc243d7465d99d97b9962caa3e6fac0fc2432126995e55aa52c461619f5e1f58a936a53030b30e5841fdb1ba3cfe0d77c98d781273cce1912b44ec99e61b087dc0cdd75006997910ca92019d0d4690b5ce4bbbbdfdf0019c2c8e2ae8a5f4b9c4656f226eca67bfe0d3777f8e90d4cc092bbd0e7f32d287b3825c37baeddc7204cf2d9070335f07b3c22e0951d52794c47c4022d94d098b38d607288468369199b7840b3a121b3a1c66d52fc7380908170c96b2bbfbaddd4e88e1b3d3ce77f1cf7505b12319fb0eed5ea013ff55692534280c22ac9c0d9f827b4ec72475f1299834e1105ac0a01e98121f1693d14f5e27d10ce2730b8975feaab47a75dcbfd57ac432fd7f0eabda353410504dd77349b4e184d8f6c5aba889a1a2d932a0f0b2afc0d58d410d1a841c160f6eea0681660b462e9b7bcab5e302af4342edb17f7d444aeab6ae741441acbd3f5cf555ac96d6350e812b1fab75054819c97ac77e74f384e2a05ffd9de2adc28d5c13637a44082f75287914ec12062674af016e348ef34ef0d2ef4b4d5fd8e5244a7cd028e011b98e9150ba8d426d0fabc998e3a596be06f3fe2d7c3af46bdf26ed1fd37b793886040621e7bf57fce0154a4d194a157c8a6af3f302a260879c591a28b6273c65504b7a54506fbdaa97b89a23c88203acf07c62c36731a93c478391167d2c057142030b2d575d8cdafee3113b545c2ab83df742914bf86942c96bd942276d6d6ca884c811d5edfb80c83c2138f1561ff30fb713d3854683c7cb60f07d29376407c63c5a5ec7ba3a9ba700e7b7cbe0f3701ed8ddd849c254fdeb0112362c0b589764687212493c7bf438e05ec0903b77fade1db4512ef3bb1196d4124dac4f1e4657f52def9e872b0c31aa4bdc08fb9d1df950a00bb3b250cc73439f2955d6d35c1d54bd27d8d7c777cb16681862c39b894d142dea8dc41a15f591b378583761356ba4f039b37fe819b487fd932356e59cdd66634f6ee2f3629080c755caf495f5f3091be1c2602a663ed195ae3d7a77ccc56d9411477e4b2f57e218438bd0e2987407f982246835170f6cc6159b14e35c41178b57537bd24c9bf8db2b7da8267b9b10a4e82f62c07e689a059cff0d773d9f4c5ad78f8e4849feb772df2f357943c654e845e1f3af28cc79d5d6207acbb26325cbe9647688c0f127c5e0e8031da75923677e7e9c931875e036d416d05e2832cfe91e00f1de8615f279ae6182cf188ee75a7f605d87f9e0b6d6ebab35e0aa34788c38b5b7b128fd7119c569add2c3347d83300a86b2ec15e2c817519595fe560669811e172fc338de2ea61d3f774b9fc9d9965321d001845bcd773bd258aed2dd57c0dce66f6ae6cf42991a6eb9ae223fb6c50ad06815d6bbe7219231264377272719a286439893ddefd2ed180d21f3990ad58bddd9ccedfb5b6966fba304f0c42cdebc7e9c0994eb685ee7db79f3553470cc93c0d0f611df7195f9770758eb6b2309ecc6387ca7e62fd9b220c6ab39f657032803fd2a015634abd73829d0058c9960bf3a0f788a642ef098ec627f15b58ca5d6bb965251c2f1e3829c83ba3f8fea57aae92a4500dfff3c73d0d0a11ced732816261396ddfe85772454594276a4beaaa36e2164bcfa787b7493f40af404263d1c6a4d2cf9fa12713b46e9a496f4dca85f6800c4da90718942838c64bce8b370211023af5f494bad465ac916f728c79d379deb8ba09f6afcaa781bdcafc17b029907fbdc79d5d03925e5ccc4bb9c4c2ec79d4e514268f9a984b97882a8dbba4e865d7c44f89507320afa670b2a43851502a686891844b87cf65fe3d407a3d2bfb8bfee82b7400dd77d4dc427e16e71713af0b583212a27570479a1aa6461e66efa0eef33c6a4c3ac05f5249385a5ce0a4c2b50da420b77c1d30b37b5883b4f3ea0ef59d87b45a4a6acf5e6316207f1fd0a019488f32a6f3a8517dd3ba49619143f57f62b7bb1cfec8dfe18d5dfaf678b7d13670f49d65ff53f50f2dafddf1f858bcd7667b9ade86cf064058dfdedf7d472ed56365c819512fece143419daf7ccfbdb403835a7cfe0d3bb2718163e0d7046bbd53bce3edde7534fddd4cdea5786060d94ebab4b33bb74a833da438046ec6d787b3c7e88a24c670234b743ce69dba5aae453d5d2182692084cc0b238633feeb80fc684c863364797314e344d0c9bc4dade506574bbe6829c2dbc7429c6da5df2260a2c5306b0aedd6d2c830f872c9c100bccc5001598843ae5fcc26da830177e59a63d48fbeab5daf2b7ac66ef31469e9f9001da671b0c1eb2336df53628a081947f7d9fe63adcc8bddafdeb019edb952ddd6e0ad6fbef677caa99b000f96167fd13b2324adfa1d3c78ed5188159f5619b29604abc8e8d0ee8e8b888353a07aaa0bc6a3cf914fe737f3bbb0a70a142b16e52aa55975d383011327018d2110cefebecd8882058c19d4a4aa7f080fe4fcc781f43ee67c4eaa948156bfeaee7cbfa277816db60fa5deba4bd9978a7ff5e0566f3def8c0919cc250e304a3965279417010664596649f7b1ac400934ca6f8c9d1ce1d63c3086c9730bf9cb762414fad35019f0f2041ba5468c3eac7dfb1e8083014affda6ead6b2013c29495c6d35a5400bf544774e301eed5465ec3e12bc31046593ae3eb9d282deaafc83c0d8cf885d557f30be463e7e0330cfba4d6a69984ac978a6b5c391d6d1d28f2115a0ecf4d7cbea55153e3e9f0b0c219379d2c59aad5c83e952124f475ccba0fdb03e3ba62844a823777d513e481fd69bcba19dc62b014af2f9c8e482c163e061d5578c5aad292d254de96b191ba88c36a4ebce818d9d61d4933aad15be9aa63eeba2de6026e3b36c6249ea5c8c2699da5e75f4fe56cc157169f0a78cc9d3d6b12f985583a4d6e28de5e5b30c70b3826342bf8c6ace75639cc08fa4f7562702a307060004b18d07423d94d0e658c9a9e7141b625d85f1605942fb9e510c971c87193e72e3930e79c8008b948ff93c672733027c94febf341d293541ee003eab19ae", "spend_index": [ 0, 1, 1446282621, 4294967295 ], "result": [ "401b491b439289d26a2f389d10fd79ce500b93e9a9354a07ca063de47bd21fc1", "30dd1c57097fd956c04e75a7d3a8ea6768ff13a9dd990804926664203c1b2b88", "0b2095f09814fef07bbb58e07069524af34c0416e4e20d5766ce5b682e5a31bb", "7d175fb5b55e2d6ed61a7f183854e7fb48b822d5e2a5d62eb15963c716b22daa" ] }, { "desc": { "Inputs": 6, "Outputs": 1, "Witness": true, "Version": -943280664, "scriptSigs": true }, "hex_tx": "e8adc6c70001061d608d8e000000000000000000000000000000000000000000000000000000008dad378df19b99cdefcc47348448fb0e3f7b537987dcfaf7a09f1dbe4688f88b41f1a63f06aa3824f4c59baf3d47fe01fe38f012be213c6279ab131549f362e2eaddd1d5cb79d622ddcfd738f2588879ad7b3a54dca6c89e2c848b0a94461a2a279a85f4e40023820f7f8bccbeb059890be4596c919573b508f2b48396c00f101e79c3a8e8389ae4cb5b7a604254de0c8ecca3c7066cd90a0f83bd9b86e6723d6e2cf7e483abcdf7be88b41ac337cfdc2e4e4115ad7dd2ddc28b53a2d8b2c8f70c67cd1c2926760c680fd6441945a84b23cf1d1186230694ccc8661ad71e60f2610dbaf2bf6187ee5600e56ab30867abf7a3bf143b6b3eafb9afb71ed72600000000000000000000000000000000000000000000000000000000a3427510f5c0f85a2961730984b8f0628679eca08db731d39468e7422df04e9cde3757123e7b3af9ad0cad2d420ed16cd64869ae758c82ddf9a712d43fc35995419d22da479ad41714a059a2b6222bc2c7e2076f83c250488b245e9c229bef2dc1dc87fc0867a4f74267317ffa8281f7c81d70acb00f5751683ceed72c042b90a736394113c91fa6fc865c1fde963f14b3a98a67a8b555c516d2e5693cc7249787ffe875e9f2264b3daeea6fe84827627614ad35d49a74133fb63527de79de4dee0d7bfc3530431a7e699b7d3ed229c8a10cd05c1172ce249b6944b80513fe8fb66070fe9e3d24d94711943da3d044a11523395a11a8bf983da4a0eddea8629e315b00000000000000000000000000000000000000000000000000000000d0f1d3145df7dda966acd462152fd9d689cf4984fcaf790de587b8f511c329b7f9e077c7c0cc7ae556b0b3bfb93b5e66d4b4e23b30354785db6c1a59ca9f3b022aeeae09a307fcf75e16b0c85089ab0c910f76b3ee60e7db3cd8f2ac2daec2e91a6276cc189eaadf445c0000000000000000000000000000000000000000000000000000000029d9f470fd7f0116992fdb68d299e30b142a324bc40cc9552ab0f16fc59056f9e41b50231c0ebfa05b69c4807762552b67c35b7dc616112fc9bc34ff7afada3f00979fd82d40d70dde7a12a7865f2835819bdcd8088abd36f2b04bed21aa3d58a407ebd7d307de842c4c870fa4f3e265e5ffde33378d4c4e3e4b70c68b9c581e548adac0a497ad3e0cfd07e72c5a20c0ff6253544a570cdb65dfaac0df69d7710700234c5940d953bc84ad41f7a6142ef1ebb37c025dd9ecf6a61425cdb34a3667c2ced06c0dc226bb43a7815a079caa0dacfce9c7e88df6e4c55f46d2bb71687a49418a9661534b7afe10d7f767c2fab5cc3890c88941c61de50e5550d4f27c084aa75b698dc45cfae43c12c4ce5fcaeb56e6da34ad1b61c4f22a9c91a452d174d240d8a52e346ba86a4db16ceecc6d339c83dc551c63d03ac50c9bbc40d907ee35dba1a208d71476c072265cab4d34a6697db0ebf01ea4f69d152ff02282dc340f252c5067054d8b99642048ec672fb4e4bf6240a736d89757569fd3e694cedea8eefb8f6b284aa482a2c5ea1d00000000000000000000000000000000000000000000000000000000231ff2bd76521251147acc8b898b5bca7fdf71b404423f284e51e708785f70293019045937097898cd23a89f6df62557340e778107d77aa11f22a905376c41a29db9b0d7b42b0c9c5870f6d9d927c32baa13509b8907e47adb6e79718d36e6f01312644ab586d754d6d6e1a6445267abcb21a9d24549dd25fe79af4535fa8248c1271600000000000000000000000000000000000000000000000000000000fa14b3fbfd4101ebba470ffaa34deaf30a9658dd643d425380bc1e4dbaa7e56f7924748431a86440485dc60be0a1c9ea308535ee6bb2cd8c70cfb950a2ab7008929e4c9c845a77c3da89f7c80df45fa72f40ffd32ce5a145b3e6652a9d98d4ad5c03c90571977bc5086fab8d88fb700e3788ac099381b590ddcccbbb8c2fd7a417d5284cd75cb963b168f3a33787c7b7a56ba021c4f09fcf21ce81a0834ccd2839e920003882e7dafd4170b12c6c0ca3747e54651cd336e8122d11640cf99e20d0928886a79cfb391ac295ce06fb8b7ebef3eb34f995380be42830297091255cfc0d37bf92faefc9ca61e1dbb7e85d37d190c86929459375fd9d4b8a5c3cb4a80e2ba5a815b07f6749052579fbd6fe597920814490091239677f9fbd8ce69e6352d9508be69758b310cc6024b45cf9d2b047b969295339c633dd9cf008e02966dcefa60f647293844ff91af801182ec639fcf3f41cc8fe887bcf61222c015e771b7d6c6bebe509a563c88a5f936960292dcfa603cdd428c7e1e97fd1939929ae7028f665d2aa55cef4596afae6419d5eb36654f793cdc3162a8cf9bfec8c7a9c9abe89215a78289e259c8250fac22db88e10643bba30065fd53bfd8617cefffddd6ed8a1fcb637f193f387c191bf2456fd6cda456b1c359f521d3a329be8e64a8fb6ae43bd1cc0883d5a18b07e999497cbca30ae93ef079e55f96c2d01480a3e513c1808674a110cffc6c143c6c6ddae11cfd8080b6e72b1ab01e476779b01fd72014bc379e636939751a8547d44e16a7344b57221e4e59477c8325b6b3201a7f02f4a9b5c1c280bfb0746f011d84c1ff9c79b9b791cca1f64e93986eb3aa42c81fb319ac173dba4bea727984c55251841466e5e757c67be24f623433f1a5784c3bd1240af7afdcd5dabfc5945e85c7e33c797746896ff56cf2ffb1daa689cc45dc093cd3cd16974a7702580d0fc57881fe24d837c28d9b2bcaccf417f938180d67e83dee41d9a4b42f828f53cd9313e8b8e75fcf64537cb4264c411b8043bd81316c5f883dad2fd38fe41c160efb8d30e71db64a311ad87c1730322f48a77d5bbe57416ac51bfd60c5bab3011018e6d25ed68f271fcfd73f4bd2be810c8e3da310f71192b65deda9d79b069168ffe05cf444f2dea1fe6cf4faef2c1d55a9a0998f4ddb6f5c9bb6cf1bbac59e7455649e0613459f4da3c5c5fab2b78a1b93c6f36dbd32c92c91104fc46c3dff48df58abc159639512c88be297b8b735d6153eefa8c85b34fb17d7622dd9e6578d4ad4fb80c616a02fd3201be2e969368307f65045c67e44ccc3ebb559892831e75cad0ba0e1d3ab1a02e4cba46cabcb94a8418c7cace3b5f5696923977e85b43daf8e5ac7849628b2d97abf5bad07b1e7a114cba65499e0cbfb7dbd50b14fbfc98c234ceaa28a27152fded1407e7cd99cad33cc298fb9d32f03af05749ce022d73cbc0cfdb1342ad19bef4e5d1f97a99ede2678812c93d773f62f9a81bebaf56b075f18b8a3a6b3c1b91c94233e102317a8c6c88b0833d1e852f5a8c8af1c86b887043ff8157ce76ddbcb1ca113d5c284e7894b27578c7490ff4f2baa51e35f6ff4873568e15a3106c33ad73dd586b4a12d812677cfec3b42df0e943cd085654cb031e588a50eabfbb945efc96152cbc8bea48255fc1596dfa7ed107107d07a608dfcd58f5be49d255523bb23bba79c22f582fdadd25134c56050ef730fd0c010c902d0afde16b125a722b5212b9337a413eadc157a2737330fa0a8565d7c1ede5c6502e4918414f80842e71a7a6048543a9e61e49b67d7de21333479fe43ef30843c28897d1d53948a5d92c87b2de62bb076147b4de04ede2f8669731116fe95b975e5bca64f032fa0627fb2cc3fba548f23247b4632f0d457961d982f5b8717b2150f0e9dadf0e8942ff8196d813490d28c0b28387507943753c7919c4cb3a4dabb5943bea03c844e010972bbbdf86f2db7579c2b2ab8788b614b17be6fb721978ffdd3f3a51811780162161614aa6351e7f1e890a7f13ef7dc28eb4cb25231b92a000cad8ef265577f48ed9be5ffd58486f0b0efff88115e23b2a5050a07b58676c115cabb15a2c103f5801a4c286bbcad5deb72ff2325e45add15edcf421b11ead72dd7e86981af5c0d37331483b69284344c43ccef6e120db1b47c5648d6175aba7fff3341ab364dfd109ace8bbd54448e424b8bb80a940dd1b8865428c23955cba9bee9ba83ab4cb067ac3d706d95eb36fb87e67c47444aa6cb76112bf213341ddc255acd11834672c8630daaa764ba9750832faba54daa93c20dcd3f188c3641d30f719bbf3d1883b4634d9e055e002e30df8f436e1480ac7fe3ce8a845a46414d09684023555e62f56f5d2aeeccc3af82ea4993c02d30fd1e7d5fa5bee40cde77b5d91b2e4d1641ece2c79e9629c13d90c7ae29fb57366ef1a8098ee92f6f515d3bd9f052e3b23aedcb79feeae5135129d88a29fa1338f5b73adb26bc5e1f5f5892e34fad015e54945c187fe6e3abcc3852dc42a599b527135ba4dda1776f05c5f3bae5773fc99b281ecd3b5ed92adbff9dc54e3853a172c745a99113812eae3bb9fef5014d3e25dc41005851edc093cad4ce886bea68004ceae5a6787e8cd81eb855888f72efb2c59c9f78210db7e0f130b3d7c5352549e0aaf4092cd174be428c78ba235f8dbb9cd9cf0b06f26fad9bab87dcd08aabdd40bd005f756218017e02cdb3e99df25ced8e60d7ba0af9bf039903134e0cb761be0fff9a8e80fac094612023fa0b001df37f1b867f0c97303b89d89ec9101740ed03ab27dd3874b8d251caa12331e1a84d935fc60490d51d1032766cd641cd50351e4f8a913dd4042db831181eb2338d99b19bdfb37e114e9c1e7a5c9fb62533f73aace0d2b6950ef0b36729ad3aa4cf6e916116de2b227187d8547ea666878e19b82076027cefda2e0671972854dc81b9854587bcd1dc7e8e6e6ece36a6a1f612d58a8542412204a09ca7b91e57e4ffbd886f4802fef20f531e4a99faaa01589bc4f7ff9755d3c6e8e838ae56c7eb01c52c418f9501a4596b6e219727fd0e955fa322a5b8f96786477a77e26adfaf664b380e0b62b12649ed4e7f343e7a53f5953734b2db89f3ff0480ead74fdf201a333fdec92e56685ac2531974e0c32f6b38ce525b01657fa77badc73932cd701efe8fecd96a6f90f1f738097abae2b681bc43a0daf92622e990e9424a36ae01ce280ff2f6da76d533f8968416c5357ad40cbdb39ee41d7081f2e755a2b6a7116a294cedea31d186f4dc0b40e9b383b9cdeaf99b7b26cc727b1496b56444fdd815115ce80604f22f881b68a6927bcf36f34557e99f7ad11fefc93b2cce465a63a15a4ded07faf9e351286b317bcbbb7b57b739c34c85237b054e3a423674e64203706fe1d24a9f3d071988b7b3ac847020352448817d7c4d90cd619b8d4fb8c025fe05104b746acaffcb96f0f85a9aaff62fc44cc9b811eea896a22d68bbbbf9e54221efdbd0a7408fc0487d13528eeb66bda0256b0ea15ece241693618daf3de2165d08376c51542453bae70e711b861327cb6fe5e05b606af2a2357e9c5aaf3319c51f87da4cd390cd9715ac09232d1009e3d070a1170993f0b41066c1be85e5a72a044bee1087218a3e740170dd0c3de5e6c6be127243ac490baac1e54476a6f622a80b7e7ddf89624ce4d589b76c66c8bd7ecd3a1a6add51b38d9f2ac2c2c348210719b2af5a521315d689b2e2b5464455c7e9aa528c0cf2d0a3ef337600d271adae8a5aaf1a856a7cca627c81408ca36323b4484aabbe0fcf6c716ccd1070a3a00399a2056f96a0058b4bcb3ec49d6c303ae96fc340c21e3bef62a1db8d77ca8012ee5b5bf96f9fa05eb08e8f5616b52406f3aa5895de4e2ac980b21cce62bedd6d3ed04cc46bc272988b9bb4d6750d914156aed123e08aed4a68df2077c6f8198143697fcc8e8ed79d63dd462d18d627124803041599e2833123b85cade4c1bad3503e9b6e791c0e5a8b26577d4fa748b4e51ae75b9e77ae7d17862b2e12ad3eba748d5cbdb0704a9caa6fb102c12a42e8ed2d02866459ee51daf7b439e6b13f41b92f305ed41319e9e33869fc7f1940ebd985f01ff330dd17a07bb1c84fed2b4d12ec630d9f460e6faf8a1e74e10aa9f2a400da251377968bad097897e5fcc847cda591b7fbdd93fd8377daf174ca0aab86ec900bc02d49d6e7ad08aca6c88454aa351c42b2790b28a50b1311079d11b4ba02f259902dde2aae253e93213b51a018c1580da57b0f49a111534df9219ab944ab36629231f6ebd5322684526d95ea1eb4d562916601b622171097cdceb43a839990803ae71517ac15150285e54c809b713720c4ed4de61a9427f4f4ff3a03486505278088291538ddfa8e792112a6e65f13c57ca7c7767825445f5c4d43a5aeac806b82bae6b61b9077a459c92e5341e1f172f86156d536662dfdc7ba2198675b1fcad23488cf16d32d06aef40b8ae280dfe7015df1f431befbe1c05e23344072789d61a12930e1c56d5d9eff7ff8783366e4abeed891cb95dda9c70a50a472145d7733514b9ae2ba8ac9a2cc482a4c96f8ffb54ea75916e87b1206209cb273df9819b2a5ad66553d9b5e5fb148957528809accefebe7115fdc5a9ad6e65af7b1c6aac46b5fe8c7ea585aebdae333eb9b18500c2f22e60ed67544e1bd30fe3", "spend_index": [ 0, 1, 2131649645, 4294967295 ], "result": [ "33c4ca61245d3f6ca36c99250cd3dd0cd41727253d849c858da5ede5ecde4a67", "90779500f5ce8db89a47c08c7a057517d6f62c814093153107a03d98b30c05c2", "6b7033b441fafa098659364a02ac2e95cbbee6a8bbdaf5ca2991bb731765a54e", "bdd72df524ab04c74d98acbc06ec195bf33bc4b93ddf74bb650a317717f73391" ] }, { "desc": { "Inputs": 9, "Outputs": 1, "Witness": true, "Version": 485614025, "scriptSigs": false }, "hex_tx": "c9e1f11c00010948414d3e00000000000000000000000000000000000000000000000000000000e59e1ab8006cb08fcf73f1dc8200000000000000000000000000000000000000000000000000000000f1f6ce6d0097953b6a9fc38036000000000000000000000000000000000000000000000000000000007d1a45230031f6dc8c10dcbca800000000000000000000000000000000000000000000000000000000e31a9fae0065cefbeda6a6c30800000000000000000000000000000000000000000000000000000000c63fc07400097d994d032b7145000000000000000000000000000000000000000000000000000000002141dbb7002a68b86cabae3bc700000000000000000000000000000000000000000000000000000000a095934200235da408b25b2dfb00000000000000000000000000000000000000000000000000000000ac56b6a800e963231257a8f62400000000000000000000000000000000000000000000000000000000475e475600e2b549f601179a5db6314ea84bc865df5c0f6ac5eae793d0616fbc788219e8db4e5466b3db1f294fa29aee18da2c58e1dae9d4efa0c413ae6be6cd6f149d4a0a192bc213cfd6e3e56fc062ae231a497a940d6b3e165046fd39b129f478896ed9098df5036fa6f5dfa2af494d2cccfa14bd765aaac1b2ffcda4e686823586e5d9146af0aa81c1c61d46dd8ef11951516d957e841d8df0a7a537011ea5d2c0da275de77871b6921204b77215a9a7ed5232e5cbe6d2c4faec4f053d4839b8a84bbc02b0d3af82d46d6732eae896f7361a538717f4e8d77301267031b7effc2b58c3308b6c07d17b8d7b5f9d8f4fdd97d22b6fa13bedc72148d09e92384e2ac103c9fdd8287f24c8d8769f8ab7e78570a7303771be40b89ef19cab7419b5f67f2f31d4905e2140fd4346daff639d07ba1a730376dcf680ccd919cdb712190ad9a797519d4595eef77ad41f7129b577a174badeef18f6bad0e74b508eab661098e25c88eb6c3ee7de43aa205de5e3ae1ea914e13b5af00a29b9530dc2a4d7350957438411c6cb1d89a7ccc1f7797d450cbfe75476df523c14cd39020e84d8ef3116582e6786555c096e8c5e51f89daac206ed996f059f20037de043ce41e87fae26248d1ca0ecd53e8ec63cfdd7017b48051db5e7b9a5ba62f239b27794b4785103934e1e549d92801727ef659e0565278110d7ed2f974be8bcb91b4bcd6fb9c0423edab23f1252dee60ab55117942ab25c4228b0ae285188ab9a5947656f611a8e23ec3609cf6e1f3e1410af559839d6ac367e3eabf1828c86a6ca7a2eb9d8e7ddeeb2fa53ee197e8e0d35f998258053f17d6b478265842f583a5e8e05f11d4e20456b0c63056f8b7b43c6f3587850471dd7ab986b644dc7d99b1d3ab438673be36d2482cef1ece0dc3f167913d4a5b7f0a6a859b6cd70fc817849e06494a3878f812ff52099db85a0bebc8e86b0928628bcc0fd50ce1083ae2c669299551f9e6b953959d01262ff1bbe7e5f084a93950807fef84b0c450ebb5b8d889d4049be3140257d64e4be8f0d837e268093298d0bd0318b5a02bd5ff7fec1d30467609230dbf7df931ac8c80cf914785191f8395676fbcdc3f825c1d3e76e1559ec51afce8675a06f98a6fff56ac96c298deca324c40e60dbdac1ddbd91475ad9d4a48ebcc7508356e0cce22a37f25edb5217694dafa19a58b174f5f78b9b09ce2a6f45110b2ad518e9f4db533f4f492a6a01e14b5dffb188eb4c55518f07ddd1cf2eb2b83e854a897d30e4680e7b054a9476d5ef83052fa42adcc810acbc65cd6022fb6da2b84125fdac01a342a1dae23caaad4d16b3469f44e9a7b36f45a12e3411af6253a2b072912c899d363f2d9ae0f5e21ee8538298edb140f3cdd2593b8004de075afb13387b7d17320300d1c27d6c4ac8b8165bc2b6357b73169aaebe9a17820e991ba02340f388fc9fe622913183eb87e543004a1a67140892503b2ac532cd80b73521d85db5c582b97ff4a628f96627777b0d83b3b5ecc7f056e06db37d29efbba8de3f7569c55d79000aa24ff70858384db9d6e9eee1b02034dc0f5ab67888e5dc9d4de12f28049e79eb21613136c1fa69a09b9d74de7b94839a5ff916545318769be4180e5ff5c15766f29c552f181d88dbefddc5756d4ada904895b4e2cb9d7506165c40a6403e9f467ff22e98f11cd9097c83394e37090f3fe8ef0761bc9ca96bd1491f7886654e931ebffe8cd072b772369c3a7a37030c9a75fe950db98972920af52f6e119c477d58659f06e50c088f43218e34e5db754ddeff7789b7d955ac856645a445d2a19b4fdec8963ac9bbdc2af4e8aaf810eaaaf457e2a7caa6dd48e5a879457704a6967d7316791169598cfb3fcb258e3acf2e667c020b03126f3216a38bf20983d902f3accc14a73e48cd04fa304393a6d6ba343e96e6d4eeba2dc6ee41451570b1f78c1e70ee5b63115698f21f52fecb014ddd5acad48b3c71c7e1c73633a21ff89fa707e294a1094c0848da8662d18317fb7bf2f166e37d77073306e91158b161f840d2ab01c7f728f33890b329000a6829eb41311443c75e29d4bbf56fc5620a2d1cfdee67947ab3962423e00a60115e4af2ca2409cdffac3f5dc54ed09c5eff44e2860afbc0c2010f525e4071474ae65c075f5fb38725941cc99c1772ce3903b772a073e2436ac084fc0248f24b7e9bf1f6b12c316d0ef74ab4b3dbe410c00b42acf1e164feb59e28345e18e3406bd69ead142e75cf9a104295858a86b2caf14f4285e5a0fdda01618005338892559a941bbe08e44b7176ac88dbdfac6999dfc42287896d81f83f0550f1aad3db2c8e9ffcc4829a0e0f398d1b71498356e95e5941ff47f1e98775fa0dbba5392a3e85c4d187c8093580cfb671d3c3934c7c68479968c6d62ebe3d87867729cc6d9d57edd4c4da9ec3f62abc81423681f4a270b84985bb0d3a7a49532ccf5cf0d59d715945acba916c95389039d7c2efab83bd37bbcbce1b54cc39b11565b7a17334947e9c61efde89db023f9b23583371f6fa02d094ba8ee91426155c8651d22959d145ec9c77bf47a013e6497667fe9c2c12a667fb0b1b26ec18853a2a01a0d5c5251b4a0d1cb74d6f05423954872cceb8eee7ad47d802cd528eb0f1a4ad7ca489aa55ca7a676c9007c75162407640d4b2551503ea5c71ca58c600800c10c42128d24c25853077184f111ff3682578563f8b0c2a336644f2f1efbce8d2aeb15313f8ca7e92229cda2b5c628c3a0b3fd723647e816ff5787f43ee4c4c8afa0afaf15e45a71e3e9cc035e4398e8e7e25a5a9ef15aa1a5c8d54b2acf5db6f612afd773c156572bf2eaec9e7007c3bfd481508a35e950d596c266b836eacf4b2fdeb01efdcc3989ff3ac37eff5c0ccccae94c05eea3242b896f0a7037bca4682f56978175f2bf8dc7d6b1903374a28e71ca4702febbdfdf1015dab9d79165783a3324ad5a624a941ebd4e126e4909f35057cd46e3e2c2811e9d2925d27f9e4612e4c61853223e026d8f3398e5ff89d037f724d2908a7fac7c992980fb8716722e632ceaa451c141273625b761bce8add10eae32e310af7d05bab2552e70c5c9109273a3a2b4d408acdab7a68c9c00611e4616a29e80ecf6d3abaab07903570609dd943f8431f3701b3f5d65a957089335f73c7bf3338976337e804eff75f6fcca8679b6cfabedccd7d0201e292113d6fe20a8eadfbf23f56fbad98296879bc2083d1e6caf3faa26842605ab771251705e1263189dbc5b90c4b94b7ec1b7660e79882cf93fda08b62edea32947299b59ae61bd888d83559de50883c0e905cb8294500d60df4a613a62f34b00ca7069649a28ed88800e9cb148556fa28e45f50ee797da5b83afaad49e48449ab392875e4b6a80d2396a188c2a9bf47ff04dc7a05b604d5d044417fbe3de08f8b7048ac651c6acbd911036c16eed7baae9f5a6f19450b2b8f5f5b34b30a2ed28b6a1d51a89af31cba4d446a9ff18098dfb93a440a20d22cb06adb2916b2b8f79cff5fe916930b1ebdd42e12a3917b3fc7452af7c0d559bd00582851e3c34277c9bdcb50cc376ee6bec35f424aa2a9204f70b144edf20969a2cfcd209e2d7049ca419bbb0009a4c8d3ae67f795f7eb28d4bbb0303a7c4e71c9918f065468fb0cff6aa15ab497073b24b889680001fd1901894a4b3923c046b76fcd3d6acb61f8926c3c28b479b7c5386b017d8cdc6a4982d02a5b1a62e57bfe2bf15058cd9539146173bab291389f395e216e669d1831d6b0f70e7352573ce1166ed134b68253090d841d9503ff58d0d6d62bd9be62105a56a05738caed763f3066731ae907a033300e3da84c2c091bed0fbec57d034a0254627c52d9b8f28d87ddad29bf3ee2a709feaf4d914117629104bd0a60d7c34b91d52b0cbe008dc28d0fd3aedd81ea71fd8965c9be2e8bab0b015511671ad05e5bd8dc9c806a041018887dc0cf2c27ef80cf1aac1d1b345c1d8783e53702ca40d0328ee5f7b4118cc35a9608fb793d224495630c8fae050aa9fa4c6f25b367033d98714fa0e85a9155b084fc9fa7f6766713189f75dcb91246027fc00ac4644ed36c0cac7345bfb24f7462cf2f62fafece0ebfbe5a92ad3f2a7cb377e5bd64c5d785f7bb41447cfcbe163d0e79ba2ecf37f09c44209adda4fee988e56f0cfaa23191c0092c86393b044bf35c22857b69ff858a5b22aac5312c82f308debf2d5416014850d3302636feb72965d73c4c44d98ba2833bf5817e8321bd7d80dcd8762a5db570eb1e3168997f1d2a92554bfa3d8dd33d6111ce44eacaec37e1206b165c45d2e497e5c28b770181b52309a5a2ae28c0e19e33609b4a99c39239b80327ba0954d4a19a1c1325175f597e7ef5e4b4243d66e2b74e6438ac8db31d010903f131dfbfc0972bb0b4df68e4709eb0757072f4a7be1c6082cc91b85b411b20912d7245e7915767f7f0f0edf381de2ed411203cf323adfb5ef46f9abfefdcc70031f6f57cee8b6423c179286d16f72c69140adf47ecc8007e01fdae01bc9def0c121a1918904ad846f2db2dd97862b172e285cbe7018ac93cc5347a63bf8bf1a18cf43896a2c0c32b9eb96508dd4e52afca94e2d4949e238cb913de37fbfc8757de6d7f1622e1f80a9fab03de82f5201269c234e43f7e7c77e2fafa82196a5cf93700081a5629d1c1591aaf0dcc533e7aad89f11e195ae106d9164d83bc117d330b0625ae7ab914cba3f5e9efa4f0cad23f6b96af65834973e023387e1d5168dd25e42c20efaf1fe6f6540c04c698be4a372e26aae68e57b264aa8b21e35e124c89e72481a32bd69e298386d8dbd2f837ed5b325a6dcf245049bfb304fb580eb9ed2c0e12a70610676741389a241b0cfb07a2df412d5b124b7dab5381805f0c3822cbd4554cbccb27c2e42f8275e3636c0629494c5f592f256e3c026a193c3bdff6b78c5aa503dfe2e15561f0c06292e1e3b176e4b581972c957d2451aa8407a6566b4af1e4799d9b8a83de5041619cf662bfd50e7a36ba531a48d190bb2fe007b93d5de397fcaf2e6164480d3bd6577d4b6a63be31b3e0be6eb785a00648ec9deed2d1e7ede249ad0eb2d6635b507feca5e54be1786a04eb882197d71c38c0d11317526d8220047e27b8000005e515bd", "spend_index": [ 0, 1, 2773995730, 4294967295 ], "result": [ "17a26c6ac5835fea6a4d6768276d43c6d364e7d4f8640d81d9b75ef1a1f38919", "9c69c5727e1b331a00f51c90399781644cdac61b5e6e50468364558f29f922f2", "70ba670c7645b244ac7116bfac53c066f9aa483f5805181e601b3a0453e6c506", "3063e65347d8252812789922643a202cb5851f8de9506b1fd6b22feb389edb75" ] }, { "desc": { "Inputs": 7, "Outputs": 1, "Witness": true, "Version": 879929405, "scriptSigs": true }, "hex_tx": "3da87234000107e3d9f699000000000000000000000000000000000000000000000000000000000e02a8e129f17bbd3a719e5c419f786ad2cb5934b82905ee6d9773b0a2c224c9e61b43ced03d3f387560038684aed8dbc02b8d7e12960000000000000000000000000000000000000000000000000000000050e6e834156282c8744573de6a676668c7d6cf7deeed37cdc6df31d0964d339f715c00000000000000000000000000000000000000000000000000000000066de206008ae386ae69c9456c00000000000000000000000000000000000000000000000000000000a4e18cd8aaa758a30ff2ceef19b9fca18f10f62ea82e3b20af78e1406107eaa1eb772f4c1e92809bc9a0c10ebfe2dd6ab865d81936b53cc74d00ea45139f61d1057d3e8dde146a1a4f9b4dbbf5fc794e43ec5db10abf1d8ce61abf55e3eb5b3d9c1e48aae2a8791cd00e36c44e36d2a7292d79d2c6846d4d68d326dca8ea48675a7a4072621357ffcd99bb738b16a4ec35d8309e2c3b52393801c9396032a8e7a18705356a44372fbbd014d1aab2f255ec7b5712e2281b000000000000000000000000000000000000000000000000000000003d0b52060024eff817d8b6370800000000000000000000000000000000000000000000000000000000146f8940fd09017154e0794010287c09ea7938690c178360b6fc93b4e491958a1f54135372238c5afe7d176efcd03ba54df6ca8b09a675d776975d060899c8764216c8a10b7687b368c3e05608800c12d8e69a26262a1a9ac5a975cbcd0f399ebbd649bcb0352e2e45390d2e653eaa5d4fcba293df4107f0d994b7cb28517e8937cd728697a7f1960d408f1030a02001d7abf627634eb02d28b91f5fc6053f937e5ff9d520d9cc90fa669ed70e308560abe1463127e47f2c00d42a5e5a9129e5e70761ccc83908be832b4c4087e3cbb8e81c5e6b8f41816055c2e857db3e5ef3339e03df7b29ef4593cbed65d6b386844de7884fdc01126b1a2ffecda1905c827140f566c5fa97533a6b7fac4712e6d27840f83247dca51100000000000000000000000000000000000000000000000000000000e033ae24fd5801a6c7e03f06d046f97b11ffbe34f85874413f50c63972e2ec801988a6586084d9345ecb81b2e539d96fd52f52395d6e52dd0f1a958362f7311280c8eb6475b74b1381a3fc3b8c7be041c01517e5c1e9c55d10b46033670794e09ecdf1d22b256ffb5b949dd130d680dc2bebf175b3382b97884fa21a1cecd329361ea6850537f5a40463dd36ef90985f1f0d73fa53a84dc48ffeecefafb64f7ba63b8d10e3030a6a1e7ca3ad386d88435f236a5e0669b64c045ea22472dc2ca1fe2d6345aa26c3723952181538b3c9f4f821ad14669035168ec12a6349a25a5caab4056ff3a12651ac3612e1a7accfe16ce6f8a4633ed214145dc0a1ea425d2b57f0c7af659fbd47093e065cfcddb2646cb4396496026832448f9eb20ddc25025a1b24eacec73a56bf8d953bef2a4feb6ec7005d9557be1c9bb1ba9f2f7782bd2162fe9011a37cf058edb76796fe293eea928c207ef3962d2e5a6e1182156885b2e4e50199a51e28b8f42f38c8dcf65496688bfabab447460b3b8c03605e1caed09ec1933b59d7e80d55d7d375614a5d809082b5506072df28ebeff035c7b4e443fcb6aea5238fac882999851e13322a80b56333c13aee8d46e659751a435de60191d7ff6a84fa3b4b99ea066c9ed7a4c31fef447b22a6f4f946038bee9e64dad2a3721780d452bda78ef82864afa74c6b57068df83ea06c64b0cd56d7ea842815a989e166c6c9101ce812c1fc3c4cbdeb217d59ac4dff2a84f3a6b7e183e6ebcc04d6f0d918be5702b73a14874426ab353c489f9903fda301c3cc7978357621e503e46fa82a2ebbd557f2dc43d40cc5edb212242356bb089ffd837c09958970c8beefd7c9055540423cf13398353ec1190495b0ec26a64bc690082914f40c508754a281337ccd04bbaadbd179cfcd093cb8163d7c542b4dd5aacfe07761444261ebc67e612fb11ec447c031a06513362de39c2e020e8ec2bc2f4bb9f92b4ae1a1b89d109cb2ab034b177f07840139f2f39dbbc2614559cbfcffcd9153bcfff7df2dc946036c6562dda1dd0ec183235e49dfa049161c5b723a82594bde07681443cb9301a9dbde4775fc7a8df326be0b0119e7bfb97c68b325d15f5cece4169ec52e0ec0def4f0ebb2dd944fc8d267209d4dfd92d07917e0ec0e4a82094be02f8ce71a756b3ff6b90233273198b397a2a5ead5d9a7389bfca6d8d577e2bd0b1b62d719c296f793c2edb25a478eb36ee82f0ce0061145ad555258be0e582dbaad2017f31b4f705534cb874fd75d435acd33773d1f72e58d64d6901f8377db26b5625b8db4d0ea2728e47934e1506069211433df2124411bba5aefd45d6d5f1089a5117a5d7c86eedd6ccf50dc38a61d1c6c754f66d7319bae4af68ff54f5774260f059631263b80719326596d080a389a4ced0b056e34b4bf1a1adc582a925e36b35095022fe1f34afb3683e7b47e22c9c7f1a9a5a1b7a5a3d0080f3ee66e4e3050177f1ae9fb2402f62c665544cb32909fe85dcdfac66ffd8f5dc28c2869aaf0c2130be293a13b73414ceae0805d37ce49961084d34626ab8fc8fd57edf9cec217d2f5c25949b13540c60c27434118b4220437bf7d40d1baa11ba9533b04641d7742a175536bd7ddb66961a4043a9f05c61485c0141bd38a5db5e20d923347552c0c750bbc72efbefa53fded013057c3861415e4b829aa3fda0d7bd6db680c796d4802379b1f07a831ddf87beb1c0626c97109f3704d451d10980aed9daba4908fe96281e22860b6030ddb3b10c4445e325b92c28b75900dc5e4b1a62992db85e91f2c9443e23c9029af2994787ec03faae38d49c525885e8183fa09e1012464e8c4faec0890d7de43b0432b417c92fa9788fc54842d16af13be204704eac6064fc6bc41aacb05a8f2cd7104bd3f779ddad20ac77c8cb47eca14be27c25e94d9704b527762a126f5fd91626391ecac9a7cf74437ed1f99d12d6e47e1af0a6cbdcae2c5a771e1a24809a981a51de6f1ed9d3b623a48cd4b11c8629b256815b754b193de7a19ca01897771aa3c84fe150cf2dbac86b78a3af53ad743e23d1d5d58a5b7eae918b28de940ca4566b591e3c3052880c1c9ebf603058f8e7a82e3bee91c47032d04fe0817a50f7fbfd5989410dff894cf9b60189bc397b1c6f4a48b144233c6d2c8eb0210b8c53a2700280365dfedc4674e6779c5f2a2a0b68df2a4b25b4ce3f85e5fd94ae8e355d456ac8c076c9bef88fe7c67e409c038cb6e91f8c1f3570c16a1c1a0d0d1fa0916d07cad7ba438e944c19b3f378a6f76f912153c65055d9a68284b2f6085225b3f214d7da32dc3b2c13aaa0669c0be90a5d3e8d48a0188f6fea28e391d8317e824e631482208d8be7cf7b18c193bc22bf118746418906fa4e23a2d0bb7b388c89583c0356a5719b0abea895fcda3f499f8791a9bdb60c77d3c0e4dfdc50156f33279ecfa8b078776c7008c26162ced7244a31b08a5b371c2e2b6c5fb08bfd64052a447286984eff0672c191af0e357bbfcd8a91c6e9062b3095995ef09695dbc9a4a7fa79945b0c935a0ddecaa290e0c31ad46ca7c9aa27a91df67d37a0684cf6c8ae4716ca413b2c584033cf2aa1609ff3a57987e690fdd3d480d765779ebb9794d46a415f288fc2d52c6dd584cc265b746c60170bed30c33deb13a58118042e84263238f0e5076f7665d288fcfc14fddf06310d3447cb96ba1dc19f9ec8f63a258ef76b8ff6e9787792127fce45a78e9bbf042c55a2c7d0e2167dac6ebb218f7844b2c9aed41708c8c478b0efc4936460bfab33761d4c2c4f7beda53477304d7e0d7ec0cf521871adb9cdd436b9457ca7856659ffe869a6338a72650cef63860880d731a0d3ed51a6ff7f1d6643d8da98b16713c7012badce39e2aa0f5d19eb86b0eddfd81c39974788c95abd732ef93d3ce7e533dce0d25584d663314176875d1e0642e4858c19df642d2866b92e40e683727a14de01775dee9392fc12e52f8e1933ce98762e8371958c61cfff86523161c6db101e9136782da819502567fb8668ed6ae4a4b3c00eee9d75a710add723458e9cd660bd7467db8570e21b3e295a69f02fddf0120b2a480076d8ca3273de406cc7229525423c9ee14db0e2a5687f5d93d32c32717754e7d97fc553b0759f77d7efeffb969dfe0fb539773e3b8b2f1108e0bfe506415bcbeefe5a66548547e4982c4422b3cb45d17a6c928a82aff83361f78563fd27bb68bd1a6bf4ac80c4b455ca5bb28b07b52b92f398a693d9b0faaa91a43b7016df645421d50c863f3d284a5ea75f262fd958db498848160bb5776e72b1365fb25568c497b4554ef56fa153851517c328b8db1648074cc8b9369dc46f6e943e229fbe80c51820abae660c8109e6ec19da4cf61510208a7082782da275e0d5a54cacac70feef115d0f21947a6f672e8b992cf0977c2f561d1fa8ef9be6f9619ea8f603cefe04f53ee88a1ac46b1006c7c589d46c2faa71e4098fbbee407646fb4cf7b148ae107a872afb8532ad7b64c0cfb0a7770b4ceba4c201174b11516a7bf6fa051b331ea6aa928f0ade68cd5fb530a3d8c456f4f636266040e0877622ba9bffc13046d82dd158d5da579b964c73e9789f10ca9f63141a48453a61a454086a3d94a41b8c78410b13ec39e73330e6df0476caf5f0f5591fea5689898849a677440e3ab812b640fb103349abfec5e7d96f04dd5f2cae03d9bf927a2ec0477e293794fdc92ab43c620bddae7a44f2e90d33b0257a5cef70993a3b5ee2674fd51012f9d4c699cd9203ae3413599a60a3d13be84c07ea13c7bc9fc86b549efe917a0503df95aee8b6f8c769bdf671505113bee89f968da307658417f90a36a81eb36026ad3aeaee5309a05edc8519a21a8c8b88fe8d9b5da019a299b63e6a09be76c987616378151f249fecbdd1cfb237a8dee3bd8ce6b0f8de13d48f499d2dbc9aec4a5a38666b475034626fd9dc103c5952ecd1a54365304e3a4078246c723b72f8c9aadd4cff9267ab74c35412a005e42424aa2c77fb4ca11289f95b44541d9e29692b9d3934f902efe12d4e6f7446043f98b159293c8e120d7c1d2dff9b13764af85381952e172727adbc3fac1feedee324b79e503d3217eef8b47a2e4ac29c7e5b51fbf4759d6c84e8220b649590970d69b222d71f4a29cbd62bfd31110fa88932392a6f6407da69f88e16587a4f9485a2f982db8d21861454c1eabfc0b57e6f37f470adf005232fe5ea38bf7870a6dd302fd2e01218f2eb08ae0314cebd3ab6f1ca408dd789bb68c4fcfbbd003f22e7f1f0a56de9c0257214559b944ed7bd6ae7e77ac4b2456fe28179f38fe65eabd55b5ac6bb0c5dd7a9df2b7df7957b9e238d5bced728d294edad1fbbd9ef6cb3d6e8573469b0c5f393f262524e45365bade9e016c27f33d06fec702e9aeaf350b34dad52a4cb8a58af6079857c692f89d49699cc6527adeeb2ce92b290d8404e175b3d682e80b6a7311aed857dc0bf1f34aefd63304718e36af6e56a5eb420f2953d74be7bad471a979a43728584c2f1451cd210b72bd0c33ba904789fbdb6a26354a5558a1a5b5e532b5b2fbcc14a973bc8dc3d4de45c0bba21d578423fcf78e15fb11b20918502f053ad3c7edb7221cddce74b4216f2aca51245ec87c3575a6dd07f39c5d3ef715f0599bc72a756ae9653eb311a7b80ba9876b39ef4a4c168372ae5c616701fdeb01c8e175b9c8f8df7855306c601dea40508e31f9222106b54a071ff601e88c5c237554b1f5d94474ad30af8f31d53d15c1fdb291f82060e0800957422aa0a38482c06da373a2e6f3110c0937ad4686746d8c5615575c3c6a82fb8e7a2066b561828c197d6bef8e1416205553c3057c1a3eccce56f5b265f325ce04b3a39fdae44131b427048b5e92b4af3d7f84e0e4ec67cfa9b7b0fb5e16eddd96af14398a8d034ca87d38e33bc73b47fec0be48f64240d08f409cb005e9b2c99b3964f6cf3d0b223812c881f3393599df843c2ee7cef58f5bb8e621c365f6d471ab896ce890a4f9a9b2b1fc08db1565925c5aadb9978a4324122437fc96240ee138d1285b8a72866e9cecf3a3cd845f898c0d064f107735ba909f6943a89c3b347bb6c6246c7793994551d1017e9f81bc336a74536fc85f0aa37115aeb89edc84c2e19685d7339c21b194bab71e60301f0c84bfaf22ce591a1c29e75bce5a881b196ff456aaaba13b1a6e3a3374ec3dabcbaa5f1069557b0f45499d069ad72f9eaa944b9c2697ae39c8f086f68a64e38edf53b142d4700c5ef9d8362261c69ae7f1432321c6f6ffaf5571f009f7e76ad7056dc9468e971c96d300bc758c53d888f6e3ccd7ea3d807bc32f5a75c1d5b86fa4ae2a57bd06c60283d707a193975a57dca75d94a1bfe489be6c04e637bff5ddc10000666cc47d", "spend_index": [ 0, 1, 418482803, 4294967295 ], "result": [ "ba26e6ce9adf5b16d19356d501b84d5abb001097bb87bd903cfe0ae1d97cbe82", "cdb2989c82559c31ee7e9b6efd00d87c51cb67efcc371e2a8839a5f9502c0fef", "8afa6f573ea8e5ca2aed628fb6cc8f58e730f7179d382bb7f4311f0f205e38e5", "034eeec69918a72106275f882d5d75cb3ee4d62cb8b302ae70e7178eabf14a1e" ] }, { "desc": { "Inputs": 7, "Outputs": 10, "Witness": true, "Version": -709681065, "scriptSigs": false }, "hex_tx": "5720b3d50001075daf918f000000000000000000000000000000000000000000000000000000007da23531008a997eff90dece7500000000000000000000000000000000000000000000000000000000538f2e410073621f9515f3f0ea000000000000000000000000000000000000000000000000000000009d57505300e4d08d893086ce3100000000000000000000000000000000000000000000000000000000342e363a00913892234ff4855800000000000000000000000000000000000000000000000000000000d9606d2100c8886846a67bdd8e00000000000000000000000000000000000000000000000000000000396bf93600f6c564ae62a21338000000000000000000000000000000000000000000000000000000003175be2e003a75017e0aee23b71d09d01235c865b262c5ae164cab8ab974a731b034427f663ca7441d234e0d2f3395c8cd606f698096c03e6e7f16aa89cb2ca5defce9cb543ab636ce563fc76efbe4abd1fda808d607eea2229b3e5846ddce5234a4d098836ad5a0e1e385d83d5c093fc8762d99aae65acf2140509bf0b7ad5fe0d7518db59e12dbb02a815e9f39193abd9d2f90cfb24e989181eed2846ce3c443374d2c869b33c4c551dc76d5cf9163649d0ff11f0f307486e72a62d848bc8e7774f55addfeb573df387199390e0b17233d2d4c8fb52f6664d80a8c4d6d134f581e01c830425a7d6b904744a85df661535c10181e8a20f49789c674666627e4845a99e9b21ceae2f5fe70f6fd9d3b5414f5890debb6a567d8ff342e948a116db25463becd0f5d8bba1628cd629ad348aa64c88a98a38530e9b21c2725fe7bd303a1aae9dfc662326b9ebc416262b6bac942b9b5329626c16dfe2cbe94f72361b741089f3fd21203f093bbe4b04bc3fd88022db2339267d467ae6168d81c42f3e9f44074809bae6f7360ebe955473a557bd137ea22c357e25b2189726a5733aa13623e216b1194fcf2c13843769f42703f01ea54c86c66abc870200268b937e5a4e2d1b26c3b81d83ff702fcf271e2bc33f27b4b6dae4c9c14ae8e9231b7cd0c7275ac61d98e00a53820a4535fb4ed6b3c143d501542d5ba0678b70782aee279f4d5a1d8e72994df5637634f6af86d7c63f47b86ab4e0297577ad2a3092f0319d9b11779a22c1080fe34254f4459a73683ade01f149c3501253d63d8374670a74da878b372e9c3ab82a52c8ab3d8e7aaf0729ec8db4fb0edcf39c057b22ee92e30b814a5673ce84acf82393f4b6869a6a746834d118d96af4e47cc0752da70c687e65ee94fc8cf5317206c7db7f91638c9b040137e6023b74f68b8126952b28c14e4b538fca65fc6b1739776d57d47086bda8dab6565ca1547e4d18f524f3b204064d7cfc19b56059fa101ba16d3969f9384b252f5620ec5c18c934a3b23b8bc3b9928e6e782e045bedaa8021586f13fc37fc5afefa013fcc4ae8d80727e82259ba2cce5cae5f05d725732d16479b95fcb2bb93288263079fe943985837f4fab845d1ffe45cfac9ac38480dd1ba834780c27839ee6c0187277e0b621d609dc0416f1707385e3fbb68b2eabe5774aa6c320e60438da07c8e1ee0132659ec1f972ebdb16bd3484d220661a09487b9c03c480052cdba71bfb1994931a6c2db1502e18e0b8e9981ece76095fd881aac299d74a48b0aff91eddebf7f98a438842e5142d4724905a47968509591bd5a003448e5e3ab3e1cede5fb0c40e305c29e44cfe6f417d128054d34444eac07f5bc4f408fdb66cde818774107852e9bad1bb19f78522ef925d42baeaeedc9b26483063c6d6274dfc16987bf0a32348588a6d45632797851b4fcdd5ece841bca13680d1b422c3f82fe909d9c5878032f976ba802176803cb6792568c82e8403ec60d535ee113d1d888ad3101ebb786dd30ca50bc8e3020c4a4bf1827f8253cab95d1a6a23b3ffd6862e6715626010d1db514213db2f87d5b6172cd804ee9d1873602b023174c9b4f9066ae77fbcc506d83e9bd2c39a55cc8f19956d54f05b88ff5b8bb707e829cd8f8b085a485fe49acfc7939ceda32f8ade36341a9e98ef5309515dbe57b9b3a4aff3d65558132bca792f626684c82764f6cf730e265551d737f531295713f4221ef5c70927be9fce1ac39e93bd30ed1c2e19e9f474b5cce0771b464795d21b59cea8caa60fc8bf9391ac806671d443cdcf6e5e07eceb79e0fb4f0b89f654afe3a0d59acf673ed00a641c600086992d1ba6cb7174e8cca3f1976c7dfadadc5ba544851e844e030968a67bcdab64f5753d2085171d96e03bb4529aca0ac41079a81987001b59a564542afc0f5183c30d2f14e6d8c6213bca6d649856fd6400368d3386db1540198d74445e08acf8838bb7d6e05e8dd7385a83a7fa0809a1d715b8aa324b1438a7f649c48ba08787ea039bc513d75be634ac3ff1da177b8438afd7191b64f5c7414d2053531a6c98da8d203ba2ba25e64ac8a088c8688b78d1eafa977e80f021e86aee9c3f9514357888748887d16021068bebee1ae4e086a1c6c6b2ad8969ef2f091c737307011c5779f9722c4a8a2c0ed6b0b232f7412f296cf1099e8468879e822431fdc203c7e3e6248b0c45f674832e2ff53b9976e3b6fa1576050de3adc0baf1adfa9fb42557c574aae18fcb7b9e7ceac1bcc370771da3017bb7568df624f2552478607aa71a2ed66592db423145ccd1037acd9155aa4cc4de1db42264602606cf8d6cb76c32ea9d973ceab578479e1cb686d2dfaeb703a857420670bc5f0fc8d118dbd528786ac4d2141a231385f02cfc7693c370ab4d2c9a62bbd3187a425d135013a0171fcec67e8ecc5c393db8b8a08518240c5ae30fa6eb7890a84448ec714c4e6f148d9b62ea48abff19e039499ed2c90fc775062ef829367c3a1ee0ccd11697fade32ea84c318d9dbab2c94a28e57a04e01dac1a34391d8eca56baf60484724a6d41497f926b0c43003a85398941b8d97e95187c0cf667349cc75b04bae8d458da31381c709b7f343ab9c654cbda6478b0a0e1a71cc376da34fdd62d2e9d4625aadb0062d64c0b1a493057c4cc8a92ed4b0ff0d28793a6ccd4b3035d235d878a45d66b1448182cc44308213f0382f1e551ed559b15c5cbcd1d559432a7c2d6be60a1bdad2baaa1fd89a50d80f2155ba511037f29eae8a7d611423f9304e846af72bc3ec666dd1abdb8790592bae33c6b86150c9afa44accc72a476a390b14a59bd5de1d00a6b755096d131f6ffb17b4c276c32c2cfe59805f64b5afaa4793aba92001d970f5a155bfe97be3ea4a616227cc1481552f6f509d2f0a55dbb26cb47a7982dfa53b74ab328bf6def73ff01196b0023caf5d03ad941e2eaa3c07e5b578c2fc3d375ac33137a51997084f584c99fe97d4db97bc6b51fed7bc85a4c8cd447f19fb07f5099b7e24f8b9d2cc47000df906b0d62825743d0f077425ac885ce6773d3a87192237c50392688592027a7269e1cdd7c06c03920577e3e846e07ebc4c080f1b26a2bc83325c2bbb066f6050465178cd481b65f7e36e15f4bcfaf0fd1925d238a1c80ee2f689537b09128cd0f6eef9ba1ebd04b3af97cc133f9844baeafae1153a3e0aac978b23a528aa80d87239bf5efaa4caf1019424e928c45debe598ead7b769e062a52aae2a33c82a1afd1c08818935d1df635085937dd4a7fd0101fb14f58825e93873b9ff6cc58cacf3639fcfe0b08a2bd6709d58c03ff31486100ba6bcae81c64e9c660f613bf5cdefeeb1cc66983417462347050d6641e4dd83ff4eb40330b47a2eb58da9c4081e899a29806d25f0c1e9078508d625ecd5cd9d7678040a74072d48162f6ee8e984decd76173a3e73421ea3c2341e20fb62d7f1ecad494d041e0200eacd1a16f863ed3ea103280f9d8a0c0c007e397dd3feb8416d2f15fc40a59bbb1ea3c25ea641e6cf7da7ab3b15db3ef5c93015fe85604fe97e1cc19aaabc48ac4324893b70e2c7dc23803f03412ce6a995e149efc2af6f45816fbc18b3cea8039a433b0b4ca44c9870192171065f061d8a23edc994a3c190a00001fd2701742e4c31fbe9a6a948b3bb7dc501bfb242936b05cf023e2cc8737f90a2d7cfdc7ecd08174a286ebdf7db56b3886466ba473d1a8eb5712fb0bf8dae86958bde69b0efe02ec7fa8fd5b57eade65d944acf4e2c74551a12feaec6476ef415c3d48b464782136d13f42b390bea3f9dacc1c79def8b59f1b7a268b4ea604c0ce0dadc060e62ca6245a893e51c7b119b215e3ff31407482dc77e8a552841b16b37a0d91aa7d431f7a577d5e26bcbeb4c3ffb08ee83b2ceff8d200cca56e1cdcb4f4530054dbaa21d962852d1f1834774e82b287f365bddf56f1a23467aabc04c38c3f0180326cf544b7a2942594c204430d2918e2c383b54f306cd96525e5c613b67f1997c941f4b2b1cf5884b847c9542625b48aba16ff78abbf8fc01faaea6bfab8e75dce0047d3a5704fd6f01f3d69bf4d07de4ab6ce0c1fa299b50cc19d285dac8e5ffd86742d07119b3a52f3de835b0d9ba6ac11f7c3afab482024f476807dddc8e4eaf4f0cc8e959df06bddfcb51ebe2976066ce49067ae36249c1734d43583d4c2cee3514cd2285f794d7aba35f6ed44142da7a4b03d35bd479113d300db9a9eb78c596c021bf8d706e19e3a617ca14f897f1e3fc1f92032b872186aa876fab36c32038e6ea5a418f92d556ee7925a08b94a17cc5042fde4f1cd9c1fcc6a96fd88b84ee4a5855521c1e4480dd156a7cb86f5b8d78710d6c09c7b45e8fe99268a1ba97ccf6e337d18ade3f3a47159e3a959c6f3f9afe3d42ce210d703ddf7f12f03919e1b9d8396fa55f88b02a6cbecf8b7c39c991dc7769aa8e287725199ebbbb5d2b6d72b5910c719313826940b2b65212b89d40af36ced7ea0f1a26468c88f9cb9488fcc2ecb26d9433f4cf40d892d7118f534c1f3b4bc599dd4d8acac3bf315c2ed96c25c7b1c27f43e345f0c34133763ca673e94b4a06bb7cac555007eb8cb0065b64338430cb7abd09103be12487192489da6a656d96cd43b28e714a74967b9c6bb40b8ee39d3571aad5dab251f2e5750fd2a4bd768a0d3667f8764fce5ed82971812129f0d330b2b7b22622baf525cbafee81d309f95a95b8c5e61faea5933a810d6681294bc7ea6f879cfd026b5e172ba905ddfd940115a8a51ac2fcc8b256b9608da1132367521d508fd7565978b5886bf547bcb61ca2ef122508afd507ab19c28f6b927e1925d522c6ad01191588442f94573a80ec45c5f6e81303982e0ad5c8c20de87fd0035df40d5e2331d32d85253e9e1cfe0717d2f56e20625620a13a961fbdc6237fc3ca09faa939201b077955a9286d8c6607638f65724e3b37c60a0e4ef7623b0e7705577af8fd40def56a8fce3182fd3765adcd586f5b75963878d89b20d738a5962b3cd4e2a23739a5b89dfb26d9422c414c963c67fb8c9aae70ef5a5435575fa94848ec7efb742c2f7d25aedf2d143443a4da032697b55f5ba87f50e78168445ad8e1772f28c3f14f9a571b0d7275079ad8432d937384123fa39872c88d1a8f6b205b8cb47f305bddce550ee93fdc48fad3f18cd6d8561a1cfef9c7410dbf1ff254641aafd01ee09b1e69dfda4196d7285a4e3a8809cd498603201bb10b6bd640d307f1dda6c182d574d7dcb8dcc29094406245809340bd95d4d223f9910f8e0d9287585800a21f0664f19a10be0f0b987513d65fb2b088a0376fb4ffea57be528d34ac405e3699d7ea9e7383f03246137e35ebe578efbe9f939e850fa65c3c8b36de6233bde8844966f760d3ab8be961d7d5e92fdef2ff705e0498e2265a7a0efcd07b3c0003fd18016fb0cf85737d24ff5700d01ef9140a3bbde60127a020e1f87692969c5161e51daa74206dacdec9ba638f423d442fd7352527cd03696fa3da7d41f9c1cb620d1e6c82d72d9d07877781b671e7cd39caf63277e2869bdf0735a9170c8ce15c9474345a1a513aa204817d3f62663fc83da84ec7ef07fdaaaad7656da3d7ac4b58bee10d3d5b813be5c95a482811fceb6867ae4e518664ba3439a647ee02e8580bc178c096e93c02505bc8a43f4ff6d1e133e7f4c7110ec938d77cca6240fe97b74064824813de55cfd6bae2fa05005320093312bebceaf4ca3fe609e9f5c8a041c231b0ecfdd5b12c76cac786e8b3984932d225ece946d4a3ce2512c4646965ba54d59c162ae71383341a81c0b1591339cc8907208c0cf9d1e7fd540103990555004ed328fa827e4b3a3e14a3d1090e36fb54e7606d0645f148f6adf0fba1dc44587f2572d3307c23696ea2f189f1aa54c49e2e74d1827aa1f2b5cbc676bbff2a69754b0c6be65e9caa98275879a5a421996b212f9660cff59357af5082c7226c3ad864bde65f1907f3f0abb7a1000c3a9da4d2326e3f41920d21d5ddd22f5b04b3b45a8012b95379eb1e68d376cb182512a4af8b0b716a98f7a760b50eb3b53b30e17a9661603f6bfb52bb438d162b5a2aeb26dcebbc7182985d182b0dfc1835a4ffee8fb18bb767ab2cb07b159a333652ef15df7ddd96d22d2d246cb1d8fcb1f67976df9f6416a92098338e9173a1744bd40efe60357c8d0a742ed2c87dad4753b99decd40667f9893644e6956de0ae02d97a75fb3ae2f664eb7f6f4af284939fd7b7fc4c588e624cab5f5bada9d5057986fdfa95431fa6906beb3821dd7e4bbe53b880d134c273d44e0de2cb151ec4fdac01ab4213f9e9a33d8967e7bbc6545fc623dc72f5c8d88c99a937f5333a71d0a3e4c29e2feae67c68801f215077af579cf47691b608819504b355a26adea026a6dad328f860fd6dccedd1b555324d2eb0e4517d90ae9cd2fd26cc9a4f9b3385b0624cd5bc92fe68506212561998b883948626879da18c1066a502c089dd097be8c71923d5e3d064fc588464c66e19a7be6f460056225c91fdc1ccef65e86b1c016434b6474f30aac1df6c443a7e32ce84d7b6fb54bcf8bf29cfc3c24d771eae136ee072ceb69de5f36c0d48cda9d91d853aa7c1566c77650cef0094b613d97aed46a6111e9f76ed8f983ee80d607fef12964b2f8063ebd13d5084d53b6c2b962a7733718b093906e223982d4f374d806302124778b86678779d8f7f9c73a009cb1a6577bbbbbcd299ea048e6badf2e40ff40e66b6972cb01ca874155e46095e2c5d950ed233f8a7f04fd79abff2405d0b5aa0cfc0674e0ede98a2de90e88b1c2843dd07cd06406edf0a562fc81aa817ec208fe75dba448287affe48f3422b5a3f482401b9a43740df1dc7fe341e3e68a4d281237a351abde1d38990032c439b43e38d1659c0a19f83668819dac300b20727bc", "spend_index": [ 0, 1, 960680172, 4294967295 ], "result": [ "9bf8dcd115918c86a90e3b1606b7554a0aed8a8b4ade64fbcf71bb7fc62f155a", "653676421c9f3c636ee50a1ffa8b0d78e59171b87248f1424ed423accc5f08ae", "17b38e8a8c1ef172a80aac99196bc991871c8bba4849b9ce8f76495d2a095bc8", "d15e7d2504f6742cc4b97bb65a6cb63978ff211b4bea201fc241a1460af2c407" ] }, { "desc": { "Inputs": 10, "Outputs": 3, "Witness": true, "Version": -1391982199, "scriptSigs": true }, "hex_tx": "890908ad00010a6a475f400000000000000000000000000000000000000000000000000000000063c510490057d8d8723a61c938000000000000000000000000000000000000000000000000000000008153828afdaf01c488b682390682cddffd1b933ade8c7aab8ffd7eac633b9473b611b3c543d2d7bec08f85b60a3e2902f5f67264f7dc47836a2cbf290bf27d1602d7a6d90d2dd9552f39dd9e317c208dbb2f4e637dbcf41233132191ba7f53b65964d386133eba2d4f3687d9a68001dfa1560014d38892ae433fd1404a3aa68ab16806fe5cadd97c3b13f22499c5dd1aa3bf26a15a2ed4ece6149be46270817dacd78ce297c55a9f86be94d2044ba52c4adc21b9927d45190e319776ee41d8662ec2f6dff25adf7e07c733d9571a0370ef2f76999003c783a51d72589fde067861364519fefead40a40b82ff8240eafd48e54a19bad50e9c1b6cc75c7165a373313e9d69918fad7073ee75781958c8c1c2062e54e2cfbda0572a693e008de42883218bc3638d71c54e862f84835ecdda2ec3c5cc9524319e055844d672b972feaf3aa22e5cd8c5b4c288bab928d903817f8837b7519a25c6ff07768cffe20b9b80c867ef4b4b2d969ae50a44163c2c02ec19fd89de62f9ddc9480c7fa732d7f7c463da9418a7cecf5919b27efdc0fa2b4e3eff4b7583c768c16b9fa12f20899a6a93d43cc7da614d151343c2449d5a503066bf769f2efe803d0ca97f20460000000000000000000000000000000000000000000000000000000030657987fd5f018cb1e741bb2e2fc23de850458a10d142e801866b4cfb765bbe4515cff7bdf7cf5c1a25643e81bc27077cbe1e2cf800e97d01a10cc224328438e3d8f1546b61e86d00df12d039d714acc3c4bf36043d231aad657d48af77ed7f99024e80fa87e5801e2cab470007e536bbec630c2fde13d5dd3481b056f64bc78f30054c18bee2337a23a1ea4d19439def9662c620cee8fbe3224a5d117a944e264b9152ef1300b0aa5956dc6855d628c5d7043126ffbf5b4dab4218d5145704ec8f2825a41c9a831d0e53ee5c0607b6820f48f4b74ce1b43f3a853af5488335fd614a71c27bd4bd75ea3dfd6b8f1cbedee4aad2836e974846f4919c86b6625015ad5f97f5be8a1711b1fc5158e03d8e4cc42242c0cbf680b94f3300041dd8549b05c880140ee7c740dad0eb6a85f38cfc55be23edd782b292f272687dd4ecb326145445b86e2c7f0031daf218ecf03074235a3b1deeca85fc9904154105712732d5e69263378e86786aee1ad80a00000000000000000000000000000000000000000000000000000000bfa25a9ffd00013df8bf0124ac40a0480926d053d900cb0124d8201ad91484539c220b9b5fe5ba2e739837563eec6454b7fcb08501dda4c1be099ed3d1a6033249c2bbe46a5b1958d3ff9afe0a6bc900a3443089a8e2c7662afed4ae4fad28dd42bc917c28df54ad969d97f537a97b9997e6bebfd187d0bfc78e319278d0ce5021b9ff191af8703b3f0047fb702a964a9f280477ea813dbdb6854c2434852f81fa1694acfc6f7504604a3b9a4d8ee14f57ae65e82843ef683e57259273fe9aba6d4b7b93c539ffccf7ca9c9df9fa993e60b83f434da9002763025f4a765381270d72a176104efb54b232762511a2720a0b8ef1e67f439e84a581bdd33e2c393283724ced33b1c69a43a11310d074c70000000000000000000000000000000000000000000000000000000065cd7f7100163808f7e0b6671900000000000000000000000000000000000000000000000000000000adabd5c8b249f3e9ca8e8f7d0e926557de444ceaa6f78d9d94598010997a0f2b8de4b6adeca7fd4dd2edd1092eb8efad4690878352afd361a6ed9cf4ef3fa88c8f7e1d7eecc5f226ee6b99befdc1a870f69b9b060a26752fc84df3538a0b540d9fcc415717ac6d1f556353b3ef1796bbe5a593e4e21b7f44c63f4542da3998438c56f3153cd1da54ca41e6f04df771b88215f9be7bae3670597344dc601ea6493e55c096759a468e2d25966a1d4b0c771255571848a3900ae7a130689904bd00000000000000000000000000000000000000000000000000000000bea14f12003f022e6e3100d25800000000000000000000000000000000000000000000000000000000147bf880003e813dcef0eab32f00000000000000000000000000000000000000000000000000000000f30a5748009ef8a33b603b8d5f000000000000000000000000000000000000000000000000000000005dc8f84adead025bcfe625415826c25c9455041dc5ac55a7c4be0f7d1e1fce4f9ecd313f1806782a2b6280464f8e48f5c358a188df8b61f4cc42f2bcad20884c934eaf6591cf1a8d6e8e508b45f23ba4fb21f6d0e4c6ced04e8da7859eb70738e152a0753e769992d5442b7c0621e4af77cfaf7e77e893da483633f4ce818fe150bd5157d61eb5131cb9a3012ec24ed114e7481b25e6067975d97a16fd8be9735b90d3bf27555e6b7cb5383bc3cbbad292a77ac4fbcfe9c0ac64fe7d479e1f9a1f1b5a6a42994e80bf4f9f4f9db4a568fb149b2f1bbb2fae7ab356d3d3cfb724aeab3636043664032ae1cc41d9627e2ec8a32a30d53fa40976baa952805bb2beb4278b2bb8d7a051de49e2f36d4d8e70110e5ca496416a5f0ea82c341c4ed4b8c7f49513586891485fcf2db877c5d26afae97ebc92ef04087070a12a1cd20261deef5d82b7393806217476eca4627495a852c8ea327a47f9845b14a9d2decfbee4ea3d1c4fdffd12aefeb796f77ad5661c17315701f9021c01dff98d85f45775c680fc805c67d6a2d95ae4df65a71b0be89af31ba113af8ec656d7896ab1468f7aded2c35819fc348237a2a493cdf7b9f2b377cb3a17e400fa4d42513af235fd62c8ea6c44ffa248a0ab33f44cc98fc166fe72715f8c21e6168c6f96be4322e0611eed31b1edffae929912dd497654e63e9399845e79ee866079cf3af2845a5f130358c27470ebb9241969898e3458d9fcfed3ef24c31e8c3abe2dfa541ea5332e6c056ed8f0711b023f4c545f28cece63651227ecb00bbd9c7e1fa1fb307bc87ea5012dc47722a9032471470d82e321b5725a7074088e3ccbbf2ac94ec47e3527429b5a7a573b7bd6ba18c9dfcda52d28894d292fd160401f2cc5e0514d1f01b49bd512c7ed8945be840b5edcdd38fe8d4fc8d31ca12256160e8d4134fc6215baccf06f02bac979c84136f9dfa37a81ca6bc9b93dafd369fc688a0c60218475cd687d5fb35c6bf5e969c6e8e4c564764fd17b9db562493573e907d211ddef2ded4332b5b9754845925f525a49145e04373f39ab8e26ff525ca5ac08e7e5358c598b4c399bf7f4747d7e76737e46f5c0467787a9956fddcae563690e41af1926ac665604ce84600d07c5b03d058466322d6281b3db2f0e938e0c7aa2d0ab8c9e4fe16048ec51fbbf1477deacc8de18a98d4d6b5a171b9f1360735f03fd7d010981f2056d4b289eb228edc0f65d71d1be42fc8384233ee944ea2ff6d19760a347b8b6db7638ec1445bafa9ad1b43486b47ff6d846551c5dead0eec84baf4361ee8dc98b60654e02ac96094b10078f7cb1ba2e4bd306f740a37d4dbea8fc4058ee95822e85979fa6cdb24895eaa06dd174c5176457fceb9be8ceb7c6dee01d599aaf930f1c374a191a4059dbb48cfa948639f6c4770735500931db6c5d7597672b52bacf0c4a80a6cfca728d0a98f47617161586000cc86432bd0ce601fdf5f83fd953dc38d83460464afd5d2ec44bd9cbc649195c4c71732c06a5886a0fe2e772715d92547af49ea294c7500f1e5e030a8e35b45720d729487f218e9c2c5b8d2f9b0df9416df1d1985965d509247c8ff72aedcd67d958803c4a37230447fd44b4506273fa2f236b031a4656552d24aca9f97946e29237272b9cdd0f5cece3ca859f548eb4a35b996fa6f5b229872b87f718209a4a5b3a5922060c30a494a22e93ae52e473e8663924d77763f72c1f269ff4afdbf9c31d50b0ff7bd683fd92010aba122ad38aac797b51c3637ee942084e803e531e9836270a45541f2d9e24166ef8b735ebdcc827ba0285d6e1db05e4fa155367098458764abcb4f153d9175eee8b8692a1e4b0a32b9717f3906a173ed23cffbe32d87b4d9d457c52c827676c6c0cb82b057185eedb49d37f73efbb05f5d4f6fb6dff75efe43a4b8058a5edfbdddb0f55293030489499f89276954d1ad2de34b066c9bfc72d33e98854d86a7c7e1187031e088a169e1845aecbbb2a47b5f34225dc421b6658c52aa6a926fc024ee697106e7f282849522706832be42f78436143993d4e4e8a6fd77f6c6b52947a6185eef3cb7a241562f1feffdf33b3116a9f1a28d542b2c6bec88b133c819bbf6b2a26f8ee4970364c8da41707f0bcd1644320d0e2b94e35bf3a383a53966afa80a161ff4d81cb58b1dc416b80ec71158066114a570fffc37ff2da7d57d7178773dae7455d878f6eab7d4f697eb66d8d33ccd911d0d13d4cd6c093b96823e83a8fd6a4917baa2aa976757a49a8be80d00011bfabaef4219efacaabf71e19b32582826baffa8df4f0a94211a6e764049b8c473deaac251190aabf96e3ed30019e3ac3a778699030fb9217d792d380f89ceb44d2c9f0891eb6f78a50d293c7bc67a3d7d1a9095c0c984acc2ebe72533c9b3c6978b9a8a7b23136013c2a7c69bc3d3fbbdcf3294c7e722cfecc8e02e6873b7b10ab8c885ca5f39a0ee1f16e3225a0b74c9ceea3dd4764854cda08d5b6f46b6cffe9c9743c6801fd950129359a1fe365e76c55839e720d4f2c56caf4ac8470ad71dcfa04b01cc873b4cfd7e15c36ef856134b97ef20ad53e708741ecb26958b7f79514ed18ad835d8bde79cb95fa2788c1ab64a3736df96533acd9dccc03fccae92414ab046bd09f40f0bde7d31904ff622aa15ca13c69fb11d9bb70d904506d0aadb871c6d7c4099b994adb094611b86b2c828525db80e83d00265a9c4bd20ca153b6f9d0a107a6a563191106f3e6ca3c67bbfb48410aceb2c9534bf877b1da27c70048d4236907d919a1fb4fefa6415f369f3fd71dc39cc69c72560c76022ab200fd6ff5bf7999a798e59b1948fa01684f648be7aa40a6b2ffedbc9c216988b8b41b0280fd754be8249767ad3ce4581fc9f903ae2c4405588534b3693f34f631bd8d6f2c25614ec148e13cc91b067461ead92d04ea8707e1e2e8f99dda14f9c38d9f7474594a1cf3a75388746df5f7e569f1f2ecce24319ac8ac4ad3b5ec7b1e886298d3ff52d42707c7eb7838d56b0992504eb6ae8b4794132009ad7cfe16ffe10ea94f6f37928d339361e226ec69bb75ce7a5f40e4011b19f0c6a8292e0004fda6012e63e3ea9fcc3eabb3bc7888b234ac667e9098245a32aaed19178b29ad36d7a33465a331ccafcf9a8c2b8dac0442323ace7ffc7a2b39f6de97efcf261aac11f984309cf531c7b6254e1c6062b4a2fe7cc031cc0fb2b46ca1891a7065719059490a2e3f6aece850a5aa9f55401519dbfa5af5508510b8f7697aea2fe13090e79c848a3a087536728ef24ac0f1448bf91d1657ab9f4cd11a08c86e146daf6b6b0396c0443ab5110f6132e7c6ea137e20c38c396e10bc151346ab3482e563ff9220dcaf31c2a6f9da7dd220df26cc53fab1b5bd77913c1c2cd903b2f3fa4fa3546d66f7ef2407e441006c8a8bbbaad10153dfa57ca03029071f24ac30f476012f92931b997b195fa60b431eee4b232a1392b3af022a285dbe1062ec9dc27bbbb04df70000e75d7197fdb33ac476b0a021bc36a1a1e92d75ef35cd376694feba14396f1283621d644e0537b0db0b0c61861ec168e749cd7b7ee90a29a51cb91a23af8e154fc6b4d8fcbde27ed63233aef655435624c84065f6e4e1d161f86e81982d51adf016c463acc15313aab3d7efed09068289ac5045374fbefce8dc3a1e24d66d1441d1636cc1a460afbe177e807ebf88c1ac4295660688c77c5c5c60bedaefcc0f0b6fed5e8f4ea5efe22c1186d302c29d32ac472973eed1048484b57a424433fa6c3c2922a9fe7e82131b19f667744d15d81dffc81bd84db82f118e3a965567f8f5d03033a46b7d3346caccfbe21341838ddd477af81d64a1a4c18afbb489615acfe94cea5adda21338878db3d7070ce0f1d885676e9c568b602ae72964f128fc52d6221448b359c8ecb127af09511391426dbb6e8c5135d6ae482562feb9cf2029ec17bd2b31fd9d01dda34002bf7930870b2271fee4d8f4fe32796b3e6123c1e084977b170ed9c776a8c9c8fc04d07d4780bc8635b67a7e8952bc01c6690d5432eb2d26f2c02362322ea7f1cf110b0a04eb655fa21aa221069b4fdaba35d4169ff4a39fb0771ab2553bc952b75258c1557fccd196d9f48d3b79c135fe18fac94333b36a0da5579d17bc937aea95f92c45ca279f8a79be060a5562c3aa38c6fa772b649905e2ab888d11e97b6fe5dd4d536825960c0de58f572056eb2d5ba34ab163e83baa7187ff304b370611fbb3a28ba6319df332cf06569766f50398b21de281a03460cbf94a9a136f81770de06031bc61eedabcbb0edb0a41420125f334cef5adf19d1a27b4a0af94835a3f91d1d756b31339201dbd433d4684c67a693a5bdc4fa5b440edf83cd5fa9bbf07470dc6ebf3eb7933f61e5abe2bbbb859157b7c47ec79dfef591f7cb435b1f7b48afea14cace23b3a25e27559233dd8b5a3af620bf61fc26221345f4356b64542a0eb2b99ad3389ddc36e843a6d6811f2e0b6b8dcd5e4afe87524317061acd2f01e450fd8add48f5a756728ffd4944e3b917b661b1b99e44580aed8c803f154c32d0036bffd9f70361160725dbfad5646c89f3982841bc199a2ee8d33a12e8091029703ca151fe819f1472bd5aa5087f2f92ef8b58cba3a794f0344ba301eefd873c4abcb98f5d2878b059513ee462e94e12cd6d2892f1218614622ff02e31be230ae7323555ba2116c81d2290704c1e274cb78e1813292c63103ea401b48ae93231c37c7e94b8b8b53415c2012c4a960c8fe683edcfde3eb0a6113fcffa71b41968c78d0b6cb5151001a1587e6fbda5e768c78a692c6ed8c43dde3d96807ce11c0111ade6f9f885761ff9fbca66e6ded3ccc5436ecb0cb2c1a31fb8a04bfa33a26eb49c76fc98aac74ebbf95071754564bdbebe6017310338092c94449c8742dc79ec63dc78ac3b3ec4f0604936212c4345bb545d7d396d9119039072de055580b027fe0870385012b2fe949f9e2e3fe2df3eb033c38665bac40296d351ae708dea4219d4d9b7799281e6f4a7b03969412f7b293b18e62647e3930ee942bc671c6b12cf8d7852b934cb84abba15f968c9286fba2c5cf6dfddb7ecca1734f01c27ae6cf4d340e19ee0d7bc76ce47b39b185df00384855153c5a332db02fe441b26d025fae80f2ff490dba492abb5cc25e92d6bf4502a45a70b35b125588d940dfd26f7cb115f890c3877345cda494fc96c04a81983f7528ecd08185b8cf290b2da7da49638df1c400ee4bd4fdfd00eca96e7d3f21853d83d27e410232b750c9898d4bf15d5b253624469d027e20aeb643912f87a537503c68a6a084fbdca319ef0d3a64badc883ad1a0c48c163a1987c753257fa66be3ad69095aba57fbc1308c98e1f5df39782680f24791d3cd949f765a859c36da4158edc184711d74470d12eb4ee1d45a6ff2e7f0979e11d434835f1010f456f108bd43c2ee8672366041a9883606a11dc61a0220eb5fc620985b3afa852a0d6adfd80f34c8c0908112b9757dabc303527a04e1bd733ea03dc64b9df0aab89d2a3c52bfcb6cee2b5a02db9bd3438d9f8335fa46ae4ce4436ad2aa3de93970fb2caed3d14c324891a617da6d0d86c7676374b770505ac302fd1901e43420c809945896c873c09b5bb6f43ef497e9f98f73a936dff371f1aa9c15495bfda3b0e562b8a677abecd74a7318f850942611caa66bfd29dde83452790f2abedace64ecb5fd07efe8d547b7c781f02d1ffc540dd47b9f850713e903f1e7b54edaeff3c73eebadf8260181dbba2505b21e0f1a6e809ab212fbea3c94e98d8e35b139d4feed9b77b093e71969a2d61c1b11a9152fce2bc7b9bffbc7e6e2f8c1cded37950dfbf0f300ede9ef4565aef82e6c4c61f030a9a2266aa9629446c7b5991ac3eeaf31b52fa4cd22bece4c140cb22d453774f05a62a73d45f6ce8ba96f629d85fcf5801ef7d4b4c3080e4cb07edd031e3697bb429f5d5fa71560b748f6696b624365ae5bb821a9caf5e86ae20176c18857bf6f4efb07fd4601a3f89c3fa908f1c3552ff652922582c2b798e2051f43bf15eee5b8d865116418ffe81d7ecf5aef7c1c0b0a85b437b4459fdac54a5d69bee0394b774e2b77cc0dafa9a48f6398fee17c154ddb5ad4dfc9903a2a3a35461b8547b56449fb4e552e52d93b09e774e96ea8f733269f118754837ebf431b082f97a4e9cbfff1ec9048da25901e592160980776fcae68b9c113966844635f8ea71715a940cf9385c50757ac5787e49d30451c6ce04e87a47e49e6fd054a63d364a20919b0f8508e5a3386903112307a58e59f3bb4af7bf0aa75e63e858abfc52055c5e7f539b44c661b3411609d58c4447b4fb4d01592ca020adff514057d0db6c73d24ef03327d17a860c3639c05225a4a574da6c8879b1eeaeb260d32d72788304b05a2c62e0c7119fca55f27d522b55863a1fe8d48919f8ee58c9944b31be175bce99474bf4aab57582f1203132b03fd7901f219f1729cba8171b741a33b8a163cb7bcc80b2894930c98f36f695860290563cc90b1f044af2e0f78e0491eaedcdb33c71b545f3d2839939fec0f603c10ad9d868620c94fb4d477790e657f5a624c52a80050d0fef5df104533371c2348df517a470a0c6e78c974b67fd598949c81a56cd0834944556764480cf6cb093c85338d2ebb8bf3355f40e21f2944932bbdb5ad09f453e5ffadb8be2ec163342297ca157b0688bf4f896c5bdfca8b458a2cbdf8102d0e65053d688c4abd4d9b3a238a7e88cd31ce932e06ea351ffa89676d8387225213ee66ddfcf2f4df32c11c369ded6ec98c4421e5a63d5e2c6782a083ff514cda5bb26dd59b32058f104dd34a6f6d129c11e3a854a1310004053140963c853c0a6805a164cf443127ac326bbe43238e54d14032417b7594d4ab3f433032f94ff7e19bccf860dd023a8deb94872413a5850bdf57b1d3543637064b52862dc4c55d8727369c2135df9697d80f8ce23a990395464e500fba081f438778c752f7e0b0d07ab4607ebdfdc2017cc7ebe0cdf3a079904dbddd27859bef4f5ab2992ad55acf27403f9c226b14000af970b8d67ba8464c54470d5502de88f84e0af3d3348d3b481f75ee8a01ea75082ba910ba0ab7bed4c14feab97033bff8270d7f5a286fce30fada23da9e004acf0d1094bd85eb2d3c378b18f0bdf96e6fdfd0c73d5dbe27f6401e276f99a0d247edce8225028b8b67893775f430cd11d54aed13514c41ecfeccacaf7196285b2d9da0f9c0da2e56d7012da39958d5616652afd8c18185118298df9f35099f6060bb8d6cd8d1462ceba20b98541f1024a1dfbaca9a4278fd56b7b3e9c61dafb8f1047e2f27a141959d1a0f6e53dffa8cac8e9f64b12bba315acdb1fcf8a1a22feffa3fcf863cf9476c6d54fc7f527c83a327fbc5da4f383040e44baada6259d25763792a4032a98b79e4acd6a1ed08f55b2d8e6d8dbec505bc03a8bafee6659ec534716a9c8dc4a5694056ba980012faffade4bc08a2a85f19deb2129a22c310f828ebd9b8eee35524d4d259804252646935ce6e7dc0258f4fa418a543825cc086e1be69ddb1fbc2b6c2426f8bab8169334bb414d4e6df57e83f871e68e7e807a982e93310983626ad0d866cd00c7f2183c48ee206e3982a5d35e1c1d7c184ca5147fd5401385b4e748b9bcc0459ae3063317bcdccc3a441340dc182e804ada77f99229ef5c8b2ed2c8440e0bae5b00243372af7b5281b335b2d4d09c254e32f0e4d1512946c27e75f305953de6db711482e8f47e18c03e6272b0fa376b3f6f87fc216838e8304eb3f7b8a679b86cec63963c916b66b37fc86d71f55bec1b97a6f7b1da406e67107c31fe3a6ab5adee16debb4d9d6729d49fa29a7944dc1dc4887e69e334c93de5c09b0b571f68003f1af05d6f6568846b040fb206759c5f13b34bb93b8d39409b945be7e812829899b1cc628bf579ce86b615b4184865612ef05c2c5915c7af6c64c21e16da54b734e999627673624ba3a93c41b5239a6dfae89fb73f85f85e09c40617e8cc080fa797d08124bbdf947619a3ca5f762a4a1968984008bac06435e39b980680e5ff60345a02cc66f0e13566d13e1aa2f815ee9bbbdba2d79565baf8915ca0167c8e266077e557fbfad60caad00040ad7b91583ade01f6b42cdfd2f010121e30d383cb49ae707b52a00b8168354f86acb099db4b5740bba3d3841214dd7eb78c23fcee6a5025d0759aa0208932d2d2a75106689009344ef5d03693000d88927034070c8d78f5d77538cea539d6cc70ea5160f4d362a6fd738c77eec8fa7d076fc9b6f9197b86ef98a6d86b298ffcf3db86d8cc01fa73dde6c103eaf18471ab31615f9d879866266ab808d52c7d893ba0aca1be375aa2479186a0714df84ea727d537beb4994e2e50130224426f2485d682a92127bad522df6c392348033076de514621ce509f8a6f88b00e1275d5e585fd4555e29271071d6aaea1bb2cdaae9d97986db82b29c6715a8dfe843c0c1cf4ae40c57d0d78bd822811801f203b9598d94413be0b4cbe0b8c833a74c084b1ee66bb6258ef493ba4a096f2d1f758d967318b0a428c3b8b781470c76fd970118c02aec90040d75725ea3042e08de9a77b9b1716a970905c4b50cb63402533f4357c3a697d7a24c578c096fc67bf144436c57e8f68b88826bbbf3f4784de0731c26cf64828cb9557c2e7f1baf2631c4fd848e9ac4ceeef6109f50528ecbc7da35341aae338055e62663ce0a3c43d9662d6ca7f58590b8ef8b19343770c7fc2820470e3b969e90e8e4adae6070f392d5d6472afad455b69300c70e5cb37f7e9e35e6de31532e660c67ffe67f3c4fa8279b15c323b89038b8865eb64f07b8001b75b490a8cf743b04370b6098b0ae9dd26f84e9b96751eb4bf88469d12762f268df11012950d4a2a9f9bdb48a6397e7491c22b64c3fe29e01d0a098df92f15221f73df80d2650621a36bcae34ac73a85dc8a146a2e0320a0a84f164756e352eb770ddb438d358bc85b431ff846fcfd614f62caeb6e8e5c7c33931aabd6cc9681012afc096efead404b58a4e15e3540914332c8a0ccd0d63233cb07a666b1027a0d0f4c7e6b70410486d223758b4ac006668cd4bce09d29aae796bd49559fe86daea9c7801be3a030a17c8ae4873f98271cb51ec2652effbc86bf15ddd44835ba01fe3fd7d6df43f5ac2dd2d3c56c9ac4445e0fd56e43af74714ef4d7377549cfc65f7fadc6276c1d8db5e7f9426c4c2c97bc6ff76a90940965305c6cec17bc25b78d3ccd02e1e0583ab7460b7e289449a330e2586c837c1cb01c37052a94b4f71323aa5e285e1497bdde7fb5faf8894719e3eff4d8a9d58ae0ca10228334edd17193881879cb0d3416a9158d148af2da3c055b94bd1106f88f745dfbeb6e4fd634102ff81111d255b55bce3cdc0c5e542351a0b4dfeced9a70b2baef155afee71894f704f", "spend_index": [ 0, 1, 2256832467, 4294967295 ], "result": [ "7ece1b4eb1686e819785ed780e21833c9144696c76978bbbf7b91542482d7dca", "907562fe9c4028db2a209fed33d17b9db6b513c617b65e08fabd61b725d10035", "7f66349b5ae68c930d9aee9a7a73a57ee7a793d2ec17af127e643a5969bb1a44", "0e5fe7af882abc6dc8cdcab52a6f06d7c8b0a2c6979a8b0925e05cc097a1bb39" ] }, { "desc": { "Inputs": 5, "Outputs": 6, "Witness": true, "Version": -1121365080, "scriptSigs": false }, "hex_tx": "a85329bd000105bd273b6f000000000000000000000000000000000000000000000000000000004aaeec4800d1105217c17fc93a0000000000000000000000000000000000000000000000000000000071a3b5b9005fc09db682cda04700000000000000000000000000000000000000000000000000000000ac46a23d00ed774f8f67a4ea170000000000000000000000000000000000000000000000000000000048bf169e002d4145bdd05a4c7d0000000000000000000000000000000000000000000000000000000076ee89f000c4298670060a0dcb4af14fed1dc827d988fe2ec385251a53bb551ebfbe72c53fdf08058ec3e6d6161e5e2a7423a16062f2e4639808a785c3d59ee3f3a69d02007db9101ded18f687f0d10420caeb2400fb79a78543a76a171a99b75d3b19fd523e9672208555a22c3cb619751c1aa40aec38c21a2ddc3dc133200e07446bff0e806e5da2bc891065648818eee19c2edc57bfb62a33f8bf46f347fa8eb3e72b25a36cc011f6aac189af5ab9a17b8b8b57299dc086d519b000eebe986e29d29f236ebd64da694eb7d2d02942c28425c9faa46941d271e4ce73905ca06c615dc8bb355541e131c80142beb9629e3d2eb8b9c61891aea29b67d6b0d2e01f8b1a9b22bc72335284ec3e93fb919d62ad743950f877598fb2f03f80e45e3bd24405afad57e82cc4f71d1936c8f1ac3ebd91f8641d7bd90caa0919a5948d59b7c7fc81ee5c3e38c3daaf1cc6288076be779b0a72a902931e253d81854de11dffddace28c8f88ca85be9436dd5037e4bdb1eb710ae59b2053530190bf066af04094730472f9125faa096e41c77658f54aa4d7d36711602aec189089d25cf39315f5df4cf8d11e964497d1136b85eb3e8324a12fc899222204b2df1229746ec2c9e5d411a11550be538ce5af13a6c176b5504f2cd708ccd8424069470b1c43b15ba1e8bc1503d01aa45d79c6e54c408459cd922d812e6f4a156133c867bbd2ee85ad8360c604961c8a1051674292d02ec48c0c497e33f772c022c139cde50c750cf84311fd8611eea3cdfdea8b16b2d0e9ef1ca1d03abf9ccba85299fd6f115af72bdd0c7da14647d033bfc8402030cd170acb8c90dbf54b4c530455f4365f39b85070370d0ff4e938bd356bfdc423eae36ff0c02f64fe11f7c610f2ce8f1d4a2b45aed32cc80279c8367658b0d003f0d7a6b3a0aba3bd18eb27c43a5b0170bb5c8f12316b2959ffeb87ef520c3aae27c2356d0cca3e5c12be0146c8399ab410d839f61c82382c3fa8fca2941024e4b6f3f84d72dc3986095af476021c8be1a7e42573f00941c849cf62782c0ff36b7a7b5497bca47b9b1b9a46b22827eb3fc53496c409907026fa942f7576ef948db31d22fdaf871a214166717c0109769529c55ec3260299a4f240c20874e3216cfc7b6557ef64fe3a74032a07b9971fe4f927e4e95a549df4e0a3494d301c637fb6f4d21ce6e36dc8ba40f4e2272443dc713df51e35ef69335cef0c382261a2417226223d8e0e085e457ea970bfde510ff6a076cbadf31042f9cc16d60d88f952f3518cde04c1863d45a2e1b44a2c230077ea1c62bd56bd2cb46fcf37ac22538a60ca77637816c2553977b8a8e55ba3bda6076698056fe2be0314a0eec5917ac78d6399274e2907946445ae853101569d395f6e8d3d5816b6aaa3328aed955d8627684415c1bcd284bc32a078603c594a06b5ecc214488486e77c0950e2355b28f99d442d12b41fc583c1036e254816b9bbc15e5498121222c81859344c7746628c4df946424cba87e2d1a97dcc8ee7e64394ed194df3b5e78c3e05587720c503bcce1c40490dd154835f1f5ae98306a71822f0f3a16a1fdc8366a83fcc24de976cc600a5b050152ecfa9fdf9702945fa33d1c8d0e51011da4ed316a20ed46d85d63af623621f490dd7df5510bd7b5515989753025fe6e26074d7c254a9ae38ddd6d91210d6eeb7696ce5b5a9264ffca2954a26fd6c3d7391ce9402d755d45409eb31f6fa3c5be14f30c5e3586f5354abc245eca1f18bf770260063e0ad116f667903fd2b019797c0c6f8da47f4a7204b1019c0c5449520f3b152675141af11985746f9c26f4738c4577d4f833efebc11071c7dccc13622d55f692bfe3f56fdf1c6b54ca598e7317eb35d14d1230f93a8a6de2bfecb18fec35fc61af109fee8e124cf67551951415e71cbf78628719657c3b180ea821e21278f4ab030e31f5713f4264032ad81f8f2e9ac1dc2581bc24ccf34baf127ca8d636032f2af82434d9a76144aa7aeb4d0e62bba3bb6564b1070676be310fbc96f33c7cfc749318d6ac90f64196ff89dfa08c4363a5f1c211ed36038cbf5df1aac3647696567bdbde61513be983a9639f5fb2a6084d0b0e9657b0b0b7d735ebe50c5a5e7fa0eceb8be0748d6f7ff257441a417ecfd3c525754728c87b228a7771ef0c11e200738121786b49d11994ed58aaf276db014c45f963cfd3d0137006350bbe52ee7816c885dc9a4b560a84b12ff8f010b0296641da8fcffee360edfd8a245782887ee3cb369c99a1693e919a9e1ad0519f5974f6fec0355f3e9f3669acda3d9b37d0eab9c7823e02798fa8aa433194f4812bc328f37c79ad3d5d9fc225571d74006c958b92d91fd026ca3fdf7ab8e22869f17041349a9463cec66691cc09f100e9b7064425b184977861499bfa404f773f798aa475653754fbd71f004f2aa98fefeb9f1285629dc00c00ec1350038630fa0b964f9da49fb6c603f161f344b1ad2f321a6743de17b5b98d6f7fc80933836bf4f569aa1d7bfb8c493c289208a8dce556d3b6f2a64ac44aba3e47ba4d23f588feddb456b6e1389b35cbe4021f1ad4f240f8ae77c6e8c1567ddcd995ea4b62a3fc7bcfbe1c8bc8b6676ea89690db799bb9762d242d67c4d5a8f98870c8ae683dffcde119a364c20cdcd0a1b055d8ed43cb127d43e62b1871fa8bc87b308ff5419d60b6c7b80307d11e93f5719b384a97842a7a1543a62923112239d05e797b155777148b86ee2ca55515d238fb0b38d61f76f00042b21f785e70e481945235ea7714f267f281f7dbf86af9c49e2afd833c2b333d889234a81d7f8bdb5aec5f45b3b2d1933785dda2877d98bb8e7e2b79b0468cdd51c93601fe5389b4ff66cec3fdee8a970c57d4fb5d43d56dba3e51df41586258cf4de53f5b333658f1dd9b3c4bb5e881f958f5892ceb9baacfdcd74a8f00b302b438692c1e5bcfde50168dfc8eccbba89d7f930ad3022fea15249cfd94dfae54aebfd3c14a6cbefcbcdad6389b1b935e406140ce98b59ec617ed2ab62d70d085cac1a703f85af5afa9599a0591002f3a2a6bda8d991111526dbb8bd1115fdb155f58927c74f936c0bd2824817ce718e7bb12b1b9ada1f8e150f05f144899b81a96cea71527e5ff5a71fca4bd4edfc50aaa74846f0970597aae8388bdaced656fe24840d4f8c29624d33b3622d00546a1d76a2b533a94b5bf8455d7fc24d5f22329486125a1877ac4538282da12c6b667ec1b46ef72f365e715fe17fd295c707144a33a1db8ec7ec4fc80985685a31b2cc785b1bd5fb15d4254dd3a70aaabea50b604e39d7c4429707d89de53da0026877b675a09d34d23f52b0feb8f3bf27eaf2dd381fd17f9cb0b984fbcd63aa1cd073c6babf589ba34afeb49b456fd741e9d6d91e9a8c1e4488fba3e57cf23ea9451c2300b1fbf0652f912fe51148b9b2cc54b16c454b555acc104bf90f6ca8e4e77575dda189b08864ae1dc9405d08c6e20d6d609cc315a27f0dea43df7a3fc63d5b28a43cea0be0cf41dbe364f398a6720f61f6f5a4befbe2198b5f7a634c8c8d1942e714014c2b80a46095fa5ff5de0eccc957b4b85566de6cd59505f9a69d9eedcd410d263e243165d2c8a01c9fac4f0e86403bbdf7e4120472aefa3d1c62035c7e270d49dbd0f51c49c4f16c4622671831a9f96911ab7a70619b49b65e50abb0f9a40dc88aea860b9340bad394ee58030e3a58a17a82210425f8a08a33e9ef0e0547f4980258e1633c35c2d2ac3790825bc9fd7a5d40dbedd1d5b1bf00e5c368e6972e3ac8ef7f5ed5b7a3c27595b3a296d73b204352613bbda155234471bacfbb6bdb7d3d986d871e1bf701b84394b9ab1f9646c7370e1b0e6b0fa26c9c1539f617f7325df6c9d6a7872cbd67447cb8cf73a0adf3997e83d4373ed3525f938d1424113d94d4eea2432f76ef9ed805093cf57dde55ffea902daa4690bc7b9c3728829fac59b018c17d23b2bdca64fbcff5b951a796e504a32c7ba8776ed180046874e89d800bc2408114e82007a7190f8f937a9a8669dce413fa8910a9a7325487b2d3b6cf87197141459bbe38e05959c24ab74b9cd3fe3ad2e84b730fd80328651bc1002d586ecc", "spend_index": [ 0, 1, 1966205163, 4294967295 ], "result": [ "e621fea8972801c609584be59f2847a8ec50a9faf91c0e17ec32ca8e8e165ae6", "9d938fcf5a87e0c748031ae2b11ce67eb76512c5b7f627a7be40e3ba0c4b656f", "365258ed1ed296bd7011d1f5fddc452749352df21ee50d72d1e02cd3213711ea", "856fb3d89e5d18d4e4a12dbeea1366026a5d1a155ced01d743048e78edfa817b" ] }, { "desc": { "Inputs": 3, "Outputs": 2, "Witness": true, "Version": 14177900, "scriptSigs": true }, "hex_tx": "6c56d800000103dc1d957b000000000000000000000000000000000000000000000000000000002769a2eefda7014fac369f73dd8922f35850393dabdfa701f6d3ce48973cb051d46b59b775410ba0e80285f48730e8178e4d2417cd58a3f779e1b34eaa1eee4adfe2264abab895637ac5d169cb043c5ed47e43cf2cb8b9772c4acadcf2775faf03e84156a2a6eb0cebad5d8671bff45dd7c96f8cdc01e6404ef78bd453fde86cd46a71138049df57b55894fb927af05a51924a05e9be935561d72141293a1ebcacec08c3a1034f51395599f968d2fe34ce76916977a5e27e33b9005174ca5e39f5801ebe0fa0b0c4ff303803f9fe6e9cfcecdaad5d92f51a1bfca0ba679f5a10a1c33bde58eaaf5c920b31799818b15e0212bf3c8882773760155d233e3ed093b7c9cd1fb2400f9e3ad443daf835c587d2ecfd4280f15790d4aa51be2a98826e630cffd33873c46df52cb50a8b5e5fdf791c3a6bc4fbaa10e6196df4252236dde90c03d42eb98d1d86cd752f9ddb4e5b99effc659e8a5c2ef2120eaf532ac03e35bbce791615352ae6756cbb5679ae748421daf6bc1a55df02672928b903cebf860efe165beabaa078bfac2625c89190b987c36bd56dc0d04eab01663212f0e89143eaeb395384e4fce5684c4a36c1460e1d43d00c13000000000000000000000000000000000000000000000000000000009e9e7da90057f6aa00d9b8513e00000000000000000000000000000000000000000000000000000000324e2466fde701347b2a1a5e83b3499c3c233a256102da9017b348266a0fd7b0f308e53c4f155cde9d5c006a1249f38fe70c6c8df6f47d2258ee470057b70ae70da5c9d10be083d6e6dac732254b2076ac3f64caea7365c6761d74079b7ca5eadee66c324f36b06c3724e2f6b65f204c9c1a637e7199ddff4e4a916a607a82d529abe5fe33e2eda3bf6dcf4af60c1e497813788d2493da4730431c91d02c03c98548b89d23998f4f6e129bead4635e5d5c4d68666965ac496071f7922bf2e157f9b3dfdcb276774d7a08f1e8f5ff0e282e123168e16833d1cbe6c1774cdf531872405f2ae69a07ea44a83e100771baa28e304b03eb79fae3767c4c4f6b6f3ead4c05daa4e849ccd898b6c822efd7dd6a031f213ce4e0da322cabb60d369f0ea79465efb495434a7e69705541e0b02080e7742957cd6c5bbd986380fbfb3a74772ae248d00364354366176fbae18809179911a47504a8711ed0e2a1a4a5a77164d1674bfdca4d3af69eb13246aa9d89ef859619fa4cd8f513c79346ab4cef2e6ff5f65d302ad3535f58b8e0caefa24914a62deb6839013e07e09a42ebe9f26661480958b8cd82b8c385adc240f47140ba560d5c93b06a1e4d79974ab5847098f7ad8b9c8cbdaa6edc0a639963d09b78dba016a2ff41dc2728e55d376cfb197ca09f58136978a3cb149d796b915e258efada5d02b89df0f0d827d82bc89af85ea26bf30089498e1636b711f9e6f9204ad123de8111ebcc9c7160bad2249ea106120844bd64d419581515fa0d5492bd4542f26a16151e456253e93d0d0d464de3ff9cd3b84f571805b43f88c3f27eca3abce06d675fdc9f505a83cfe496a13dc668756308c8366fbca951072cbec7140c8e92b687f10cbe35677e10fea684f45419b925e135624a072598048e81d9381323783ca9211594eb314f657a82f22c4bfd4af426ff1ddc32b9eb736aff76a1fb488376fa6fa2376682192a8d93715ec7db49b44b1a4d4cc8b0e62a6720c8ecb7adbd65c6be0dd54f1c9e5cbf9dd39c98376597eef0f94e6a207507148e24df6657cb3ec7ba43f0ed91523de1e9f0c8799e709a9ec8730bfb4352c1a21a34417c3a58f74f665525259d6285b8b0648c20683ebedf4f9e8fb912eab253a001bb2e28cc79daa210d43f36309550e5244ea9af5aa62928666edf42074f7147eb26605470f4c4916467128d65dadfd63a48b864893af9b3d819ec6fae68208a836b5e8a77a81fa08db60d7f6e9775d942d67953df77e48cb74914b61b43016bb0f54afbd1f98472050482475cb23443e6751d82a0760a51f91b8a41a854a8ecd0b7c1a839ef784f0e7287e2e8cc03324cd1699e7318867330d59461888289d1b8fefad56be6f6f129270c000032ed7a0cd8ee10e50e0fd9e7056941d644d25a7daef27eebafb24881e114916c7c545ad6d16f74e653069cabdcc655ffee0f60a1406c813b4c288f793a48d86f6690696be47c9a544e87d1655bc0e9e8048eddb90217fe9755fbd029c5b1d08b5dc767a08c4428a9d8eeff0d35864d51a4ad8dfdc776899f4a563deb0a24df87bea5ae0799cdb9eeb0972641b99b65643512a60dec2a0cac676d4c0bdae3129443dfcb744efe650fe82b6c16b60a55c69a52d4e5ab6c156e30fb2d8f8c2b680848a217d6b8e85129cc565930d4b913fb2376f23f1c8043ec7cc0ad45f2a99bef965e948c350c94726e3255fa6b8035c6eebce7fec5fa54899692ba1f98459e0b1dbe355260e2315f024e87e993d265521d2b6b49e642a1488a6ab201956da05e6c0e590a60210004fd5f018dd55831ee67bdd28c30054e1ef609b2ee88897d0c814aa1898978a299315c5f3509a46aa09735ca318dfecb9be3bf8801aae72d281aec64ef2fc210df7ad3b8e00bf494d462c64ff4ff166c4404d4cf1e24fda5149486f1ca73783bf800bbcb8b8c1df06642e7a89b6e5dfcce49a2591f971f9db11fd5628afdb22e12228ad75d053d7ddb6487f28a537d245cc3265e3f067dce2fc0d07a4cb9650b066f895555909cb9ce9569a516d9dfe3d1359f6e4295d2582572968898b5cab0363cca1dc9cb85bad37c9269cf75e0f0fa10b4dbc18ae2a62e9bfdbe441da9a2959730b17011ead2d669d5f24389a66bccad6dc8df0e2e7f5d67661c394c221faa1073f6f3a05bf1e6327402ddf6b815fded475f5a62406ca52548be25fdf2b894718ab237fd0768f9d56f31e2e3c29474291c68b5b709a0cad5ea97266243c0870487ee79f967061610a9c5c5ff8595c948937f17e2613e415c659f20df446d39a685e87c36075726b1f9699cba8bae12f4ef28e15626aa47faaa4f02216e077f3952ed1ce5ea3df1dad624cf33ca7211a706b245ead08f50557959cbb61ff1dfd6c15fb5a3ec1ed1acf3698c7fd3c80e9f1ef3f2da656546733b800c1c334c0096f200e6aab1dd0aad63f5c56ef353e178214f589e1d7e96746eb7305bf6b819930329ddcc1878b0f192fffa4d8aa65419a01b0ab4b3e4093c5a693a3ffa96be3c51a7a56ad66be6b3cc6921f6b1d82884caad4e258b68623bcd0b59cd8b42bf7ee95b5a300ae9b18cfa8885a4364d93e48c0058b740ee84eecf2bf0dbc532cc9b93dcccd1661721eccbdbfd0b01bc0f3b0391db6eb8e92a3f67969b1ba815b8285c6248f8979e1fe763055991b306f1770fb19944593512170e6497f14b495a06f79fbb64e180d7a44f42bbdc94a38502c1dc1beadf0d869550ffe3967772373c4fabd8c39a812c514f46ba807498a035eb640b9ac62d168ce79e91117e9edfd3c9856497310d7143435d9beab5384394846f0851dfc6cf850b55f3ca527a618115e858bbeb70c935884b4e16a613ac188e68522662f231b5d41cabfe1fcea1cc6232671e3bfc0d732aea58450c1f8c702a76c76a8affc45eaa7e1221601102a84bdab425535cf2cbcbead034c8f1b2bcbc42461ebdc5a8f6128f19e965f99dd4ee00e2525f7466a920b68e33f499cf5f05d931fcc8d6f5957ff624f2296986ab5f6a01ee80b9bb2f4d657204c1aaf819e469b54e6850da7d7508ceb4091b9ddbd86667d6040e3c38d8cdbfcd826b9a6c8937d7b3349d56e4f122ee5c18600b69be4cbf752a737ee327adaa1192657108c94d61911e75ed95c6c449b002013ad4be652e9c824155424ccc4a5443472e5ca195c1907a2555ef453eacd0", "spend_index": [ 0, 1, 991402756, 4294967295 ], "result": [ "69503af7f18282622a773f8aac4289b12d802e301d45b969f6bac81f9a34868f", "c303e94cd581b06bcd2aa205d10aec0b3ddb9977e8251fce846bf4d3158fb071", "6f7c04b8b44c20c64453256d6e4ce5ea8d888b4b8a74950fd9f1777d0f54c557", "b82f362d8be5f7c0dbbabbd9b0f9a908e1d168416c0fa6240ccf6a78f5225100" ] }, { "desc": { "Inputs": 8, "Outputs": 10, "Witness": true, "Version": -1517733652, "scriptSigs": false }, "hex_tx": "ec3889a5000108c96eb4cf000000000000000000000000000000000000000000000000000000008f75b167007da378e1c0a6d665000000000000000000000000000000000000000000000000000000000a3b015b00f2f3cad92e460fcb000000000000000000000000000000000000000000000000000000002257749400ade11bf4bbb59f8b00000000000000000000000000000000000000000000000000000000ec109ab9004d2aa4f869f1a73a0000000000000000000000000000000000000000000000000000000090aed3c70034e8ed89e84edf2d0000000000000000000000000000000000000000000000000000000092ddffd600410e2fbabd3f807b00000000000000000000000000000000000000000000000000000000cb2061da00c101e4a981daff2a00000000000000000000000000000000000000000000000000000000b65f3cde003bd5190b0a187c93202477d158c855b325eb1c284a4354dc20059ca77ddac89a181465f083d0f075c80e7fb5c34055a1fa99623fa3dc7d68ae6a0c6adb3d4a6269673d1caa94130c5ce080928d53d3fa72335966f1c1b32d8fc016ac03f2575507683f73f134c73be43df03127b45b0fdd99528d5bedf4bb0a84fae0e86f6eaf5f7767045ab9b82e42369c13b76b1d12301d7294e7aaf9d4fae27627a2f108579807696fd7fe7228eab650492aa342463e17830a6e04319b9e585b3070333c04f03e63e6dc62824fdfb25e6cd0cd831242321ff438d8cd5029f676e6a147c8db3f953415d38451a3bc393fecf61d4218ef34fd80ef6a16e9a36a247b883842104e19ebcec7499fe1f35fbf7103c93c9e4de19adfb26aae69c1e539e11a8c66c5da857a59dc82596ed0725cbb61b3fb56ff857c084c703f0d7398016b2d7fca28c9bedfda40133501a2f45c52516ca8681026e5afd37246c416b79d087661a36f25c415f9add15e71b4e7018cc58ffa96134e6c7a5240e30181126d05d77d83ebaa866fcf371deb50bbcc4acc682226a0ee2e100ceda76431fac7654735a6ebf13f1ebcb0328ecdafa1e4780b35fd5bc805f320f9681cb70ed13395ac10cffbe2b2408fb4b8002df23ec9cf7ef59c2a7cb708f06e18114135a03f0fd4b3476a71d973fce042616b188b2c742a5d169752d9ef4ad5ba55453e209b994916972557f46ac3922d8503dc6f86f4ed7a39317d8f7c079ea709cfe69178deef35a12c9a24bf0b72fb3740897a47786fdb71c42893ffa002c70276ddadfad9a9551485ee24d1e3b323ba271d5a288ad575e691660a330f6fb0d18165094105d9bdf18d4c5b783668a97804f7002f3c75df677474908bff3743cf90aaa04d47ecc499553ec8e0d516ea52b011489d4ff3187e4ee821b1dfac82e61b1517dde3a757adb067243ce34bd3ade7ce1cf567000e8e049bb887f669b20dbc502ea74caf0212e8780a70e75f35b298c5e43fbe3340471d9678f76cba3cac3687f24c046f81ee9276160383fc4490044e318a309a6f4cd2cc8e32c56c2def96341a22e3d999ecda67de1e7627b98baab7cf5ff7731a55297709492626d449ea1c5e95a51edf210c27b7d8bda02a93b28cc63c9ef122a50c1727f1c7c25039667198a7b9b3c004131d4346b5013f2f7af9505869bb921a2aee2bc8a19961efc91d923183bb59b8047af9be7a7c026c58438aa1fd790df2b14e5dff7c4d20e22b19a4a2ba0df2728694080d0cb5fb8250083aa44c7952d3a048e127cdc34f0d37c8ccf2726a8eeab88cde748be9182c992ab6945a6b14f72cb792a384e3faad4e2fb29c1f1a3e64d5751b96a333c6a44051559bdda15058bb1ebbf0b0be6701f1908915d8e3b7fcd93479506292ef83a1f7a7a2b88a90ebcdaac824ff72688185460901e6754827d853a9fca376ca80a2a17c7425066ae25edd6e45ce5dd75aef01a613f65b11807caa7149c878cca3710401784dd20f21acff288e24e9e5bf00e22fc4446f83581896e6fd42e520b6939f7785f990093e361be1d5579d30311f581fe9e63e5fe15420b5503fe446a33a48dfa950de1fa7998a20bfc5154e088ae7553fb8dc72c30824f8a6eb895d6fdd244fd0a148ac6da438160b89d2ed458c7979a40ce4adca8caea7ba397ce51769341724211e0b3f193c6d34fadcb03e3c555fe47a4e65d69cfbfb24be6196db8428872a1e297e587edd10eaa379505bbaa85eb95e661cd4e864a15b800a09063219751c0d50b3bf615a2e630cc88297794d575db5769bc69cf903d02bdb587fa305f4e1aad02eec007f2eeac5bfbeb6f55c4321b759c4c4194aa7f82caf216e4c681fd1ec8baa441d47c62ea6ce78a762e780d5fae4e16eb20ba217beb8cf094332584cf44e3156d3aace6471fa7e34a047764ba02471cfc2061165b6d28cb40ba8a2a59ae4ab1b2bdef20f55c943650718e714ccdce2b2848a97615aac28bcaeb2372427154657f9fd265d2990a728bd7858e82c60e7f19f40acbd58b06b6ee64ec6a1a2f4c3ce530d28544cb8c8163b6f0f7b4f6faf95aa69f0a7e23dc852003c0ae9af77fdf579fb796e6671b10638af2ce27b62a3af5236cf0f35d7f2e2f77243e1c18f40f1a9bfd0d92bab26b8295a6f8d1eab9182c46f520a741d71e7c0d4022997d8c009ebfe59dbcfc7456953e4d6da1b58d0cb43d591f26d976b8acf29541fd5b793d3d3611be820e41258ca09ac4301a8b10f75fec6a3eebdf94215f5fcb1fd5a8ad268441ebd084f6fbb75b6c0f35f56549a2f8b2131858c22651e19f555bbe6b62e81128984541dd1c4790968b51e6f6f8b4058b310e3524f0b843c9477e180e9586d67800e7f9547c8fa9d75bb7125786a629794644dab2b4d697f173bafea4e2fb9379815d9630d881883ade829f1b43d7713cb4f556ea20a27e22ef67c8757f6674228470177e9ef7ca3bef311c2c62c9e1c72807863f6f0bd0d027667a614b2b882db870cc61bedfc7392890f76286edab1dbba2bf624652ceca1c8a0e4054bf173cf92d552ed73de2a267c99c6497985a08b98dce77f272aa2e8d74147bf628982ae6113877347e972f3b06cf8b8aac0e678592c9e1cbf525ee34076713d5a0a91e3a723ab609bb9123ab02b34df16e8b84dbda2dc184cc8a271bcea7126ed62e56c21c86c4d7cd8dfe25e9f9b15994d7770e38f5cc38e0818283cefaee362fd36fb484c81198bbb3e210d9e3ed5555167efff4cd7317864d9832472993b1a1dd50bef045c7be42fbef8e38e13400ab34a5d51723af20ca1cb50451b8ca9cadd8281fb97c21ee66b8acfdedcc7bf66ea2ddb50b3894f1b65c1f30a5a52ad94f0bd69f3a949222c37dd6e16f6ad03a36e69eb29fab7bd0ce087a8ec9e54beb98fc680e1ce3a700e2507104a2ce4d7589e1378a120f926468dd39c0711958b567f02fd6301b983e08ed2a3cce2b81a15fdec2e8d8b2af45e349fee5e94d7358dbb212c37f751e47f68a7a28286aa59153d997f68ec1a22a66e793f02932ca0e7052df82cbdd4f453bd2f310658a985c35e0949f5dd0e2dc6b3cd42a1b8dc2bf903d2309fb7e2f482d158216c9c572c0d35871f5e8f30b951360b9c9f36c5cf8411acab4357a0c939d8d83fe68aa1be30a686222455c01fbbb5e13ed34b178479aa7d57af812fe3a7453f86eaf1db4765b5153fb738594d9e75295528ca9834d42c7cc8e574766521e34632c93f1d62d685aafc8131d29ec5cc1ba92da3ad041d854b2761b7f8c87add9664ebecde68a456c008b91a9c66234ca61d984de78bb1a96cb581f4721a15a5065f8b5cb033ca16139de594cc9e2428b677c50affb8e1701ca7daa0be8e39390de35656866644a9ead3a01808bbc9e339820063c5eb3358e0237856d8fea6d1bebabec0353cd168260baf6fb3c98f8e4aeebd23f4d0a64ea92b6ce908b7bcb3c4470280a37e07fc1ae5fca251ca227b638a23c77bcdecc6bef7c4755aa5d0685e7e36716e4fbba09ccfeabd9591a480b7afa363eff247e96478a7bc5b5b6ff799324b1d1b4d02bdda001ada861f73d34ae6532e9616b2d1ad676c0c0588929fa08f14375451de5b19cfd21b9c0cedc6aa9d8a1f9629219ea86390a9f701b8de9e4b4cff04bcc9db609bc7f7fa62f666afd849ac1677e882cf6364557a0908413b0659fa53d7309eb2dc2bd94a4427a51193c403fdf001f6207ffbd6605ea5cbd56e604f2d7220c976de52b8f5e39b7e3f72a90c959bb8ff714b06b12a84592a731fec4e0359cdb53c0029d54d9a7075a28ab92b143e39b033f80050d1ef52a00edd8600e4a0c3c8c227f07af71f969ed906cf84e9cbb0295666c728ea5dc10dbb8d27e81c837502b02e77333bf387c4357563388d240234a3f102f643dec5c969e3945cbb2267d0b5db30dd0654a51aee237663dcf23eafd2e6d633474bdc11656b9843295214322b72fd79348fc84142ea521a28f0fea1baadfe7a52f4b12f302b9e34311bbb1a2db10ea8829078babbc1b26a3c50d98a6bace538e5a865799135778c31927902153ef12e06b8738889943f411744d9a6559ce1188cb6b161cce6d606de96f2fe49f0713eed1f002718c5c2150b2cbd5ab777e2b8b9e968f1d4877bfa70f59d27453b8adceb637b7b4b4c7040842006a9dc5124748492af969e386d36d118fe110437b58c0008c64d08f6922d5acfd24866ad20d7b9fad84afaa9a15a369812e42e2111dd0def0ef599780a8c5f9fa7b577389369e4517ca685a160e2fcde1cd47cc5bc4ce907bd481b10a1a8b91b9b6a9440bb907ba3d1534a25188ddf7e80808104209d6a2aceff457ab62527e1667a87921dde35528edea619875677f0d16c148d1e3c68a40c89392a79e6e162cdfa21e9700d948a98d84b80c72bc5d6d86bd234282555ed39c51852a886e31b08bf6e75f98247965364ba59322fdcc0744bff906a9b6fff6b8c4a544f3537b3918a3b079e6a5df59853337f4000f81780a506f463690ea3f07d96046feadec0b7be2dd25e539cb65df7a336af4329e53bcb3708ed5a1e2fdba737dc4f2bb66e587190326d6d774b20620a218c2d588e346593bb9b2b40818f33f606853576c2983fe7fedc362ecc860003d99f8dc43a41ce93265bae39f46c3f371c4b0dda97c700e06727fc147cf722fc28c95e0909011ebea34a5b6c1b80a58ff312f4a64cb502701c3585653cc2b9acbd35c5a94d04fc646e7ef1f9e96436b937f652d42d510faacf4d945a856426ee7df0e4fb0e7b116d2d07a84a198f2641ae52b27bc52bc555bebc6bf6643417640b99c242fbc9738c9ed6a5d16f7fbd34dbdc20ec583001db8f2ceeaff7a9c8aa8e66b20f97fa0d523fbd35ba6bb1b6a62d51bd2b36da8cac1e9bba4566f0b69e180746ec8de5547d24f8314c7780c455b115a65c269f2f9a77ebfd8d011c7b0fcdec9a7b7c86f5058bdf8e00da87c16724fac4d146ecc02cae8883be767fb6e1c78e829219e2396927ab1b2bc3def1a42cfdcdbe5240474dc655502fa72e9eeeced08584edf1f03f128b94ab2a8e9336cede8ea5fef4c49bd654a237092e29e5cf550ff284b5d12e574dd20bea8f276ffe53251547e56ca4cbf8e511e3d369a003fa4d9869a3bc99b10f07fe410cf1a0051668dfd1b4d608c3bacb0add1de34024a5d37676db4ad073a983694fd4352b100ffc61b9b5295ddc9f8da2c94a2ae3025fcb344ea673639bc24263f7df5dc6aea9ed4dfb4bd8256bae274973201f4f70f9fdc636b731ebdd7568dd7dcbd6bda8855a891898d49b3d7a35f0ca2e34c5b485c36c9ee5daeb50849a2ded8778092e327d8699b5382aa72bdcb28c99d992e7700a59c62bce1f5186028102414ffa70f004da7f9bf79a12ce9afdd3a26f5215127ee419dab7de9faa8136f132e8d51f958c17e54e3ea7bc3201d9df814a79780114ace094057031c65198c2b2fe223a47b07550951d26757e8613608329b09d030eb9ecd2c24732322b1c18871976a35588eea616d6d4d1f1cca70f2a3951cdec9857b33851183121da07119c30f4c40b984a90bd03a2a2afdc2ab10928c21d2de853355eca48c9913aa98cde53f19561c454c88e25073e1df0725e5f08090a012eb75c7e0c35705175cc31e05829b8db8c27a3554d5ce19d9d789cf4c49efb97aa6fc83bf565b762c3132ddd4b3649185fc6d8329c78b07ac1e24d8411a2e0a35f761c0fe10c30ad3bb42b35640267574831f41e61faae1628d8b0b1abf35e3470e4d042a384e63c3a7174a57895d441d5395d52e018694a4cd1818118b4aa23c8633aadc88995c332f6bfac8a166349ebfd06171313eadff7c9e27deca63c0cbd1f0f4193762ab3f8fabdf5a149c9cb8d03c6c0ec40e9b78b8c7c95ed762b42b4fa1644a4fd7201bd67c5512d13fa2628acb27171ac67484c45f70e5f20b56282088da46ce92d0bb03dfb15d872ac84bcf7f2b03c2856687d203b5ddda5878bc0313d181531fafe406675f02d47c18cf07a784524116dd565e5d2615fbd746bde4a32a9a0fa0eb47a00ea4f8b8e11c6729c4cec89a09b5ec7b3113dbbb0bd68c29fc8af943312492770e1db2dd2c025f1866ac7b4684919e5b1041146554ef3ed6fb940c60d1747b292b9806e7db92248c3d006f70ba3587a78ed08f2248d21989d614d8bc3f3eea2cdd4f5e866373a16ba2369b3b6d909b3cb597c816e20e4a2bd7d3de74dd640a340b5bb33eaaa6b0c79f67d1b4cfb82fef380d13f71f6f5f0d5c2dc12195b2421467ea95b329cb31dbcd031917a99687efa660cdcaeeeaea67cf60db745593498fbe9aa461bef67d8a3363d00b187a637c01674f77bfd890f1888b01ce30035caa30c54e8f5bb82358206714ea7dee58763fcb2305de749d87b13d40b3f910270e9152bfb17a79188fa470903784c58816201fd6601aa569674ea2ea296842a7dc54b87d8569a21e549614c5cee7947a74a112ca113593af2aa6a3865effc6e8f0fdff570de1c7587ab4b3aaebee043502bc78790f327ed735b03dce237300adc6fc20d972ae01a627957ccd011329643facfd736b4a64087a55d19ef855bd3152f71700644e08e3074a1f6078c7b67e8c4cc11f1b03bcd71c80eb873dc1fb8551f3b2e8ea5ee84b21da54f6ca9cf5c6555ecfb14c18d45013c72f369f70fe57ace7ee047b4f14713ed0199687faac741ec9be64ae1964f823bc912cba04032b7462942d9aa3e1a69b8f02af3c34aca59d87179f44bd13b88f9f74a1599d61ea60f704ecd2031119a5e8a1e27e719ed9195956ea19f059a1f5300ebffa35e72d3db017a30170cccfd961d9f31a22051fb72b2e6c3d9d7fd58b117d1e0a22cfc43c1c43936d04511e5be1381ccd1a6926089f5e5defc751aa54193ef0731c83ed726a2e1d01204548d57263da8cb0aa2ccb3ec1951de75208bff064b01f1414eadc3b335a162eda28958f69d81729145db18962e396d4df01a1ba54047da4da2871bcf00ca8b217397e4fb56bb31ce46f68339d3ab896182cdd2946dfaa7cd7238d3b8cdaa687fafa406f4b68a8f673561793e8c4a2c53f34a06d6e1188acf9453ed290fde14e70fb9445c49fc8187c49428ac58c8308efe059860bd57889e2b4bda7545905b32029f12f1220bbd06ca7b3e7c86fdf715b420e2cdc8238d8cbaa4d7ebbad9400afe831bfe0aa2d5d13cd37b1c67a61bd4349742e0f6432816acb2a74ff89280fe633ee5db7a7d5912e50e2193ecd62e271b118e2567d9314a72ede75edce8596bf4207a0d1d20743c00675a04ee", "spend_index": [ 0, 1, 1832806418, 4294967295 ], "result": [ "37c32ca712f78c0a2b79cf694fcaa1d5b9507f340f7990c9cdaf302e49115fd6", "d35774e6a3de1804d0a272bbb9ef66aad6cfa0d8d85168f713e8564cd6efb18d", "f4542fa05da4f3d65460dbc6d5405bc53e598b7c705522acad7c60ebcefaa820", "8f7e23d545bd6a60f1163e93597898fc7aae20908cf6d7fe8234f938accd962f" ] }, { "desc": { "Inputs": 5, "Outputs": 1, "Witness": true, "Version": 1048648188, "scriptSigs": true }, "hex_tx": "fc19813e0001057919f7c800000000000000000000000000000000000000000000000000000000e65d7e7bfd32010fa794039affa3f3e9d96e19bd2307ecebc3ad309305dde575999a26b27b4262c84cf228e3ebc3d0d31babbf8759a65d0345a8c2bf61b9be6a2af584ff23531b5bfd0f9b662cb66083a0be67059d5ce61255779f53c7238c3a7177897217579cc2ff1d1eb2f80e29de5e4b2cb15b6004a1a08bb0bcb84c4086bf3448c14432fa5f0bc38f5dcd1b8bed4b5f805a79702a5c0085f68078d172d5b55595f19de6df3d2dd394c7ff16f07d3f6cbe26f016777467b252fea9500ba2cb395d9f7b6f20060546b6794f71875555d16f657502c02256bd753cda81822ad51759b5790ba5107aba32f0a7e91a9e94ca2603cdccbd2ae090cb081983bd3df7cdbea890fcb854dd1d917161b225322ce82dcb199f7cb93f66be068cd96ef99d4ee79a6b53b4c66a22026baa3055d2eebca3c0e582d49a1ff64e11234dea527500000000000000000000000000000000000000000000000000000000f0eb47f700d9b7f0b981d8ee7b000000000000000000000000000000000000000000000000000000003aa88cdba15df59d58b7f3d9273991b0037035c5cb84016ec440c3db710bae81a7a7162f8b53831c32f16337eebe086b882cfcfa56e989e46014e61cfe190f69d2adf7ad89fe29ae997d5d3d83597ee980493ecc54dd04f767c57aa5ff7f4e7d44b230dd4e1a7eb535849e0765430afcee14861640c6897473f36dc9e685d50285e1f431d602f02ff636c62184725e15da9dd72e113086db1242b411a5450b579feaf8b85130b4e2f8167e5f6646000000000000000000000000000000000000000000000000000000001d76f79600962246d98aaa1dc700000000000000000000000000000000000000000000000000000000a8bd311223797d73a99a97773ea1c65ddf29e4e025bd6d12f0d12da4146dced8b40f9e9f58e011577dc0f28e01ca1fe9e7c5785e0bc8fca81f655fb193c3cb85d9a0a1920457a7c0939de6d52f5abe57686d0b9b8b826170729daced19309b4bb74dacfb6d3ce3b66e332f249cb92158e231f79f5e4d13e82fbfbc4e943dfb57e13c68c8d0980aa49e135a53875c0479434684375c255739c8e256fdc943edfcb7276c5b0eb18e9a12d49b0122547c48534013b06ae87b9cfa3879e56fe2d729d0bd7a71c5cd6e9c0fc7021789d634068f5140d2482a4d799f8ba6590b2fbad26afc05ec6aab0f9dd741ece954a841770e0d3e68c1333657fc9ba7ab5ecd03fdff00c4aa694fbf47ab2d7d6f6cb59c44a81d3d0f7809993078acef49a26ab47dcb204acaa9f15de4bad7f7b066889ef08a969153700a1a12e94ec854ff26c73523ab66a4f993ceea341b8fb36ae2d0a4403ee93d6c06793c6762d2b70806d4d1ad1847d0be57413fe255b382af298e4801062f51cf7e4903b80002d75d6472bce7a548e201a54d227b55b86b2fbe4e99c021916391942dd0558389c90599318f73dbc336369c2feece76768fb4ca0e23baaba952b96be66d6f3c7d40bbb254f782e9b1edaad4aba094cea2110a3a563c4da9ea50f579e095d01aa52485ffd27f46f376b8eb5da3922c65ad27da94afbe9da4e2ef143f7b7204f5055ad631740e4ffd9e01766c13a9bdc924430ce32aa146bc075a579eec1d5ab120036fe39ba33b32ac6c5c0280df3b3e67103913255a4f2bab80e39e50f6a25de1bfd448128778d36534b5ef45a35caad784310cc7f60692275c42799946befaed27ce8e60f7388c39e5ee32b00b1c9baf4f2b3dea04ebadc268bcf65b694187b715aa98d2e7538e2b4f5adbefedc18d6965920ac4f97ec926546379f13562656617970b7504351056963e2e8452291b4e26364ce3298a27fc018b421ab2b3c0f4c08215d450194b8ca8aaed612f7a60e2f1a0de54cb616688e57598aa6608c65cfab1324e74580fc44d8763379f85cab070763d4dd177f29e01daabb4f54e4dd0667e57b0ab5fba7e2b455f9eabfac1f6b1474a097db21b4ad8e08c788b2d5609016985b8e1318c431cfaf2897fae7dad1e56e1eb18f95009dab214b20d328c24bd53eea3ccebaadade7c60ca23109937dd7eebdc31149f1c0c425b9b0bb1a09dd937775f284f01c391b13a7507e1b448e1bbfa25b159d6f11dc6143d5f804f4aa40ccd623258eabdb4b161e148eacffdacf6c4562f96147affb315332d094a25fe688647aef1fefd54017218f7a9aed63a7468e04e2e7a5c5101622f2a2947dc730663680943b9b28c21ac147ea83fd2ce98df5d029a3f2e1c49d0bc0b41c65f2cd559f0131eef6867149b72e42f1d0aaab36ba92ff28fe6dbeddc8caf96aa9b261cb9da990f5f11ceccdf6d825634effe623182b2f941e399b0f02be0bfcfa3d9a7f4f7ecfc805e8193974156b1a075104185ab4471bafa751cd0f8b614a25d79e3e5afe017d72b0555ef44264921a5622a88912e19b8a44a403277f31fd462751fc591493c60891eba1ec19e1b1ddda2f9ed1678b612908a65149b34c365888485cc47f4484f6f4ea4ad5dc11b0769bf61563ace4e43e47f3a1d5eb24a96f17a8fd4c5e6a65493010d0436543dabe7ce47a239e69f1724c1dbcca5ecbfaa12ba09ecc6627464e8f490ea115d3037d2fc988df238a3ff0960ad0a2f0a3ef83ab69e08561301f2bced3ef64beb2e77a6cf7d1c8f2bd8823772bb0aaacaf802cdac226222a36df8fc1d2a36e1cf4ad433ef61005e9823c90dbbc541755358ec515ed4ea951addc744c8b49a860718d08aaa5ceae5923117ec236ddd47747e186e284b4cfe5e3be29a1c0f8dd1a4d5d1417558b3652886bc382f6cb99c80370eaeab9ab77ea56301aff7956539df5971bc22dc22eaa10e46deb5c3bcbe7ca9d2e98bd9300d7510b1735c9cad57c38e01bdb9785281493c2ccd5a596b729f3c2f78b1e53ef8c360300ba1e3fddba198afc29dce9ca4bb35c44d34bdb2fa87bba1cd46e8b9b52208c84c4a02d87d57be9ea1a5f8aa2fd7d6ed8c04b73d8dbf866ce9dd25b537ff7aecf7496374da878822c2fdff94a4e4b5f22095ceca58d0bbcfa46d234b25dabdca5f372112a10ba841cf9fc0aa2f98f3149736d3e37f75f167e90728174b74afb8d14951cd217082dc03280db31ae34b71cd3b92472316a523bc8cd5791bd60edcf7bc23802244669e7167f8860d4ffa693a612ea8756637fc03d77bdf806c411aa605c9fc9f47c80b5de79d51780381aabcdeb7d34765a29168449eb7ec25164b5facfb63170002fd77016d0113b330ba114da0e1ec2376fbc6e0dea5d13ccb97e91f07324780f92bb4b4879a4cfcc62e04ea41ede08c420c881ac5a04a5e865cd6f39102fca7fea650f31f1585bb551abe4b51e06d840094620b09422827443a8dab11b89e5174c0a76127231ede40daf3fe062ce63b6c39bf9f502ca8f43fc385624033c874fea14a0bf8af2d0e8f878c65e12d4466bfb1ffa584f5122f9109f2e06149676378d414aa32f5d447553ee69fb5f182dd9038aa7f1e27d98ef5a019a870d7d9b8b0b4ce518f2cba8148a86ee53ccd74abd4f65277387681ff486f8eb9ba0dff07747fd42d64e3e0e9dfecc3c4d2c904f62355d07f3d5bc5cebbf4ab6bd5892667a135ea792cb4670ccb1e85c738638df3c3ca3da23798e3bde0ec1bba7c833480c0f79ca237655867fc86d41b90fa1accd7b0849140188f6acc0e5c0886adcdd0b0f69b3d5e0eb98fafe9c4d6e69a3e6c83d7135f34437712e512410f70487471a30d67191c6a30a75b278ea61fb9fac3607ab088a52ae54a39efb6fde90139c71fb9cc0c673ff4606c1accc1b525cee174b00aafddafd80cedc70d7818163da95f38b887644cf9818a35249058967246e8cd70a5676092757c94c9739190ac66b13b79fa59d86e2c9b100a65229b637fdcc040f4ce14841fa72d5169a4b7b4deeff4cc85ec6f3ccda4af982a3714ae14c6a527512e3e15b7f9edfa51a6869394d786867e946a0024ea8c8ae4cca888625300de49eea2d0c54b73c3e000ffb51671641aefd6089f4aca68ea5f161d60e4b9964f4f6961dbee646cbc9658ac1f0e8be238f0e23c472d699f998b7f99fe5bfa5191e5fcd7ab3cd62c17abf7ea2da7ad384180f2e81c30c347f3dbdadbf88a1fac852b5a0b504e5bf32bccd5b3ac0e8950af75efb1d8b7c2649e433bbe9bfe38dad16b7ace8f94c98002331cfdeea45e7c93a55f5b37a04b790e55c01cc377fda7ddc272efa95ffef7bc9f30e30cfa13ff1f423484b6eada061883bf78f970521380e39cf8abac77ea7f9c17275446031d2ecef94401e1b8573698d1c91decd47bf727f0dad4827141f8fc397476ed00eeb6b30b7809e53f3a0c28f698b18d834513f04d81357319493dad3128881606468978cbc0e7eeb7dc60337ca853d5b577745c0bad4ab4958da54cb44544377a533881bd34e774dcd072ba4cef31837e90d8030698f7aca565c8d53dee22130872b30f0008a203fd1601929a9d48a5e334f3e6ff49f395c0f070b1c6bdd244521f7b465e3bcdfcee15a34a7fa76298ff78037f8b3d2e8813b4b388905da8fb019863d11ecbd5de55b4c87c87d43260d706762ed2456d7dc73fd660e1f843007832b9c1110a73b74c484a89e09b5396ed59b88c56006bf111e2d685d30c45c52e9c95d3e9fb4fafedc73b885f56bd0d5a549de64638fed8e73dea52a27f589ebc61a097e67685ee93af6c34fc39fed019df6a22df2d08d499be6bd86a410a64c6884ceab9552880893b3b34421eeed78c9fd04109c02efadeddb7d7d53f6d10e3add56059cb85856ea2ca5a27e15b714558ce7ee2150beb2774e988331cf48653b85a00ef9d2a1eea097240e36862652002441e51de78d450c382e34ef6e46862fdae015738b3601582b13040b7fe6fbc6de4e456734c53e28f8d14242555d3316b2122e3af0ba377cfbab52de62bcb33dff5cf6b20a6ac2ec69b4fa6b7c2e3ea541c75dc9f2cb85a377c2d8eda281735670d567ac52ce01187c90e4a6a64d5280019f830c220df13336d77f957f2866119453d8505f28e794e7eb4f3147c87a6707740bff8cd569bed1758a18b91294043ca784d998763e7b8e3f40638e4a4bace7bfa0d8c37c1902fd27833e07cf3bf3dd2df6f218990ef22b3788ec5eeb80f6e4e0f1eb8711853fe6abd0e1541768f139ac59e621611427bb155ecfbc29a1e6a89cecde10db352d9e47fafe131fbedada6b88cdb8be8450ca1ffe6079ec465bb0eb09c8f1fddc78b1e3275caa337656cf9d950c07a5b4352dfda1aafdfffe4c1ab0a2f187e77681ccca41dab610784669caf96099a4ddc642f3b25d9f32cbfaf5a7e0fc2be682b053d1ce5852836eb5d92cc311bac97b15644bac2a976cd79b98af208ea418f627f12ec7cddcdbcea2af39f4142d27dc082f62e72dec885c70e5a9f0221b3eaa530682e0cdd94b77162bf7a754b7af5e66235b8385818eed92727d692e663571cfc05168be1022940ebfd5701023fb4b0525dd9771341a3cc7c30e40c4b8cb63b6ce521d5f2dffd78502cd60366ad656f81c062fc9681e816fa1d2996ff1781a7faa15434bce60053911ead81a4276b5286ef6c4fc275cf82f70e03321670a3711debd9af75ffe89458f6ed08030e72f3b1009710065ab123e7c1e0bc59def831366737ed18d296e30f0a0b54864c8bb3ea00f78019cddaed1f9fa04904bd95e90d325ab38636b5ef808e642bf723bd908b880a8290ab21b517edc655fc5e153258247e86da6cc4685bfde2cf56e67c4d2223f4ad1ab281e8fe141770731666738dd85afc02514b6570f443034fc13366baa6d93f21b4c0c4ce3890c2c3318f499143cfacae2399e2a0ea631c7abbf48dc4fadb9344e541733be5a422a2e8bb3e6c191f791ad3436b985264cda9413e1ea3e6d901ec9b415819c070b550a56e1be07d4e2f5f5d69cd0adcc82a02bdad4ac97af83e61507728be63b827bb021c4ceadbb255a5f1f2", "spend_index": [ 0, 1, 1745923530, 4294967295 ], "result": [ "a304cadaef6eb838f6df326869d80c806d58a93cc20c494b925c726352683c4e", "eb7176fffdf7912174e560a5ff54e1ac08395a806d82cb455519c2a3fc55b660", "2f8bf5b54a8d1d4aae6856c708332f620d186e0189330269c20e0e39f0329004", "422e443fc02afed28b59d775310e5bd176429d7ff35bc6cd1023ef209e2233e6" ] }, { "desc": { "Inputs": 4, "Outputs": 7, "Witness": true, "Version": 535452497, "scriptSigs": false }, "hex_tx": "515bea1f00010459b69626000000000000000000000000000000000000000000000000000000000dfd2d400062fa8216f775ec6e000000000000000000000000000000000000000000000000000000007b683498000ceaa30783f09d1900000000000000000000000000000000000000000000000000000000006b76d100612bc5d8ad80741c00000000000000000000000000000000000000000000000000000000ac4553fe005ca4b29c073c7a98a88aab204fc83b558c87eae04823febc0d62216f8f50e8d45c6f63e6d271e9a55847541bb8856658546aedd79563eeade644d8ba23840ecd1f32e0e1b9da9e74c6eddcec47c6e547b9d59560d00ba00ea56fea17780a2415c97a7fe356fa79b46df5c74fbb26f814fea704a0afbba57dacd18551b5790668f0fda2a20fe32f6e9734d9ecc8c0f8d356e800f05b40e290f059e2cc0c9408a7794156edeb6cda5219a52516fab0feebd6f4060b5f616bfe5977404f37a0e9cb7b15b1403bd2ca9db8cee82e7b2df1d9c791167727167c014b917e00a912c837957b4e52619b1780a59fe0965f157ea9eb445e81ea5cf2c6b46b797167cf6e590ad4e2fe2f0c0baf47844987b690d5b1a4b433df5274f1c923273c441d301be9077d600861433c275466e5cddcd77f4468b0fa50daee4636e2669425c3f9c5b5e1bf8bb93b73051aec8e11c35d1d25917aeaf4b01b8e203359cff019a9bca8b8faa25a77e6658e1eedbd598666f7cc0f9b5c485bb2d39afd843e4ebb4424bd80d7fffbf8413fa8c9589c87bc230708cc056fb1a47227a44ce150ee65336c6bbb9c143a4d7989a16fd3e91d546c9178c8145678056c75de5e54e71c7116a03d52d470721711d5f062dfe7dbe7961798941445fe1ef4c7dc95f65f43af3b4d13de55f0de7e3fe90b1b75e8fe44a99af1b9cc830ba635fc410b2896b1b92b5bee25cb6f4924cbafff05491b9b50e1ded3f416d0b21ea074917eb30247a725b8ca9833b944484913795baa96c9c9acff901e686c505ee1ccd05290b6c1f69965fe029924b03ea086f772a82f26388cc799d45e6002f42b4bd57a9be968a0576b98bc4de89b67512d4d7b763ffa9f22a128f52de0157bf03b16e84e9445f1946f7a2ac8d36d656f71d1c292b966dc621b687c4f1a40358309363213d971b61d6153eb7093ffb96c6fc53070c6f3ba203be741cf669eb0458b0a32aa8f31c72b16767c68fca193015059a906f877c2d332ddc2a7a9dba3d0ccb42642791e40920cf5c6596f34ddbfc59322cc09c02cdad94e39d7a303e49de3e6e2a54a1598754febccca739ed188a7d60d61268c093035903eb2ee5a754414d9d03ab26d0575e88ea5321154c3191ecec3c6fc0a7e2f7e05351750e09a236f81eeb792c37b8ce475e47fb1c648877abf1ab00f7629685a812f6bc82ca6c53302228b6ccc8d5c9fc763ff2f1dca827ee487321338c90d0b81051ffa2da2370d34c928527ae0edfd5b3f972f4cb458f4cfcfc1eeddc9bdc0da78f416bccab97d75461e3acfccf8da45da0cd56e0e3d9388ceb1b1466d0e85a9a5c262b6e3f5728863c72d1d62b5294c954adc112dd7a6b93099e1157d113c9fb6f5d3aa92f3f90e2fdeadea2cadac863ad304d35d0ca05235484fb3439798b689746018f02fd032bb573808b2709c7078b7100f2d40c222ec9a30ef015a7956e8dafafeea28662ca4cdf117c5589dede37a6fc8823888e2999a853c5531daeba32e578913fc8e49ac6f57733252dae6e208bee83c7a9dcbb72dcd228081172d05b858066a7a8d7e888efbe47410ff0539eb83d9bf032d95a0f705d2869f06ddefc31489c9896ac79560bab1293b7a2b0f8fbb997f3a98f173e3a3cbb29a648128903340642a3148a0a1a5b8f33f615708c5b6efaf4ce13bede2e2751b7a20829a7282b2d88f926fbb1f23e44e26b8ff665d6d56baeeecd966065eb0db1fc0b042ad4339f1c1f9aa091eaeef7089592dba546120ad92d320d7e001a22be2337d5c8b6566c83eecb73af5abbfa7ae3b1749191dad4f5b7ff0288cb2b5373bc96ef8f8f429818ee9489f3fcffde8e58432b601a62465da63ad432490b97f9f83aab7289b93347c00c66ef55682eaa80e0fd3a8eff5d4388b1b1aec069e627d87c5db55ac3bdb43fac73618120d6b6f84c45421ff322477424252ffe2aec5b3bbbcb6536d7a5dc39813a1bc530ea3c9827ad6a474fae6ac4f09ba3cf2197a25870f7dee9033a10a916b3264f4867cad04f970cc3bbd133d43cb50045827687c02add9d4e5ade421a6e021f188474f02fdbc01527d824809c664e54e8f4b2fadaa4371d88b0ee4574ad01bf803c4ba806225aca73e858e12c68e0168bfeae8bd9e5cc961b798f14560b62f6087eda65f94a2fbc3f9917bf685709ebf3280510ebaf2893b656a80ec764f495d47f51649110508ef7b5762633fbeb205ca070869b741716c89859a91a0fabb35b28921b6c5a90a3c21582617039e80b61bc00786cd56bda070f1cacd6bcc92093230000ac7a7d7187997fb5da934318d65547cb9fd6355f34abc588ae76442631d9709db6760889f20df6669ad4e9db3e29065d0502e567197a0c6bc496cc4e9af98c15d74b1932b9e22aefdfc2a70941c5e3dca15b9c83f5e9ab66fd165c857510ab7d1814b562b79ba913ae004b69a048873a83bc846902a153b08b0324188bd75c0e318f2479341dde3ca8f81f61b33441a760bc76745a70ed62858405ae087b6620fe251af0a3ed8fa831cc204103eac583ab86bd8d10e418da656d0b6139e0d4e2fc1902161b6bc2ad28b82f693340ba6e45f3ad13ba8fc52a3a264723d285565a518b1af1fd46d5277f63f159293e686dc767b9c66eb95da37aaab4c213564a6093d94ba16b85fd71a473ff4981e74bcb61a4d7db1f4fa575d191434c10e34cbfdde01c3f1caf949d144abe593b9a52524b3aaacf8dff9a3d4c25fe2076d6a264795e52de382f24afc7373635e26daaae7b80c43a1a285c7ce3598045139742aa3bfae0e4004c030be8254f8c98150ce1c58fdc69f219be6750925ff6eabfe8cf00d04cc22560f9bc083a7483593f22803ea92cd567a1e0c6fe0de2b09170002c4bd5df3194cc29409bcfc88c49248093fc7b2fd1c812a62454d3c16c768cc1de7a9dcca40780f88432a1a3aadf2d6a2f5126de20e54caea02b2f00e770f3c77d64e764854f101c2181928a4ec8377f0fb861467afaf8a32f32412202d69cc95b6f1ea6dffd9f08709c9cafec3547b44c20073c0e2450794dda51cf3be2824bb68fdd4610d671285a1ccffac680f211e37c4074f6243b16c6d01fbfd737eef125e60acbff68e7684c63e5db89e2e056d5e5e514fb897fe4be075cfdd26cca3b7c8a2cf82f0c4e48b96faf04c4cead5380e57d19eea56a658388596edb1ceb3caf2af98d080406d72595df691a785d98d505347142fd7ed2f60d4652e656b7fc912a93f259e0595c7138a7bfccead7737284409b7d1a6ef2b341d1484161c7e069add654b9a92a426eb8408b6a19ee42a4b66b9f6baae81b117899f901c46d048b4756bcc142363bb637e8999079c0c2337100f33c51fba350568d322713b9aa45f01fd1901c919c7c579b233b9eba2cc93ec17504b87f4669eeba782a38c4c16fd62c6333e0934a72b580847d0ebe3b91d6376c1123c5923adcfe1746f87cf276ccc15674a32d7bd26940379fbba307d0afecbf564c8b7e0437b77128fc5e9d9d85ee983cf23d4c8bc69e212f24e0e502e762b418dbaa6b3a801041f9f8f0dbe5a21cadfa2c04675f4718dc795d71de2cc844b4cfb07d62edebc09727cb2487e31c0d908629c4dbaad67df2ab072a1da00b94394ec434993fd89cf68bfd61d7493fdd649574a554ea9ccc9b1aa00fa249a5de7d0895faff2b2d91b89a51d37268ec8f60897ea22986c01edb50372621dd0162879f07b9cf55cedaf153ae14d857d757cfc7e1d365b11101042d2d167103051f9b1435bfdc80670c8cf843100017863e7141ff0546fa57cbfe458455a98cf31ac368fab25a2db87f7c1ae7d3a6d83684f8560050cc8069039e796b68fc9edc1d8501ceb19e6b593c773022adb152397cfd8a9853afbddcc2cf3ec5c85dbba43b57674eb63846265fe477d25ed98c020e88ce914837d23922df78ade825388808798bc5e5fd949fabbf820", "spend_index": [ 0, 1, 2274644705, 4294967295 ], "result": [ "f879ef7cb7f507819bce8d6dfdbe97541312f1e2549dd441bdbfd7ed6d5932c5", "8921764ca88849594762727400d22d26abc18a9d3c960b6888dabf529de31d8d", "510b2046effdf94d4c171282607e83bc20312d9378fbc796805a20d95c97bc8f", "b7dd2560894c2ad5e70447ad231ff15591c747d30226d26b0c6169ce9717c11a" ] }, { "desc": { "Inputs": 3, "Outputs": 4, "Witness": true, "Version": -888944471, "scriptSigs": true }, "hex_tx": "a9c803cb000103251b783b00000000000000000000000000000000000000000000000000000000c8f7c4bafd7201729fb4d0f26e4c3e5eb7360935e9bf440566e57bf40f0eeb83ae10b9f435e34d38a462a1935c6b2ac739994d78e02396d81f82c51934aaf5511870351c831b4eb97c9aa6e827ffb6766d4bf10e678ae1e9667df40810132f8421637d4a6e7c938a800702832739d6727198f52ce35df1db5f970403d1575706e2782dbd1c7a8d96d51351bd21fb07db8a2cd913850e818ce1032bd2e048aec5fe9423e86f0ea12e0bbdbc129496a9808aeb5f8439ffcdfadb09b03c3c21016061a559851ee1e87a88a19ba4a3ace6c025bdf4478337fab304dc1291a273df17ad1a3577d74c87af692f00ceefb8ac81c03dfd563f84e4c58fcfa0981361a4ce8dc2ad49ea28792d889f725216f0d15204a6603aed1fc330d88415120f83b839e546935e3787bf483d200af99b9a383200967471068062da36cb23af2b5e902d9c8a35fbeae15814d1599f8d218c049f0f5f3179d680dd29fa3301679cf9dc58d52b2901adbd2ad75f1cfeeaab4be057fd8ea5ef0b23fbff4fde88afef730ce08900000000000000000000000000000000000000000000000000000000d3e5fa947504248cd0ebf1870672d1b488d6e685ab1b2bbd5fbc3c80128dfc342e9698c38c912f69018c7b41c36ee8019aa4f08d1fbf204111061f361eb2e0127be0a7265c8ee7537c68d2f3882f732590e4c63eddeb1ea2a2384b61d9bb25142980b87a45a9e3ae681cff259e230f15235b5c121960fab6087415ca96389938ba09000000000000000000000000000000000000000000000000000000002ca13736fd0001a25993f1314f5e0c90ff7040519a16b00a0cffab57dc7f70b91c10e5f22faefa53c4878ecbf5d21a77f72888e36074a83b8b444852c0f05ee7d19a453c0b08d83ee2a6a326322a195a47c1e2f7524ce5afc13cd1fa14fe25df6a3e66a4cece3a2cd54a0b5f8fbf37d261e9e29da3b9d3702865b39d3ed4292c1f48d578600134df0efb3889f22a88060838591f2b142d25117627b0b343aebf18010557e611373dddcc4d7f6411a8c02c593cae67240458eaa6c833115d5e4b753726a0739bf26becd66db413dc47207e20012244b171b12626a1cece8abc3069ad0d45d68330c46269d260421e310c0a5a4a5efdb1555c79536c0811a642fe96d9e94a5fe910f60dfdb104a15c9baa71593917c84fbd4d265d202b34393df6cde0f53f4ff6ed825ebede1758c6367907ede27e473648824cc7853ad57d93df391d857678ba09318a8f0bbaf3905dce6ca495c1e96c77ecb3dcce0131ebba23aa297533e47ed3fa21b2e6119caf3110b1d3db806f823c5b943b69b2c1980beefa82b158531812291d74c2695fe517fe78b9b6586a1d64e94a7a9b1e75ea3df9815d60657abc47cf5ee9af8421b07ba66165ca70b3cf2390269e02d147258dbe9e9fe0f934abc38a870a31d77c97bca4b0632b606fbdf08a3a6007234e4db5b6ca246f6946c8d968dde8a10de3c6c0c6e8629f19d1b3bc51b582949ad67ea54620e3bcf364906692162135c1da48d2e8ef422cbef344b9a4d0b957efa77ca5778ba95cb628c541706b148b4ddbb5e4b340a5f816f21905955cadc022d10389a356641e24c429baff1db3b30ecc6ab39dfd2eda6a6b3fc89b955be6aed5ff35888de8b3d1a41ccc86a62166a610f4a831941bea7ae2d30153071a7a9336f548c051a61d58915f2494e9102e0fb37517e69e35b41216a02cba836354401b5f4d3bdc6f5dc15bca49db4dd953a5c25cc34728e988959e00c80cfa8eb6968cdf0f6c76496397902420c48aed0fa610c4d518e8e3a8ca3e33148292c266dc2c2b441898fddec53a6295983f97ce751dd0dfda8713291be81ce6d12ad8c4dfeb274c33c323645fb78fd11d63f3548e275fa5b7de6720663c68160a36185bcfa86ca4e648cc7cac31115b04e55b590d451945eb28e787089afb610a1bbb0659dc4283a1130e3db593725ab2bfb98e3a3fd00f05949eb566ff8dc2f3788cfd1c11704fcc9b54a6da8daf265d7811ce9a206b220d3c4af63a67c5a1cf2c2752ee0054c4e2e8c6d647262b57c842278985faaf1a8a567fb2baaa7cebcace1c3b118c75a695aea39e91789a3b68d1abcb82dc94904d7b25027c92b8a3761106d9f1772cd5068707c4d7db9493339a9f175c42e113ddbbbec61db98cea297e0e48044a86e91153a13b8b8c6cd870ffe44f6f5f0a45971a0f8f7e30157855ab5168b9eb3152b45186a2cf2e82b4b2854197a8268dc2e90ac94245aa11d4fcc2016740bde768ba2de040f1cebdf3554a9492a83fdd76378d05908b4031ea74eb744878c31c6fd508edb5d76bebd8fd9ea1b35fcf7aa5850183e7d5b779a11eeef0615ebdbde6947e92ca39912fda2602c817e018816f729d6c093b201dfc49d731bdd52364c128af248e8eea1a09a86ac386c92fe71dca5c357b25b2d6de613b0f6b6cfa538944a58d3b7ea987a78d33a0e6cb371ad862593b36bb336a328cf655be8b6f130010d59b9a02543b50bc152874449a2d50310e8d335b2b01e8996e04865917c6344dd4503ff6f8cbc587f97a8311d82b81bab515becdf3dddbacaaab967d65d2cbaebf8a3d2fdfc7426bff579ccc377a3a1b269f3d678fa03a1f1ce684ec85f3d8ca636c4d4f0caa0a87fd223a9ae4d690ff4cde281644891b3b569aaa5258fade59540e96594e78beb8160339c5df01564c797b9842fcd44b0ed9cc2e3d78fdc249b4abffda51b8f1e59737b520eeeeeea89231a3f5f637468520d830d6ac314df4e81228bff017834f64d6789ece25cf47ad5f9b72361d41f7b164b26141b2150bac4aaf56c9d39e319a1822720f5f97da745f299715523b4496ebbcf9b8b0a90404ff05604bfd4c01562494a70e34cf93bcad4ab44229231d261b15da497df316a8a226db63428dddd06aa6be8ef94f6a4f97908af6a4657aaf9e291bb8364cf00e96ac73ca638c25a9ce35a686e4483b4a17a1c11c143fe0b2fc6c30b50843d27402b1f6c5d5ecc474e239b22f59be749bb37a453cdc19fed02a6273fc85243eb20c453f4db442ae2b193bd9f9ea8da49397c0adcb2a267927561c1b706cdc6e91c6358dbda5951d3c4586448b37743dac2bbefe3ea79b3c453b30e99b1cfe21b694d85ec4854057ffc8cdc71f6bdd8df96a92dae2197fb1251c6d5ddaddf0125fccd569305b1ccb4b4fe6729edc18291d947faa64f7afbf74e0a11c0da2849ff4444eaab1e296f9de81b6879c0d6e14630fd73ec47b0c5808f7445f257813aa12202748a8cb65ba35d6071ae50cbe5f9117c78c84e389e1105ff0874c19d43ee2ec622204cd43e2e81274372407dfc7466c6bda6603ac18be46e527073972f958aceffe5eaa9c8d2101ce10a79b7a77df95c319e354db74eab5960ebe5426e5be31f9c79595fc29dab8ab1e40cc1f52cb2b3adb4c06719d68fea391ddaf9f96c5ee18e0052ea48e4f7f0cc7f792989b7f44a3856b06ddc52a094cc5a8fb0a562a79ce1b92178f57680f8124236d40a0e0b6856dd78d18b5ecad5c4fcd5abc3996b29ff8ffb1ce7c5dd877700e6ce9b2a7e231d5baf9b1d0b163285d4a0fa02f5ac93e726786202d5078b4fff0491241d7c7d945483e17ca661eb81a5045b7ee6b4e175270f249081821f7440e963ca43f0b563b2124ee45efd1ab7c76de79264fadc3b513ea641034a11d7b294084d9c4a31556e8cea777059415be90302c03f8f0a21ec651dc1bd0728589738cde4e30a9daefdca882aceadda3850eea452a0c356fd53e", "spend_index": [ 0, 1, 1153863276, 4294967295 ], "result": [ "5c8a06db6631bb164a1f5ceec23ef45a0db6f21162d737b94e502453c93ef43b", "90c55941badef257688e2516eff289b8f0f6d7d4f59392e6c2ab23983010346b", "fb1379eec6a0604e711556897ba7af46e15adada80d34675964b20a2ec4dc52c", "c6f673a6d3aaada09196c8bc72bc63dbf0657a1e623370397f2fcab93f19f61a" ] }, { "desc": { "Inputs": 4, "Outputs": 9, "Witness": true, "Version": 580803147, "scriptSigs": false }, "hex_tx": "4b5a9e22000104c65d934b00000000000000000000000000000000000000000000000000000000bf53673f00058019c490910b2e0000000000000000000000000000000000000000000000000000000086ed708100922d724fd631303a00000000000000000000000000000000000000000000000000000000e6b4819f0035a755681a1881e80000000000000000000000000000000000000000000000000000000033da8854007801ad48096dcb11c966fd0256c8fe93130a73f2a303453dc954b465760ade7ad8900c35cc91666158e193bbd2c41be5a02519bf5759e47054db65c0d2fa395c0ac8f6d33a850cc3fc588a1432af5ab6c1efa8afbd812a7dfe0f4c6e22b77cf973454894ccd88a9ab6c812e249515efdcba78d830e27c4c0377198e7a3bd64c4a8a69fa21ddec9036baa384d1980ed9fecf8f54577559e9119f806a65570ed6ef54c56d0054b550675b7f18e1ac4ef6be2cb82b3c57bdc92aa273ffa0116450e9454c450a9e28dbe68ea756700c50548831e234f5beff8555cad7620692bc874d6d18d402476964b3c6faa9c39772e99ec65ced20b421445bd577c8316f64f560e278dbe89f595498fe39405c045749482c71f744b94804dfa414488cb19c79268c47f8fbc208f71651f4bc7c0edd892229a624ef8d1ec2c39c4cc76323f984cb2859abe3e5535488361e6cfeb9a608efd8b11152735e7114ab9273f96a0fd4b14b5f27d8a646f6c6053b3e62d902f7ef559133aa7a00a408f9bb2b2b1c659b484df8762a93a8acd67bc78bd0ec14285fe3e0de18cc30b74cdac50ddbe5a274542fe6b26afc17acd0921557907e257c86381cf9e0307c3cd37b63b9acddfcdeb4fda9cc1942268641d5ccf320ca5ce28de57687565453d385c90d84127f0004de6d7462af9c400a394f623657a0f6c9ce4331bf11cdcd56a8d84c45d249c21837ef50d348bcd221372ac7a3d4c79b29a20fa290754980c96ac54d701a20754d63c4a9a4e065e289ee9aa02718d11bccfb61926d4bdd165d1ea94ba55342968b89fe391dfa8d6fcdaa4a7d1e23ac230ab1a3ce163692422da91b80f815fa0af697d40f26b304cece4e399ca9bc79874327ec1b7402c2e338df54092d6419a554cc85edb919ba3fe6ac556a03c8e21621ea1415aa6170d7724a3ee66a1a25eec67452ea2f0feb0d6a8973b916e259b0868a242caa425e9e04e629985a3d3fe6ed92e18276d013ee33765ef03c66b98739303a8f0121ef2e7d49f84d578740f46ff60fe7db6dcc71f27c5ef2177e90645822d512cfe704a5e7fa8d8241dd4574bef509b18581f5b1ee916130dc89e0efa35beff49077f449b22f9c1d8712312612d2c59eb0c0f19d138e4345eb89892aa037d3f39a8dfc8cbc2d034be9dad2c9360012568f7acc2de7591dbfc5ddf15836f1ec88f65073e185a60e1c833664f3c843ec5cd7b52dee3035dea7bf95bdbc7a6ad865288b83dd7d446ce4f8b543b790fabe3dfdb90fa6082e5e9f33d343aa3dfa76d0083ec8f398e193ecdd8bf9701b539caf8f6d7eec356eed95999783dcbc97766de1d93e04e5166748c80f71069d467485c94d4904216c6594c7698119c95418d84fb2e9674f2098dddd439ddd0dee560d5370b40508a74f883cfcc6ec1bbfb1464bab1382b168581484abdfc16fc7b21d18aaddc42e05b9de07645ad36c5a3fd2b34fb1d92b47e64dfacd23b8bf3a150c8131348eb04f53b9104ab0949dd2de77d3f881ec5963d6a05ceb5b657fd950ac2ee021bfeb8c58cca30bd731c2f41296c821af25a393b5246f6ff49a5a2c56f9fb882a0ce5c6878f60aefc598074235fe6b55b8cc59e8cc92788f2022688e2b8828c58d45f7663ab1aaf5bf66a11f07632716bb503b1c6b3753c6ab82fcbaa52a0c30e8ee6fdd769e21fc7358c4e3e65f6277da87028a49b8b985b7e0a9fa302393f81f340a70a6ee5127ba5711e351e67a588433bd14163d3ddbd41e88f79325d6436c2289cd37521739f728f5caf35dc8fd6f134f64c62155ba9fc49bf3e0113096b42b938d17f992f51facc4f5f02457bbcbb8090b72a0effbc9146cdbb640e3620c33dbc38726a517ac7af05242314f5e7380fa4cc40ec7a9a2158e26c217cc51eb7ca093b6425e9ecb64e0dfafd4a7d05a941e9abe755fbefa0f44e047a9a7ba9f29fa0488de73478c94345c55d3883641f85e6549eb407b7ceeda048bfa8b5711526cce638aa8c7722816c9202ec84940abf38ae4e77172b4792118b674a842c0be40058d856b44f18e5e054cdcdadb38d143d62f18df307817955888565ac898ddf2dab2d813f2b1bb762d027660387af38882b92d965c6475a9bf0b4a4023512b9acc1767c9d385972fb000512b44c11bf1c3e5a7f263b61f61515388ef77c8bebbdfd5e858dd6115c154a8031c7c2a2dd6e2b6f2b4622e9be8cf339db0da594782498b950bc85733c2eb12491fb881390145a499c4a3b78503e9763ff9096e4054a0e343d247ae1bf56b2082e6043fbc7d0fecfb59196827083c44ddee9e21ec18e8600b38e1d4a56b564beaadbbfe99a1ac774fe83ce7424dc5267155a13a38146b701ff9c37c4381f0e5aaf31bc88d694a5a978f71a9d2e536da58a64375e9ddbcafad8aabeba5f26de48458cca691e4cfcfaf26a7f73091fdd06b7ed4ad9439873b9c7350bdc4d08178bd6502ae6b22f3d62655efa5f973012930f6c8f7a31c70dd7820dcfffd3cb860992781e730d9fa0688cfa6f8496356bf5facd6163a27c45ce66cd1335bdbbe139d4ec2b43bb2a60e12a03cf4ea045523425babcbc0f75f372f53a6ebc6b55f123abe5d4490ba62b10a9c0824a2280be6b8d0d3b67f9a18b8a8d83840c5fe44d9d13b9c99e080c569f379b4c0033cb28a92279718c225ebac555660d044f51e5261aff8bbe9c7a4571d377b111950b8dec8c55baa839b8b6cd2d3598a422e8fe482a1f9f18b5826bc3d84fdcd018394b85a87880c92caebde41be7e325ee598e0ed0d92039f1c6323288f554d5c1a0ee68fc764a37b3045393e500109edb1e1642e0c214f5d447cf938a5ee02699ebd8dab9193f80ea4efe5c5e230acb8b19b09ff21b478be15059aa6d5efa8e9546baab46a9251ed688a30cb143bdd92687d42f55ea112d0cc25c9e7d03ef7c6c551c3c44867b9fe4b4330b49a7223874304b9848396db39db404e173a6d9dd34862840fa6b406be38323b706a9bca9f9e964c2d2faab77399588ecd507e264023c19c53107ee9494f1e229fe44a808a323f863663cc9d1d397dfe39432da73b83b0a892d468727cbc43be9d20953f01b0d3a486152da5862ca258fb38e30ac01035d61c21f5ab45b6dfb51c478e35e567262e242b8b9b1e84fb650ee09f251e4feeed16ef83ef61c3b3a7fbe628a05577b284167db82452897446be681c855e987c2dd5334ed5d24979d9b7a19ab43e4913d815ab24b3cd5b802162e66ac3b05a77ca3b5f86f550f63b945c3bbeaa98b1b44f28c8d26aa1ca3181a4d3bf4e209b451274c599f5ffab358634c7835b8161937352cb9524776086c6bf4f521bb4e1f9ac95a8b77a4dfd80c02aa03e4d951a0bdcfaecb466337ced74be5092ed681d700e69413b9a3de7c4bd5a41fd6b0157edf746d6c5b7e04bf22453cc2f497aa5bb014972ca85145416540b6016412dfe9e6ff2a9ca522849b349800287d3f4e67c969c6f4ea93748d8de5fe494a59b2da1be863937d50e175a54b1fcb092e95db4756ef7601fbf5e52be7ac3c3550fe4fae6e865def4b7597780d2aa5f99b3b3a9415df887185e31d4ef5cf80a13034568313cbe0282b8057e1c5786b4cff765250fdfd0bde410b88dfac0ac3b32213743887eaf44c27bcb634979c8969d4c769e4ef1bdf632a72e654f3eb34bc69977cef88869555d6d3b898ea46c9f6f571a2b41c87246a4d1fe1f44438e683cb63875ad2422f3bce6f310e6aac1d88fa968348f085aac0cd17c7ab79dfda29de07f8d968847b34c75bd6ce8c973183f5a95681b8ada5eaf9f4041430eb1997e96692a43ac4cbd4680aab2e67e49a37b6f76887ab3acc8ffe6b680117f46730c06cd3ecd8503e828902e97fc07c2b3fbd61f3c566c1efdbdfb2ea193afcc9289bef4e74d9baff879382ead580004fd4b0120f8956120f011da246bbaa1af3b62e78c9a35911515b3322cd23d0e56c4e827a0a9e83fd088c6f08fdfc59bc55621c40fa8841b9291dd40f13a804a7db0777d285cd4947e7f6f83f7673aab740ea69d5a265e5d303585332e3cd5300de52811490316da607fecea530e5660c8601ce66499657feb1cd53f4dc1deb7af6ce8506db0faf0868ccf4441b23365accbcd7045baa9e0cb3dfb824689750f144fdc614000a51b0d39217704ce2b53d7638824c6bb06922622e07db5727c1a33705087c7576942ca03162e161e1a0f9df27fc12028a4f8495bd9f3050b740d47a3b675aaff8734d595213d58084b917d1bbd3e1f204c1af9ccdd9c180b10fdec6564119d6302831ccca8c60450d6bb670f0ecb185b0fa27ead66266e19896ac4d4087a18ae159fa622c400fdf6c88cff0a016d788d5351bea2e51bc8788b08e08e486e99404231289aa7ed4e9a59fd2b01b3f52284c1b0ba242eef612e8cd93fbaa20dbc29ec3d571c02de4592e35122cbf251160241f47ce013a9052be3c4ed3a80035408a5df87518877172e1d76e576b651feb103e81e446d82f8ee34f7340cff28d2f44228a9e9f3ad1713a384abf39229f8200e025e09284c4e93411c04ea1a10b871aea77dc155fd272b94bd2c60e858194842bf8daf8381c747ed10289b83c0947a6d6e2c9d2b735740d6560af9e8f75d2fd4e72df8f2ba694274f4eb84edd48827704a28154032dff2cd5509debf795d80d0d1f23bab219021321d50c774291d99fa621ca6e66bf6f3eb38f2f5476830cd5975e1f7382da2a1f4b27fd0cb517e41e50633f370705ca72dea4dad03f12a41f051cd31a1fa91c7dda603eead5394ef291e4c00ef4b205ecd949c7402bd0983db716c38f974bf86022fcaadea58223f9aa1ed4de669aeb7ee45c26cafa185d4ba208bffc952de67abaec90b263fadcc5c884a13eeb446950e949ef3eb9ccdefcc461c49159a18035a16aeaf16921ece02ba62455df77a2377b83f0f509b936f7ed867d7ddbb1f3df288c4fc9b3cc80f96bd607fb3c84807a83d610f1645b6aaba175913384911621980a6e3e531fd3a018641c629ad7fb6c613b42f9f6b7de2adfe2a4d008d8dd203a5f8c293d1d6191c728cf71edc6b0057ba8818d242dee43dd02722142d6fea71310ff0f822b6675f2c4d4b49ca9987b067d7c094304295b027eb58e9fab52cc4b604d56391b29cbce2fa7649a760cd8e221b878668ac6afcbe3f35cbeadd9d0292de04407da3519a185504730c42c90e338045120774bc3856b0f4b97038218a0ed0adb355650afa77b08270cef2ff292e0e253224d9d9a2a54da473b02afda724dcc79aca703022f577049ffc1584d4edcf803b17795082cd398613c7cd1cf4e04065389c43a1b0ed11eba916a17cbfce8f3036296dc8377ae662ec2b25bff9e2c0020fd888674bed90ce5f5b74127b34c6e6867e6ef167e8ef346c9f87fc8e89e983f416e0394f8161f0cc2c3ecdb5671d4b202f4aa4b76cc89bd9d497bf2492cb03c21bcaeb0ece7aa1f1c9040524f218a95b9e1e4cf8b0e33cc9ac151ff00bc9c25748a90c7843deb84487163eb12b752eb670a852079394da01042def421bb8e6ab133663fa9c46df43856e06d08ece1d2f518b4e60bce03039736ff60d1bf030e454b845cb0b2e38623605e4924bc98532281194772ec6988b0bee8142acc559ef3bafa6461f4445e6b2ac2307d7f48fe70efe6ad8c2fa9a5e80cfcd8f93dadd55917a054076426f25b60b09c466d0fbac45fcec52267b2da9a76731bd9834c7b9f67bfd9101ab8050977cd56c6551f8ef7307d978e9ac8fe1eacefe970a29b1445f18e6ef70faa70d5c6ab964b66175e7e7271ee0ca85d034c56ae9f374f9136cafe897734749697db9c9a1c20c6887f44050164e54081daaa5f81d3e706d918023b449d252e718d99980a08eca45987412a99a0044321c82472ad2655a1d0f537b9a312311e0f5f045579b2d011ea21908938a33b45c5fe32ce9fe3ca5b62ebd782f08b38f0a196c152e8e117c1075d3c4fd02e2e0d36a3b0269aed464840dc687fb385e32750addccfbfc75ebbad8b05a2fb8a40665a516e505ea9653cbb0be63850aa49067a13a1b55f6f625d1217ba67afc5c4ee62ac7d38bf368a4ef915e08878e2c77e1a5e733dec8e0d98c6c58ae6abb1f345cf121b1b47abccc6f388ee7f84db7db7fc7f1b2838e41e634e0d98627878e200a3c906dbdba79d31d205baf73cc60f07fd0458267051ab48293d5145b2f0f48e46051107a671570171c48d69ef56f9fc982d360da9825e2c75e42dea21022f6b63bb3d2606ec768e5e76aca2f0ed3c5024a10396bf397dcb73c72a9e85e0d29cdfde4016b1fc6c6df04413d2cf71f573d302295c3eabb06b19963c2725a1d96313e5b6aa6df04429fc61e8dc971301aeba91d5df5e78338b37599ebea007116805f849668b08ae005ed60ed21380c1423deba0946f96ed87e6fe7364da77421b08abc5812c7f01c60a56f4e6f7adad3d7f9c2750fd89a2adbcba7a8adac20122b5689a04090640d71c20005fb5b80b6ad0c6b49883cb5cd2050dade8beadcb271d7c33b7e1fd1b2a94c294ab10a0abd4d6804e7f9c5fdde9e12274da8518eee580222ee582ab0b9f4c357860447a1693dd14e1fb284aa6a651ddc7f2c942453ec6ae5d16634020390aa8ce3d681a2876eac4cf42157f48956f952d0f05437ca5fdfea4c132a5aee42189a667e171ac6c2003c828864100f90dcec8dbf1e11d574d008853961d7afb8394858f370b96f731b862a44ef43d4161aafe08b3d4ec58d23318f7ba4470269330c8fcf04846be12c291f85b38242913c36e496d99b5fc642893c76498bb09b2b7cb620e95955e4fec18df39e626beb790a812ad2671539172ba2cbb022daed43349e982305e404bac7ff698027772cb6f24e3747376a30662ed88dc797f1c3ee137aee5f33eafe19c3655df618c1a32e8e16275173dab15079c6cc88c7f055f548cc309087f30cb788516e69fb3ea9ae4b00b1a2a323c40e78bf93538be6caa0304a", "spend_index": [ 0, 1, 2939854918, 4294967295 ], "result": [ "fcdf47a1ee4ac0d669e3f28b02780f79e19cd82d966bdf50f9b767b76d59c471", "f8fa3225821bd05cb845052d29b83ac971602c314690dde1b28a83dfdb9d475b", "822ab57d856af2294bdb1f4609c36abe15aa2a01038d1ebb1bc6bea6e3bb97b0", "bb3a5942ff153f6f57b3db493e78e3a3e591113a563abbdb18e2bcacef8b3773" ] }, { "desc": { "Inputs": 9, "Outputs": 7, "Witness": true, "Version": 1953367418, "scriptSigs": true }, "hex_tx": "7a056e740001098bcf013900000000000000000000000000000000000000000000000000000000d555310ffd7c01ea056fbf3fa34a33ea5845071d769bacdd9223b15887a365d5735ac9fa2aef798d067e0e48c80a6ce7adec80a6677c0a8fe36d685e7c97bbd10496844d28d72deb185934c6d20c84c5af23ddc9e10bf700b7b46a587c519a097e04ee57ed0d62e1b1a726df811d81d84c4b7726369c79710ceeca98cdd7bca2b37226eb1fd7818346590f2ef5d98d0b789bac830283e70926330912a20309863c3d67345a2dc35c49634df7b32ff3add43ef19b010f59b252bf286b28d91db3c98bfc0afadeacefa97b15f20e9a7b7f5f10e60216b5a2b40e72b2c142dd5cfa6e19c7293dfcd38a944b89fb8168f6bd13fc45d7426685c753613feba034cbcc46d6da0e9da4916bcc68058fcc291f8c68fa4fd07722159ff348c2888a6cb1d45d1de52be4c3ccf22de16fe6a3be6b46a44a5e516de79ea39e00ca62ea08a4b72b7ced5fba7b172b4d58413ac4b298f5eea6ce738721008f3c4baeedfbce01d31c20936b36274677fabe387c973044a927ab0949f1e70dd341a2e010647f519cd8020a8fa998e0da68ccfc000000000000000000000000000000000000000000000000000000003a158ab3fd3b01edcbb535d5b64a7d6996bfe17c58e2a5ebd3ff252642c05e2e1fbafa1d0b66fb4a28a56b02f0d6016643644b5be63eb3a5343c8cbea11710cae3a1eabdf122ac1e567c6b3d415016d06aab5349b0bfc7685956b87e89c7458fbf6b86ed302cff73dea07581398319e35676b7ab00df8b8c7a250fe7dbe0636f45cdf9865da0f36f5c613a60b4805c6cb0a45b3f4955839856f3e34d629eca4620b7095071884f6e07ee83afc2351c9b87073a80e0fe196826626230a61a2d250b4179eac303e627c462daea938c90e0fdc82a2f1620a640e3244f834ec59dad1195ae888c97d6c6028cdbe2ff1e185825d3dbcbc5e3e0e0598d667549041377bce0344ba166f4074168f787ffa1cf1e9ee03bb32382ed2ce2949f7b6ed75959f48acf0a4bdc1b154f580874a78bca650c38b728d19238e69170440273fc405399476b07aa086168c99c000000000000000000000000000000000000000000000000000000002ec4eb64c124b4d540d391e34f4f6a42457d87c5f45bc7f8c1c73bf51d9bd49e0295a19a76f17698ded03f2fc58ea2326fd623e4585843b105f2dd23c5f92cc350628a4bb731951234ce97b2a2b6239696425120c7c79d071b1e12e88394c72c0b47f7ede3283d8620a912909d04ccfc41a4ffbda31d7469fb0076ccbaf359d197a175ecf368ad278f10eb6945842710f816d50ba0ff0dcddfa82b93a926f0b7abf534c162915412eb37a177311ed1b4f3832f8741ddccdba7a6fec008eecf80c915cd7f6f23b893eddbe2905bf300000000000000000000000000000000000000000000000000000000deef88f50a4d1436c03c15c54a01e47ab0a19ce75ac398000000000000000000000000000000000000000000000000000000002c0ad335fd0101d18c5eeba066aed82cf79d250f693e64db9fe9bf370b6c7d4b83a73c61fe3e58dd94960b9c084720c4dbaa8e6f1c6477e341e8fec705f1fead295aba3a39fe8df2ecebedaa5ef3f625b9e09cc81bae99faf232326c4fb9574b4c648916a33ee2a9d513d2c581ab688a5cb2151fef7a1e7ef1efe1969fa86d0564a89396cfbc3410840ba73cf10afcf8603398494cc6238be2dbfcf060a7b80cf8590aa8498486c397e88d947ebe733b1e1473db3c7e35463d43cb926c9e226268a9185e490c39b4f2c595d1146d4545e283807225841a84afc241c1462757fa61f8166141510f6c0dae771ffd5cff4fa63ee57ef9df0e160132a99cbfa560d6f0094fb51db9a58e078c6b5ffbe28cb60000000000000000000000000000000000000000000000000000000043471405fdbb0133f2194de97ea27663309e1972d1124cf6d7529727a99ed9ca9b4c23f190710a5fedf38d07e8b9abe3753ea6559bcfc9ab1778d2640085e78db387400ba692b3a70c84956ac0dbb27a1c5a668a3230323970d19035c28cb05dea6f349e48411f85cdd607654217a3aecb8b5d9d027fe7d52f01b44eddcf4399cd5e62e2eba24eac0324ea405e9571c35b193ee907e45a2d3c4ba062eff6fc3196936a96f7a70a2fc350f72d7d5a0fed32f3222c8a45da5cf37707b3ae37ad0c2948e4510f20e83ddb12ceae3a607c631a82fff8967dadd85efe046fdf51361692a9f3cb0e0226e90309f21c5b76016d9c83c80a290188602ba8d1c85676b03354265148befb04e32737b81b344a0608793c2bb3232d18f560a607e557cbe8336e4aff395892bbf1d459e4ed3c61a57e19ae46849e63d1335ce19b656cfc7b366f89865403bbe44697311623ffb4c4967d190466f5e57d85ad9588a40ea9df468fbeff09bb1b30e77fb12caa074e1deac70d32e51ac56fa80a73b45c94a730cb5399ea80a0aeb6ca1ff84b1be8c6cf5d4ce1f639a26b640d993255a9a40495705af6f08088cfdb902f8a63cfbf1a7d305946704cf51f7328a470ebcab3414201539403560def7d73d885000000000000000000000000000000000000000000000000000000005a17a5aed9e7bfa067da9b2728b085c6698489ac84fce97583234b2bce8b025df43903db6ea89229b14dd458ff28b3ca944c7c03c69de8046dc43b8306c12c7b9d04ffa1b7b46b8bc06fe070433e98f679f4d6102bc804524fb69ca710920443b2eb018ad58c280140e188e7630ecf759e941eddc40cc6509e997876b4cc95d3b93ea694a53f5bf2154e62f45cc7fbc53161012dcf4a36d205137e6669079f24c8fe697ca9bf295190d9fee3c87e57c944a3d7f7967ea26b7d882d08a0af67c84f35f79312d3e65ff491ff8ca48ef9d52bb07d9508d4ec962675ee3f5d51c129e23f69f1eed2000000000000000000000000000000000000000000000000000000004e14f231fd4b01bab43b885e98fa91a306c49a83f2fde5d6b565b2e92115956494dd265dc32297acaa5aea6dbf1c08961484cded9936c3d454e959a1845d12d847c4cc58da82528daed5fd5d36049c38c5197026ebc3b1695c67ffb3946498c85861f7883be6ac36b51ba714f9fc6b128eaa06244f4a5059ec01227a7c96955a2aed854c3cb235b2a0469e3e9141501ed55ffecf01f112c78466578136349e942eb6f49fb7d8a8d02329990ef3b09ae966050ebcffcd18b96e82245a50731d483e31e7aa71d48e114849ea12191dc800189bfb49e1a9dcc7c066ebe4194cc10437b1fe7567fbce122cc5a7802fa2be59ecf276b80c9f736a15a563572ad86ca2e65a5f7db89a8c8386197161a53598d01ba553af7e3e8d4df7525ed51f0329df19bfe09ffc5e61ec8990dba96c0624f171415c31be1b4f22c241782fafb92bc1f3848c6cb62da62e8aa8e84ac189b4f9ee0868a0447d6c93b3df000000000000000000000000000000000000000000000000000000006231097bf5c68f6239ee9ac7b3241cd4e8e035d2eb5c2b47d34e9fb6dbc6f2632e09789715631a0902a22d6634f74de03b1109f9904445293102d332dbba8a33aaedf645aa6c48e180ddace3cd3c1089c4ed30ba45e650cbe0b974e5ab88a18ad86d568cf5e59f28d80a99f352388cdb7184e15b63b5ab596de74592d64136300639e5265f7791d779af16ecfe00d22599e6ad4722aa6064cc44d7300f6da03bbe4cff1d216da1908a6ec573e661feeeeb170ea28076ad16e33e60a9de378120616c2a7d0b86d40aaa6c18fe469bd52ad59c8a49f97cb7db2a7c59ac2338f971621ab2fafb5353002aff8908610d980fe9187de1da45a37c03f90a1754fc07c8870b9417662470c88b09a482877ed9c2f6016dce329daa87cd9a601fd13bb6517470081705ff21c69cc3e052eb9f945ef91b62284d6b1a9145624317542c79dcad22306be86837318d07c97f398f0bda29a6ad0bbb38f52345c92d5ea377b81c8b59cf2f00850ab79dc129885b1acae8388867de3c64aa5fb867c3eca6d9b8e82b750f40a248932e068e2c959bb5ad00ebb5f7ade72ed6e6cb7aaca6af49f20b69acbbbd1feba026730f3e96a57e4a199fcc2bfa1620107f006a3f7852b24b9bbd721adc92f330121dceeed778395cda3102b85f2daaa83ec85fdc422012a0c63d1ab193c9548ff5eada3393d89aa73e02cfcbee0197c47649b55a0f1ba0b53774ea7318f2670920f5a3bb16a2b85cdd41612b7c78514334fe44b732353ce9cc37f0662478269665a3e297ae500f5243190e3d4852aed0f977fd5080a149a6a9ae08c1db7ff2e45fe601994f20bfa7c60c744324b12ba6949474a6eac8fc44af2a8b5319a0736490da32fbff34dd1205519a845bb6d25e1bc7467456615f536e8727d1a7c4658a03c1b779b6fa8774705932fdb86c41d375d9dd4d274a9da287e9345111e2fc912f6ac82b9725be4b1d46998ceef310b364b05a0253354795e276eac0fb44a64f5978f7cf19ddd0918ac5639c85df690673d7b365ef4a438b3a81fea448fee96076571273649a86ef7a5b7766eaa2a072e6ad585564fccbac18d2fbf425e4ce024c2a6518250e84e346a96bf6b6abdc1a66114e7c03dda2bbb47bdc501ef2bfffe4ba69d28df907bb93ef009f77700e96c5e85b788006be37c56c8d4e4a396ff5df743b04e5972125436dda0b85be7933156edcf6ec3bdf9a72a8166305c6f5524dd7931d127470e56ce71327fc7a6abf1e655ac86c01e4240cc0e058b1be9c737afa12033425fef8d3a0858528559071649d47859f00a9015fb0b4eb7b2a2fefcd49f409e89951e3b4494f9a09eb7cc24b9696b71e226cd21cb4a4d80fea507b1f67743ab8f273fd1041f4b4324714aef580f7226529973958f8976560ef81002df6b5e69059d7e452173813a50ad6c1b5701c7ac55bf911cbd8ac29a650ab8dfd5e82d98d3b1d9b4548b1dd82264b246dc6736e242de99b4fdcbdbf2b55b54324a48de99c04ee4ba8c0ae86c3fdbab3cff0a01304f0296f59936178f54aad3d20f9c31fc82c7c9621131cfffa63cdb37852249bb8a2aaf89d8b55039b98a520b912f64bfc77a1f38e1eec65ca12fe2f7735dd12bf66cafb1742a5e32ce5943293ea0ce41261e56cba081dae2055acb248e5980c2c097b5d73886e877c490c6da67865c2d92aeb970cdaec3ec8191b22c69bf6ccce28f7c823428297f010cd4be2d024cbfcfb54e19e7cb70b543b9fdd018e3601f8567d2dc6a9a2f33ecf69db93a1317be2173ea699802907d2a638776c9f696ebd8aa823e733978fc9d3e72cc65c7db25db3bdb93c34ae2afd2e878b40aadab278c890c266108dcc127cc81594c9b1219a50143a2ccdfb1682c930af8d6909da98ac581c7fc09e7f52adfe20fd281422d38f6a167a22ac2eb389432aecffb5f86da603144aab6bae28b05e8f2a795b821d66ce1c306e87a3f6c306ae4c4ab6c7c43c99cdf7723856d43cc06c0c6ed5d7f11942428199d77928db18daca6416af014ea4136da02a8d3cddc24866a82f717ae97ac84588bdf716b59669fb1644a8b91b15ee6e4d27a1956b59ce0bc8e70529df27a965688971ab7f93c43299d0bfcb338550d49a717d58c6ecf0ba6061f55528c842575c8f2aeec23f1f08062fe8d0a40409611fb0280f43acb624e65cb72f8a6b46573ae016a194f92cd29d8620fb51341e716020081459995c6fda388e51ea6f7125d1c94ef66cbeb7237c385ab51a29899e96dd91f24d3f07a28d0375a733636cb71fc329089e1225827d75c1b8261aa583462b92baaeb58cda6c7fac91bcd3bce111a7d6ac21fc571889aa6d70e33e5c2dd5b5c9c8935d646842051496a40f418a660225874c9e9ebf8deb8552cbefcade8e053e8ac92ce39813ccea9d7a06aabc6d12b8efd4b30221de0e41fa3a7414119366edecaaaf5c1b6ac4f54ab5e49263e255fb42f9ab883f2ffd98017270bc88bc9f0833bb4a2f8ced470d5dc0dd1dc065afcd05945057a02b8feb229df5057ece018175b1314d3088de468c9f9d4bf2ef6b6639127ed2f914c108cb1a433719dee25de9bd645981f2c325682fa8ee611812ba947145c522ee8827f7fa866db908f350b52e30188b68629ff877db1bb6227de9fd3d4491d8244972a0cacec3d87fc6f419f8e57fcbf1ef274633b6f888f3a9c172faa5f8a3dba8265ed8da16f9bf5ce6f1bc34d1119d538d8a93b76904084df4de3d37b96682125d52b0ab1827108c779b64198e6576d250e37b9bcbd5af4ea7586068014762345ebbf3a76584a84066bf46f030bfdc08586ce0c124a745fcece664872076377a60aca14cbd48fd6c7a7c93ed1d576304b73e5edc101215336a9cd7381506b5d3d9746fb10c5dbe34c23b9570feb87a67b440f0078e45f58f18f62467c74ac3697a06511372e33360860ad76005cbfd3ff0f0c2a633fa7afd3cb3e988e1895b6d91027a258139eb8e8cb63b5385591872262162742b74cbc04edc14f1d62d67c9391f220931a12f7fa9b9ca7d5777e3b99135bdd430cca745f740000003bc0bada0f096e4c15561f7ce2ecc64717234d8164e14f61404d325e537cdbfd809437ddde0b3d2db9dbe1b0048453513ba0d697212a61cdb642ce60f308c109dacd2a862faac4b8a02b2996954629e6e551f852379e337e3f8f94b08878ab73f235b7de618fbc9891f1a9ccca3e05a177b0fd380404a17f2b6816e7195675490fc179b13b0e59b2355d2b89a7de0191d891e6343bff318d76da2a00c87529ece8751529b5d2ebb3c35539cf61b22027ee31d726ee33d55b1659c4952fca5bd9e9d37637b4f7218e10c78a4d7fbafc2d3d6fb10f5d1a8f9806551df1470752356531e366fa47444846f25f6a51c400e0b025cea081ac0e60ec9efaacaf6ed7bce53924931eef7eef5a326cadf0b8b11b304fbcc79f8da8dfe51c3ca95990062d9608c9d082aa9cbb6723f0f795b354ed37eb515875f8e89b8fd6c68b214e8b866947aceab79cbcb79e44bd46afa10b47a5542263fcbc2f76670475bafbb2b904df2352ffda001c5455c79d6ab4fc7d0fdee9dc187f07a06c50dcaed6b881f35fcc9ef4fa55ffc0bd3e8abbd9b1ebadb84a33d2615debad7e376513f3771e3035b836525032973e3460ced64b42775f0b227a9c8c94af423e6046863bcfea28056be47a0051343517e79383db0cb7b59372368002af6ebf0716ba5f46270f4da955518ec40c92208a152d961b12f56a7afcb81010bf22fff3bd252a51e2cc0ca03a5d5ab0a066d58358fa9b7370d28b4feb95882d9168aa383d0b4268b7fb33220bf1b34e273ac6d9cded7f4fcbae743b0b61a5aaf8103c97f6caca8e6a111a33e92f83cc4eef47f1f93122e0e69bcefe382f98d296082659fd9840ccda3a009df2928f9379e0a6d9faaf6b12151afe6542fd0c84043e8e6119f6fe85f264e6a0663e23a98af8d9d91618f4530f112719bd48dab00ba05fe96e899506f214a3025f9e7c5c91204fc5624216ac03e1e59e613e91434c4258c777bca28f836b457ed3110f09a24951dff70e2e654b232f25f89d2dabfe82b7b1a9f5b855202868b60585742daa4923c12a1aec177f9d5e9503f0e3a9cfabd38c12fa6bb7888892d7dcce2551873ef02fda301c8233340f2af2f4f18547ecf84016cade28842c060a659762867e8a3ab6633416ef03250021fb5fcb9917ae6622108ae2daf6723980f7085f45ca612d0993aee17cbd86e87d980bc746555b5aae1c94801b2e370ed4b18669f225d5f3e3bbae260e15ce1d4d000b431691f67168e68c8495c7a8495727e58493134025337a76b3a5c43ba2a9d42040687b7c89e69d660134afa51ddd4b5aa10b193ff33a7784badd89b6e8c3461c4e45ace4b742576767a7b01872f1d2f4cd1ed81ac921405637dcb69df9d716f8805a68524f66178987ef1d22c737fb6fcb7f69c9f62efa5da3fa4a57c6f31140211a162dfa15c2c9c9bfb66b7d2e4d1ed83ba2ffc77054f4e8f666b002cb3b6b0f392833790a04ebcb5b93e23ca16e10c4a7196e2fd2ee6234288e09f75fdc391a42cd08ae359927c6e59390f037b62d699f6c97160c97f591cfe0aa0c9b3b456a2f255cccb6a2f194ad4b48d402f9282c9ab70a413d70dc68f4579c49d8423330236f4ee0a1c4cab393179abf3fc41402a77dffbd86d3b367c9299894967b1536e8f0173be72b3daa9f3eb7b5fc6d48cad2a51038a52e45ae94cd51dde3c902b896b622727e1208ce5af0e9b8573e5da400ddfc13ce377622a02fdb3010867c1fc45591d3de4f3ff068cd23aa1cadbcc60989b6825f3172464b8fd1a1edb4d8206e7b29cf20c558b35812151a44368f186843cd98536eb3391e32c71683b0e4db1e546a9eb3c0f2923ab74ceee6651ca04f4c92096f885dca0faec18d703da056a88020b60ec41229faa6d3937447abaac80445104b53eec7f6defe7f592f8da374cc0184f374a9124d66c44d472344e9ecad7fa880973ed6b56fbf69dc851ca8723b08b77ed46eb6a1a594a1e52090f481cbdecbfa83af24c4c7f0ca321f4ff3bcf501c8d6d546e98bd7d403a8642dd8f771ca5f9fe077f3b2f0f170edd16159f0563cd992add3f525d454baa3217fa890a760fdf1bbca528236a0f6573ac5871078d7b31497934f86575f2898ef89fa9b6736a3206d39fd08f3719f7b2db2f6f1c494f859051064a3dfd60d6fb2ca5eb78e78d6b1f4320de131c5085f76e568b8ed31cf4284f894c61d3e132f2f41d4b4ca7973a0d0b4bbbbca63de88f54a2a491639cd0578ec20d58872c6d41412c1e5170dfb6f8cb1bf8834521d7e3fdf2ec91698026e55402646e8bddeb0661529787822ed988da572088e23569892d2eee4344d0ef0b0866adcd7ca925edcf09fdc2013bc4ded3f67e787daa64adc519597e194e7ffb72f49f82a2e26c1004abeb55f1cfa97155136f1d7456ed28bc1ebfbe69a11a1b6db5ca902b8f119a87287a7c0dae8ef408418f5ae205c40c4287a09ef1cc75f1dfba156c55ce2feeb6435dcb681c3e82c7033602905d2389d962a467e71546414a05b6b0bfb092d5d9b1c07371a8ac386d4f69d9ba589c1e406018ef5b8391f39c97c3d19ca0de767322fb783ad16c6e1d054fd7ed297c518eaa8a994d937457c5930c40ddd3d5efbf46393fd022da2e21d043f5c168270ce31adcc737db97da32ef103033f2e6dddc8baab30b47f59f18479922ca132605f808029113ee161fe07233cc33e4eb81af221c3afd2585ff08f40b58395cd5946c516035824076debd016ebb68344108cb282303d26dec5f9792c0b991c7a28c6caa971fc1433171b473d9c74322be502332206709b481dde8049a834ef255858a1a90f5512475d8abf3ad0b94146b85d1cfe10e2e90bdd38d035d09a4dfc313b4e8297a66bb116c6ae1c99118306c7a672dbcbc6a060241df912fcae2fcf7f2aeff5ee4e04ab6afd3ef9994d5e97435587cc4f8ecb5e7115a26710e9ceeefec4e87de6f75bbdb9a0a64e582de9299fc04759d70e49e420237f23440e6dcbdeaa70bf6e453b41baf386d62328c9926aae352f415868def8c1f9d25534faa94596ed1644b82ce9092836bfde1281148ca1e36ba8879a414f28d8a0a9907c11d9e01de3390c3b86f97d5b04355fa5e71000473532c17a1e71402e9e17b4e54552115d67203cea6c09aeef06d0d975694e3247b347100cc3c6ed44e79517330cde78b96f6e7c6a44877a96ef46e60164fea3d21f862bec96b5b78505f891bd3e49ef4a5616663ad21ae5f18e55dfcb3903cdccf2033945e67e8c5cb3c20a3b80c8e3860321a6daf65d9ef5ca7671cb585094e2ad30840d6a41f05f285d482ddb334332f4739493643421038fc649b2f6072a8d2a40cb4d4645a2e805b4d2f744ad280c4539ea5c289bf6a5d1a1c8fabda5050cf27595c5ea1db7b2f3045aaa2a356dcded4be22fa05c9a4cd4ab722a2f78baf8b4882322371a16141d9ed8f9473fa74b35a10a168e27f847fc0b30b2e3cc27997bb849aa5e5b34e03477bd30cbc6bae727933e3cb7ddee12e8d9aae7f264c74617a571dfd62018c0211dacdb985870105f1318e4a2a126b5c731ef4cc6ee8818922341d341110789689029deca3d3500d43993f85716dc05bf20bbfc6a73a1f340b96ecf4c7060527a9419b6b7c9df411c2e3622326943998f9f266d1e5245c3553e19ebd72c3eb1b6f59716aa77e68313b08bb1592c474a03c965297a572a6b82cb4806fabc3d1683a7f3116dcbacfbdbaf7342f3e607bc96d3b781c4ab593c8b58e7c4c2b45b91cdb8566b6821191745bc6ba8a2fac339b127a1586ce8776903aed2af57ee65c70dbc6b8734fcfbd7b0a622e662b98714670bde5b3368503db2b4ac5ed62e4a220e5b664b6edc44af2f5aeeff01c6cf0bc98433cacdcc1607cf9aab14425365e6445a18ca9365d0a5598928ec92adcde6c7877b80532b74a5fe02cd924c419f52f528cfc4f3fe109b675e95d07e48aca35af09d8e02a247866cfbcb50f0f85ad5c264e0bef9fc8f97dfc7db26ee7f395378a92e89693937d4281e81466f9652078a0421af5112145aab5f3302a988028a9b559abdb026b79191d14d8d56461ebc1d56f0fefc2f82923b362bb0cc7b5a4f3c7a4b639f298c00378b2e055c4f61826c511e486b1c806408f1dd6a11dd69757db9274d81694ca16f3e8834dfb75f3f206e9127d57d42782f23989f53968038a74737a19e606a1e504a852842a1c9fa8000e606743563e246ff039d335877fe0a7a5ea247cd5a579f375410680e642a7bcea7a88d9", "spend_index": [ 0, 1, 2545058932, 4294967295 ], "result": [ "b21decd167c0c15adf50de7115d216dc4aff160c64cd0908786a1014d90b5aac", "3ba1e67c39d2a00e6cdd4cbe9520944d598dc4f2d2a2d4997eb18e26b910c14d", "59096f4f95ea549c91c386ddae56658b2c66c3620fc7a810c8d422c2c38e5138", "3e0b6fac06cfedd27ffa02acb67384b1a6fc0a0dfc765554d6e6037e1b2fcede" ] }, { "desc": { "Inputs": 6, "Outputs": 5, "Witness": true, "Version": 630616049, "scriptSigs": false }, "hex_tx": "f16f9625000106c4e8960b000000000000000000000000000000000000000000000000000000002b1a1e3d006f32e6b95f1f0fe100000000000000000000000000000000000000000000000000000000023fff7800c8a1eafd82c254a1000000000000000000000000000000000000000000000000000000008758515700bc8a789dc702497600000000000000000000000000000000000000000000000000000000e91c043100c7cbfaa15e276a7b000000000000000000000000000000000000000000000000000000004f115c500087853aabf66003ea000000000000000000000000000000000000000000000000000000004d81ccdd00b03e130405516ed0ef927f181fc84da3c0ec6b2dfd78386c3c30c7f681b1c545aeb71c650485bec2fa9426deda5dcae40f0fc556d8549d354a9df2f94ac0ae5f88a9e49367e76d94c75400ee35de99d9d004b93def51477c61074a123d8da4b8a712371a648761e3f45f04e7cf3dfa8edb9c03bc269c96df0fd9bf8cffadf6e7c0ea74022ef7664cbf0bea7e23255b011c1e38cfd0cf88e237dc48ba755cbed112ff4990aec47d8a96a1e054e3c37dcd7886101a3781c1ff1d69cfc2a0526a82b48f2737c26f16de3fe8b6fdd743bfcc57ec093264f478f1b60574c9371cc85ad8a791e77859cd92e1f29a9205ed1029a01b42eeae74b04e34a699ef29f7ab1302bcfe56767d93c5cd21c82dfc541ce25b32e52d8cbd024a9604f7184ed7690e9fccfbdb9c08c5ca6997e98785dd4c377c8090914d9fd9e4c6ca776712784a1e735766617d8c14cd9f47b6db4be3c8df87af33f2e7d22d687f19b4b1ea7a1fb2924ac07a193c6cd46f7d6317c8565e93e0896984f7826e37bd8c4d2b413b0e8d80fc376bd03a9d42a37dcac66d0d0149415486334d776e9a868ee0e79525e58a7d41be5300dda7efdd2ae7ee2e2449c8775d4de34eb01417273f1fc8abe8d57d8b8b4bb063539179e25e47de6ce5529c25e4daa85f726e2b70c3e031cea4dea81489335bef20573a516bf2ecd7d7a2e2dc9fd7f9e0db328a11576a625135b34314dae5e5910c447c423c6016629fac87e93389b6cc6d8f6bce7cc8ccf32e9f4d69c21761fe806db3a096fb2e1813c514d48b8696966d7c5d802fa319d1de252f37115d972e747a90ae8c38a3b0fafda5e543c600b9a6ee436e1b5feec05704e14c5b452d5996c20d4f1ead545d998d4874b4471b4613818c85657c335d3ebd05c8a5427408c7e10d9b8fb4bbc5c135aaf09ac75246d5ae69bfec927a6431957c5c25b4e6db4b958a7478e556bc4f603bca4d6fa66fdd28536df2cca8377cc554863ee273ad43f6d183bff1ca6f43bb17c62334149b7cc4db172cb9f15a19c10072d1e066f2949bf531961e7a16be98cc922be405b8e45fed5c2daf674ef9a51bfddd784bc092803286ef89d52ea27a6f4b2b1fb590026116d39c976deff446215876c110beee0d844924b417e143390422316026e26036ab67ba0dd5f6def8281af6146f0aab7e0ec62ae5daa701676d67c82c5d686a1cd6f3210d77dae6f42a3ee658ad95c35612748997b60c3b70cf6a4249406e5bef77344455969c45068d1364d215b11dfcb362108ffb19159f46212d5a2fd372633879a39bd16b9ddfbea2c2b12df4b792cecdfffdc6aefbc76f3406645ba75ccec13c8ef382d94a9db9002c1b1b4fd99956de17313ff5268792639d4cf40a122ff5964f5f1aa1f751f0e206e7c36aede988bfc2f94b0dfe180ca1ba462ff5458e12bcf97de50bbf10864f171dd3f1486f3a45fa469af373f409370f946a344249bbeab30409a06bf47f6a2a517314fdbd017aa9806a84afe9df7eced734f5fb11466aeb9f90b56f7282c6cbd538d1ce599140d622452e562053e76786ca50c2ce10adb2caf9fcc424888671d5839eb770e6640255491fcf8e605fcfcb3499354e607c89896b25b4703f99864f2402171ebf2326df584dbeb660eb8b21aceb0fc0c2b40694b0e77566c871095e038d67771be1e6dd45ed89521a41b4581fa836d54d13311372e186f1f44460782fb4f48cc1f413c75ccd6385e8bb698f0bb96ed0d5d11af73ebf6e62921bc42ffe8ad01390ae1c73c4ec7d2e613ea6ae0c275f03d0e98e60adf87bb3c2b76e174f8dd4a3d3bed6c31eb3db2434dde9308c79a1721ce8b386c1315526e33335fbb81582e715e23436173337daabb4d8b39dc0169743142a86272bdba71b310fce565a1063a87556561eeffe05c62d286d3f29c2769ea6517d75cdffeedbeb3d35b18a1785397eb36b04c050827745788ca8e67c4ca259b056d6d18273899d1cb7de2df7234b1b2562e700ece96619d9d4e348c0c2d96e4b0d4f93d9bf35ba394ca622aa83128b0dc0bea4f582e2faf4dc7f6d61aca21f99545386c345918ece8ebaef15f2e995f85b75453def81764fada70d29c4361362ce44e839e38bc619e8fc4ffd5a011389a5de99e441b2fe53b2f2e987c82b99ed01f93d17b9e2c93075710b7eba3339e09486732b6d5e3ac58c4cad4312b4f3c3e48b2d9320603c275eefa8c3023a3934192a813e60925df980525162b493c3787322ad5677ec3847d8ea574599b2a8a328a6869cebd9b66f54a478d31e8e7ae51d3e49ebc0148a5828cf30b234027176f04f105d1d78a0d0618079709808e73b86bd03417bc3525b4951c83e6c535d1b10730ade1935b97ee0ba5006fdd38ffb35151d93221d86ee2dff16c4353b057d5c5ef250b0e6414f1447ce6895c397d933276bfbef4be7ff7f65c3bda5736df98fa7fc34b48e174305970d11cc8ba0866e09e7e8f7d6f1f4c1598f6fc7e1b39c948d99c8b11e5b3228bb65efc9c1b5be37a485864022b7e987398164114475a920b663da3338b5acd34bece3d8d3037809fe55d9ddbb3582a4d01a56249a6049ee854f2bb8452b2294f9709197ff95b158a270b4e2bff7c7debd3a9e40ca669b65416cc6f1bed4c08ddd0b7184615a0cc9a957ba62be95ca7485f594af50efc6a8d2d34cc542558a6d791f14b0f044a7037e948b16ebc392e6425fae93cacbac326bb7ce94880a2d1619148938388f9c47ed37ba12e92cce581049138a9a59dfffbeb7721c84ff404f4c72b6388ebd19bd1fb012e5e0b07b3af2073fe15b477dce1176f13cf35e418bfd7d49c55f6d4ffb937dfc1af832aab6cc36195e7609262c1906a408db52b9bbec2a20874a88f472446c6c9817c039f254b59e501787b46e76a8f1d7b6f22023a864b511c00d7d4ac18c1c41c6c80002fd9a01a804d8ef9ae0b1e5a6af28461709bb34eab4b9999b4a26f50809b900df6e4fd40ecb7544b3c7c7d36fae686a0273bcebc4cc554ae6a411f7f3b4fe7b80e231a39caad54811095f0e80eb6b7e9e6e4af4b706180f0114326635993b39a2e203366d1faaf274496fa53356f358cd3c10cfda67e2abbe15f987285d5fc16d5410f47190fada98c4835b846f30bed526d65e538a66c6d271e5785b683fee5999f09c765cc27c54e7f20ce491919d369f17f4d74be36543ea33d7d03a0bef4e83939334af24968e6df332facdc7cc18b826be57eeda8cd4a8af4c1615ad15f16933ba0f6fba9bbe3d708f250c99c050d7da0973e09c7c7ed9bafab29f0896fb8238d05be5020ca9f7752957fc2c2bebfaddcb50e206baa36bd1ec0d7e1ea86f366b1bbf4d37952863bf58b2be9db7fd75b6192bc08030189877869f181f53da3e8e5a77825cd3127ee3a15ebe0b9921ff2d446ff3ab0987dd3feeded5b28ba6a75324c847c6ebf4c2151381fb7d0a26973b836090c8ef09f7b8b4a629bd69ae469faf3e7dc3ee08adf202d9255f6fd3c9aaa3e3ece03ec10f3accd737f2a5f24483eb722432c411ac33b0c1f001b6e20424f4dab0931ec4700cbf5d55bdd44f9b169b0b4a07a8d8003aa65d3b6ea489dc014f6c0f9747178917c2820d91407ba38e1026624103924ec6177e3236c72d3a46c62d34d0c19b11d85ed4aaf56c7fca4fc2ea0c04c3cc490b492bdcbed3e7adb16a61cc419d9adb3fe02d10f4c0734af90fd39b72d717c8ef6d2e915278a8b0d82c727ed1198b53a0981f4dcf370ec8a0cb9a0e81c8c46bfe1843a8de737410aa44781ffa838eba7a51f5e935f7f18334a30032a105b7c92f19a070912366321602b639ac402e9292701f65045ae24d246864b5b84594668c5f450d19eea704fd8301168f8b6a219e8b7975688dea4b79dedcc8f6d3b5f5eaab93c545aa1dfe102ebb5dbdd802940513c720ac0976743b3f6a55887e2c8f5073abaa81e30e8ab212cc2b988d0851a57f1ba08a204fd1549de594ed0f0e7475dfb6ec57d88229e6f3e4c24e8d87f944c8b9edd6f305c3ceabe569c05ab6d3c95126f95a2297f7494689135e11689c3cb3ef46ad912b681aa8e1bef2c9ae6f2b4a753bbb65bb2d9ed71bbf110675007989eafcf84ea77c3a182c09cea35f8b10ecf9b1c6ecd21d1ef13fc2464bbf933e104bc0390a869bba7425fbd62df1bbe72433553ee6f5bcea01cf168483a7879c523c12cfc0ff3e60eafafb18599155f80856087547af10c44135f867383312f84918bbb23e8bf212420e2f771159e4d7735005082843c1d3be1404d4260583179941821a85d002e955e0bdc669642c5a423db77888016249fbe218d55b8312ff9fc6582b90f204ed6d18e05daa47d74bd59e215a89857790c8fa5ce51af6852f8fdc5efcd5556c99bafbd6b3494f40a100ad373d1d27709aece45a9ed089396422a331fe3e1cdafed115d662616bf5ba7f6f16409a4575785f8cb2d7332d7c3a43d08a4fa1ca686f06ec1ab8528b822b9381abba09148858d6856a3f7d163bd2ade4b7bd7ce144a81e1bbeb694c9906d500bda5d3bf97afadfd90e4262d799f14512cc75f06375d5f5eb8cfab332accc4af481453078270850b4ec9edb4641e9415742a53b8ee4fd06019d5a793b440ba4d6075288d82b842ae6c231c73ee48f8fc1cb829f6afa764b64594fd6a790e1daaec2875c48775382022b7b4e26f67d73ac3d0e35f44d66c83c5f68537ebff9e1f72c847b2584e347faaead6a66644f49aeb4b1fc7cadc77d64c47353b01e078b0602ecc8f59bd66ad2a5a94cf43b38056be6d8ab9c2619f55c87bd06c9c57121bd499ce147878082868bdc47e2e9e692328bfde5ce32b46b7ed4ce8541c88a39a56e7e0af8577348d15e46fc8d74ae4b6c918dc51a0863dd8438efc702725c764e1fbc1cf23cc70b02033dea863637cf6ae9c0ca36c0a77efffdcf1224eef3148a2a3ea5d36d0e318c7a5dc6fff4932f4a5ad146b207a2e217d5cb99fc898815cc2d8ee6c94e838a9b235bc7f6817abdf13bacd83d032c86f3b8ef0531cc3bd92bd65de0c22e4419f85264266051e2811caf4e41ad88f4788e23dd5dbbe2515b9be400fd71010ed5a0dbfa116f50e82374ba2b84c250ec4a79384963218b66da1f33af1378e24bc1db878dc6e10c5c70d7bb307cff4972ead4a61d2613bf7ec6b5289401f9d8b8cc770b90ad895c454dfa4876cd1d7e506fc68551c04697aa3fb29ab065e3206fbf9a80afdcde05add51e1ff5ea00c1c78eac1da84e3d7eeda5e384f10b883d066e7a7767b25db26142d3d8d0438b71475a082c9cf7d8d01d4b71308b4455dbc76705b2eea3fbaeb800f3639e2f69ffe7dad08cbc008a737a0be98c0ce0e6d6a42ebd2fe5f42d2348cc464e0d56db295c813ae3a6ba8bc5589444d25cbb91f2fcb2c50d2e03e6941e61e88f1c6dffc34fe3298072df780384243cc27c95a2aa7de72d321d4b764750219936557abd87b7b2a39d5d33763b9f6567f9ed24eb951beac74cf105d6b61ac94d70bb2c807a3b75fe1ff50d5a381ab676a296012fd5cdc2258a68a49a8ae2b515c4f93191ff3bf0355037ab75b14798ec54125b52654942dab831fa76d82a47ce50e251b82a6a4ca17925ab310fe492107607cb0c765819bad43e09240026ff932c385149b21d1c1559dffedd512c2a0b19ec6a2a1b37412135975ac0428020723950088ac508071e4af80eb96bff1d34a9272803fd360169e10d734e8a70ab7ac002d81118dd34fa4ce154d3e80fe6fd5c1609fed97a6660ab41edc364d02435152986a9935d293f58995a67bf17ec6a7ceeaa804c3e626ff779cbf384f41af72a4f64e8eb451ad6f77f1ba89df42708f57db978a78df819baa62decad76c3b4d90abfec7ab4c9c5c21c6db7825b971d9f4c2edfd4741f7c709b04a63a694d3881a2fc721fc1753a3de2de0e616afeb6426a66654246f70494317cfbb590c0f6409545ff2299d2ec635e552820701bdcbcfa97116bae779c1c5ba922d4614d6f1c57382c6f403e1c9ab1d226f8c112892c27ddd40912adbaac96ee6920d8bca349edd94c565b7eef7770e6354e63e6bf676881b24b5b50729a0c3f44cf9ff1779686c0f9fe2c89f746f0dd3d4d63770bbac847d680eddf2d81cd9f5d758b4469d73e0db38e6bb5ce6b7fec6868ab9d5a3d2235b8058b11e8371878e1fa8e6764b163371f2cd549c475896bb4b9ecb2d70b525fdd968b9d98e56d087d9fe9f584b056f098a65c0ace43f30ab9aba828a912432dc5a60df9c2c8ef5c4edde71d6b73844130434965d239d0328085e3da928f0eb35fcfaaa37037189b09c8ff9375367c5db5c6f130a4f594798671c53bf5a8e975d31d6f2ed8443f357402caffdb157f9050fd3ac530a84f086ff630e4039f9e1003c9530a015b29cfd88499d2f29cf682633c73aacb1b3da3604990ef08d986f7911b92f23423eb5b762c2697f559a5a8b0f12d51", "spend_index": [ 0, 1, 610513232, 4294967295 ], "result": [ "b8c2674bc1d4548662609e349a1ecf62051c325eee442aa92e00cfc07427c5c8", "a860261a7f38b0ab5fd7bd9b9ea5a970dc25b9bdf7706c3dff60802bdb0d69c0", "0447956b7c977512ed421e483dde6d916cb3e6932cc0c46adb9276d73517c84b", "648f6285ea779c7305f3de17c8bb329fb89716855eed576d1420654b262b2d9e" ] }, { "desc": { "Inputs": 7, "Outputs": 4, "Witness": false, "Version": 1680436768, "scriptSigs": true }, "hex_tx": "206e296407d438dbfb000000000000000000000000000000000000000000000000000000008d78eed6fde501f48b577503b35b028206809323b7198b8d731b93b79a5aa133c23bed43460b9f95b3ce5b8a990d3bfaba0b89cb471379f065cbedd9f3bd3008b96139003e82aa700236cb95591e86551c895eb35fc6fec035006c059487ae12401dc194515a83255ea54ea0083477e7f569aeff555858287d30295d361cb03c5c2d37f68909b571b5b2ecb29ea966ffb85a69432992eeab288120b6b0139497c1d6341911fc3df5f0e914a86c8375f78670ae69106e6f144ff35eef7cd840d6d03224af060c5909427c1549fa6b1270db86fe79a4d13cadd7c77ca30512bb18f63d9567f05b7e03055dd716732669b808ca2abe4d0ac6e583ba23e8f9508d629f71652b5be7e8d717dbb8f0b4cd91c97538e187a6f920a252eda4c1f5b96c44c189ba9fbec3c7016b1414bce1af8f05002eaf384c4b046f52b4f38461760261e1d747437583d804c9eac273f375444e955383c0fb914e1e85eb09f883da326f865abfca714b6013e8790f2c9a9732781b2d3ddf9b1a9ccabaa31b02b0644489800b6472b7df991a2d07d18b9fd09f7844274137ea612e9d41ab5cfe8b639c344daed18db26a04f2692c5ee90098e1acfef7f4e73b8cd3bbd4c88c252f02858f43844d4dc564817a35a9523defd41ca995d198ea29e8aad498b8aec3a257d88c76694a92ff7bf1845b260387a2620c4092df1ed20000000000000000000000000000000000000000000000000000000008cae535230e35061fae2856f238646642efbe966618520f45ed8b9c1b286ae4b7e1329ac914260a7f151eb0d0521d1400000000000000000000000000000000000000000000000000000000b749d8fafd5901c299355f926b1694a1ab345d44fed8da1a5eb67df88cc11cf9acbc3ee7e821dafb2b21a4763b1c8910bca006f499db09ebd90221d036e6d09643a06247a88e6ddedff4c6d42af78152f4c3bb35e4b5eb6f11b9b26a1abccbe926c0107bbf0067cc7c82e2de639fc2c927171798a5ef1276f316c800f8e3a2ddd7b2a1d10b388b45ba6b56d0700d51ec680f796572922d3a303ec9b7d12b3abdf2f3f7d500c6d1f120b6e073d5c2c69fdc78352259a25efae6f5a13bed818507c50120f4892c5e6d5dc2e11ac6e52581079a66fd62f83e91c82c8655d27323e6a945b576322a173f9e2d1acdb2b032c378f24cb0d1fc20bb44ad5ea1aa7712a50cca3147578df58185e002564708fdf3ca635d742f811fbd9780f4b2900657ff96e842173eff864576c23d9dfcedfee2d5826b8e4881ae39a81712b34ce0d18aa64ac075700ccf16a06a85183e1ca36036432978187fbcb83b58720b1696d197b0e8472cd238d8180000000000000000000000000000000000000000000000000000000097e6255dfd7401fa957a082e9495119fec440b03131638f0ee91c9f4a05d918a96dd588e818ee4a8c287fd2aba49fa4f658410813a42024e302708f185aafe87183b08fd36d40257db19fc4ffed1521e018a845c8f89f51e7972ca7e98ab8d401308f5b4aef15168eb9a4e72dd27c836aca7512a5ed1eaa7b01549914b128afbaf8c43d40e598657dc42b73de1134e1eeaf60590ba2ccad9e2bc8918783d262394e5da24157b648f0bc12d0b05312450f93ae2f5c13ebbdde8910b3718786d339718ffdabf96ee4294f6157679806ee824a0ea6135ed285fd7decd81ed64463ed2d5e962c4e4d35b4942a1fc796df8d127f6e81b646eaa2ccf34b7c9a9e7db4938338b40ac0fb9b318ac0fe3aeac28a95e1fdfae2bf901ad71dd78050260939a30dc4d4c1c70d589027ecdb83163c75daeddc3578d72e94c8e40ec158072d2786c21c8f060cc876316e1abc51d9d1bdfb0f50b70350b63a3549f919f08b6ae614dc7915dffc029e602dec03b56fc74cc79316752e1201af171840cad2e8a3d62f16647000000000000000000000000000000000000000000000000000000005fef348cfbf8ddfd14a1d50fc4712872f54ff256923f6a60b0b8b3e3ebf922e0a782162ad430f0238b1ac74bd0df25355fbbc7f4444f4d63f8b3d9c1e4bd0ebb4ab8647a73a3a399144619c6c5b94d311fb2fe8a2c08a0b67ddc713bcead78d0836ee8dff4d45065e8bb2f10728049b37d16317d3e680ffc3868cc1115e3487cc3c5cc399283782eba958e49fcc6f46290b71ddd5a78f3afef988e81bf9df069e648506b374a0363976167c8c32a2c7afc96e5cfd4dc00280eba34ca793880bcaa32591c458999a7942035907a8b6fa75d8712634fd86e2951baa5a1711ddf66304d40dc264422989d7f900254507f5a77d50d0f3a472a62e5608d835c510ba1e0614208be966b270000000000000000000000000000000000000000000000000000000051d91a6300b52ac7197f6aaa6f00000000000000000000000000000000000000000000000000000000ab3dbfe0010ca1f898b70432ed23ce66f7d23ec864831ba1a846f6da004e9e0ce5a1ba0f63506e3d163c543382300eb4f61c3a670bfd3cb3062e48be9c4742edd8edceb88c5b6b5f69160b199b3b21b655adbff63881325f4198480ea355edf71c7cb7f728d99ff1f0c580682d21f9516087c87f667c88de87c5004d8237140c1a0fcb1c37c4f273c2f2a7a09c5539c78db621296ef6b1eb31f00e4f3f150b65fd14fe8ebdbc552dc07edf24350ca1f4d68fa286625f45036b9b9a8ff42ab65b99f4ce76df1e2837409b8dc2767bc652d656ba3d191aa00e64be907cfa43962d93036446c817419f6bcfaeff696d58ca608989e1a3bc7ca5852277179093ac0b779ca9783d16c8e43a8c5b7a6a2d6545fafd28eeb98c0161ae94e0ca8f9cfcc97b1fca8debd3f50d89a237b79ccad84a7dbfe2aee692714d786208ede0be7db771839125aaf02b92db0167635d9ae671183e04d7b65ad00b4d8a04be904adad6092a7c40902b3cfc8acf018c43eb004e06a5812880b2f9bd5ffbb026820442f8cae0ae3a37daffbd9f46e28354324341cd7711debf5fc6559f79cf08f4e3b17dd6f24a1b201f1a6b7cccb73973d43e49ddec2f805cc82322800378dc0ac4c1bb3370c3c5dead353392b6a28fce714be2f199428940ff5c36dca16c83df719a321c224bfcee8dd44d350a1dde8f28d5bde147682a1c2007700fbb74bb5468345de4be0038928e46095b77d661d3f043280fe4ec12bde28ec80cddff8390254dfeda56b469b115d69c3d436a4157bd74d156bbaa1260c7617b84ef7ca3452f4c42fb0f97b7f08360a045392c5fb25c655c9846002ec5361249d67f977c152e32958e0cdaafce59b8fb2db49d969b1f579e9b27294e39af7d42d790eb8ea8a3820e297de620e77dc85679cfcc8cb9a19e1bf9ffbaee0219986aaab28782a5d454ef9d2fab7f20515f4e256fa0bd5e6aa691adb1260454999818a428d99446929df799af5f1537d222a5726d285d4fa7418dab2fd667419acce176fe0ae2be3c11c403dd669091175b2399fc56b77369a5a96f4b6a45f8c2ba5abdf7c03b3410d1a4a7107798fc0aad0558adaf464991f32c3f97328f0ab9d30bb7e1ced023312ec79b08ae0d0fdca0ea7ad81ebd9384fb6ebdb8e14ae73fb289c574c1d0d8646d68925bbbb264468bcbda53d10b06effcd364e097", "spend_index": [ 0, 1, 1976281, 4294967295 ], "result": [ "0257d88b3cbede09ba92c5700e93c7296b52eae72f3adf01d06d80bf88fcbc94", "03ac0c3bcd9354831c7615686290c172d87bd2789d23dca1a7b9e22d056f7629", "085b051e1d33e462e14a21602dd67374660bc3423c83eb2bef7f8abb59531d23", "4371e62d4ad87e48e7c24c3c51a98c88c430df56b1cdcaf04b31049e59a34b0b" ] }, { "desc": { "Inputs": 4, "Outputs": 9, "Witness": false, "Version": 950103983, "scriptSigs": false }, "hex_tx": "af6fa138040b6b6292000000000000000000000000000000000000000000000000000000001b87bfd700ab3ac83175fa99a200000000000000000000000000000000000000000000000000000000b565e13c007fc58c1275c65456000000000000000000000000000000000000000000000000000000004057a3dd0041bdfc854306659a000000000000000000000000000000000000000000000000000000003cbdb3ec00d93c4e9f09e3682dad388aff31c8f36c73a460087cf5cdbc12e40ae50a4e82caa1fb397413688766ec4c8f55c19626f25570d38773dbe49dc155f5c322f7255805d3b5897462d88f6e9699d7d84217c695bc3aae2240c83eef904d5aac62b34277700df977dfc0e7e1ea82f89856dd062e1b2f557f2e1d7e1b8de18db4734173a0a48ff259a2580f6ff0d33ab6adde19663d052625b6df5b502ccf630fdb6fbb14331b1d129546478302462681dca5b90def6af819f797f2bd49ce6203f6d9f9b790cbf99d9084d6182e053ce81c38d186b33a889d2da3664638eea3b73ac8d42372d1821fe24ec2f3c687644391304f146325c17f459742387e4bf571a27523dcbb12d07b2c8021755618625e8b88c4e482993686a1e0d1b2287adf16739481fbf7b623a497fc4dede419466fd6810a1d31737cb186abb3b4fc163df1a7d12e59358d1be3eff1d19af367581775fe854c653f00dfbb9f6c23606807ea2cacfaffef8a1805cd3f77a96e784e89db1df038ed5858b34f1da70be1faa3ba6ea57341a683b19d2de28e9b893d11699b0051b909d361c45c9c159d84e2dc22c95b224eecaf814d89b00d728ba0ad881f7dc842a240fb9d24d48cc2bdfe954f821e54977787e8f9b5117b26ce554537582a4ad824b550a34c6e91ffd421446dbbb7ee3ea648c7a8803165b81198b1363f9199a3923380609fc18be02ae6e0924e70b844a917ee65f7300227d67e1505d401e614802e1c3cc238b1eb81d6c63bd358f9248ae0ace89f818792c861989584c2873e0a54a3f2049dacee4ab1ebf0f328943e64d43c37e33966c74f15cb87c38411b9f5ca9e0fb6df06d7d75f50373d0df1d45b8f452235a6932073d87db92ad4abf2c971decec7942e0771cf4dacb1422bc8c59d705a15c1b6608e0f042decbd74ea89c881c2acba7c82d419360cff319155ea28037a9e9560512d640dab6af8f795b4580cb8fdf0adfc5c86c9c0b517f06fa48c468316ffb388bea39404147681106dafa1f551cd4dc50dbb0bf0c8acd4f4360ee36f5f0e85e80e591271e5baf94ef4c73cdacca9775a0421caaa130d05023d9d234fc0ad52962ed462c9f462fad446c27af24df2e9a8eab5032ed8a7635d6c20638c47d602a0ebd123d9fc7bc89283bd7ef18fe9365cd6da2c653f42c451716627bb1ba7bc8a909e3b9b4854f13ec801d976ba8dcfd629691b588c7909248870772265bad8a4b448605d4a6aaf417a6f513d8e1390afcd111bfe298bee9fcddabd29844dd802cabd53de94f679d9edf598923bb36bf2e78b8f208a82d2191f4ae768d2ee3599f9629d5a8ba23c696e1b96a173828478f7ff09bdbdcfe6707ee0721ddb15b1da9d732702a6bff634940c7fddc5c2cfe2b982c57184c4d8edebc86b84e342d9cbeb2357d21701956fc0f6ccadf87c1e0d5806f7ef10156ecee393c89d322a7b9eca24a360e72ad335db72696f80a37f91a771e4458613c4b761c855ae8305ac7a6f0f79c886222fc148779c93ed55603ce3de2a5e7fd33226b96b3988ad35dc6f6a3d59840c2708ceddffee02f3b56dd112692d863ccca02b3e06c1ac331e6da90f1a1b186c708dac6611df431bf1db9c63e773535f643d571848229379ba0f5dcd592ba21fed529f6e28489fcb8cad98b75bf131b8a01569a3ce2a31415f9ae2e6b1b6a871b1fac28c8b1369ade9f230cdf6569b1e41f2b10ce3b31d0e5bbb16e6d2ac517534b7dbd5b61d0d9eb4c7393c19eab908ba7e8b36918f4b9b4db3cf90357c735cd57c1e3375c88554059582a77eb62985ae3a85ad8e51cd8f696a7750f2e983b0ad6610815ab81ac1f917884ca4e52a5f869ee0fdecf50f61dc154426f137443673f94864d2d63017aaa4fb6e349b260a2084d9609e5e765a27a9d11a49f4aad6205e497fde446129126ff6e6b56922dfe564876cb6da3f303907d76a28210a73bf6acbc41cd04ed13a157e0aa6774fd8e52d4c64578371f0c04ae3902a691b8cd208f4e9ef0864ff94a5f931a6c814fd409993162d6a5a371463e86edcbdf8fcb25ab537a93a3537988e85a756858bafa0e11b8b0453c80c34a0274c631336d24e8d3f57fe9539dc710312643957921377e906e1fa14c1591f98600a673602f3decf2869c5f96e96568574031ac58acc342f60b8bd61d1d5f2c1eef794e1561e6e0d180702f05d0aecc55c2524507b5cdfa1391a80904f72f65b814c206240e5c792ce066e8525f8ce59d23cf022563b661de18ac59fdf8e1539b2987142255bd67a7e1eb6d0a9cf6b84f16f9fe965d22d9d770ca7ebae7fdfb34a232124c972a13bf82de56a54e1f90245b6f4405ff4ae51a139aa26cdb4434909f691d92219413b440d0f4a03c8ee5a687612d54d13fd67d1e034d52b69784e3f4e2167d2954ff67d9bf1beb6f3bce0a08d5c8d93bc4970a8d9d297b0fcad08c1184384a09ada4d263a7a4bc7e9fe40126019bd7cd22ada58d96534e4fb5c27964e8d0fb564413652416d60db4bf8c1e0c97f45bc175a832625a87c5c5be81a06669f0b560de7ce76d6597ddca1f8b5aaf26c392ce1b966b661ffc19a8005d74c18fb8cee5caa86faec3c381823ca2236177b14e4bc1bdd44f8a032877a78555aa8f1e59e540e708229cb3dbb305007b5a413d7f4585fd2be77", "spend_index": [ 0, 1, 1718455096, 4294967295 ], "result": [ "e3ebc01ab7898e0d00c74138a301aa044ff63406ff2f367a156ad55ebfe6d7c4", "4e0ebdc12eb7f1792a67c6ada5542b98a2fbe0b0e38c65f1ae70fff4b6e3bfac", "4a2e99bdd2746172270885d65bcb4568970c901328a1ac3304833faa79298991", "8c54de20a56dc2c75f8f660b8fb018078e13662a9301e1e8a9e1bc9a0f0e721f" ] }, { "desc": { "Inputs": 2, "Outputs": 2, "Witness": false, "Version": 1586157097, "scriptSigs": true }, "hex_tx": "29d68a5e02411bfbd90000000000000000000000000000000000000000000000000000000030be800f00b25eac490c0c0530000000000000000000000000000000000000000000000000000000001fa4d1c8b6cdee099d092f7d946b9d148e926825e4679e07b0d4140d03e9859bd32c1a114029fdd03acfc9e06f885e011c1cd05db51da8d749a7177e0cd1e63d8313bd283acdc936feb55b92fb85d810c9bc31f0cae6e05c829e8e21c9cfb9926b81365955a200ad67254dcd4e63a912ce299edea17632dc03cb74762498082be8511b663d7faf3f0082f888ec42b16d059b29e15d1b45452073cf670792399e87e7bb05ba46116d587adc6d28398642c551ee3509544455fed8533a77b6c40270a6aaf306437c7cc8431a2f8ae89088298f2c16e31d520b7ee58d598ad484cd0856bf7b0b402e5187d800089c19d9b32de970883542e538368825c5ce0f8094025740735050d5cf021f99236ed3a7493f3889abb2b2022d5e549ce675553af4226b71d326923c985f2a8ee829c0d76f7b72d5b46598234e940e78144d3f8283c93df60bc1b6512fd9d86c7bbd163cac7cbc548fbb748277ae932021f05d22f189a71e7f3a7f7b2cd7f5188ea388b33bc132b9334381a1bba098947cae20e9463592946df02e45498a327fd722fc5a5be5d02335bf26b3e64fc88462087b70df7806e6e95dc2a7fbd8f4734d82b39423c9b2e2e30cc1a5071b21268624e7e514c3e05de40dbfcde771ca7dfb51dee5d89bad14e56b057c9c252c02b8d131371d66ebd2de85b1e83a712b06f21b1159eeb3ab27a4ba3506d0d999456a5e5f2b5fa7b4f2384f2e66424da31c1cb882c0374fe1a14325babaefeb866a82da2866e0af202af0be768d6ff432a5765e2d38f58df4e5ca6d71dff7090180abd43eea4e0a4475a7a9ad2c7fc16aaadc8fd3837858ab5c33d855e264b83de5ab8995471dd27a5fe8b858", "spend_index": [ 0, 1, 488532427, 4294967295 ], "result": [ "511c1af7d5757ae5003bc2a03fd3730b87de910bd3f92d4263c57aff3e62141d", "4699fcfb1fc34fbea6619c9f1c07619a0d4269953d8fbd638d58492ab55e4558", "8c92f14c5b5cef4177a2b0a19ef4bb320e8f0c09c63cd1b8dd4b902065f5bf1f", "50f7f44aa75644e6fbcad666a8b7010096fac5a325b764185356eb4536bf9b4e" ] }, { "desc": { "Inputs": 10, "Outputs": 3, "Witness": false, "Version": 1533286556, "scriptSigs": false }, "hex_tx": "9c18645b0a724c895600000000000000000000000000000000000000000000000000000000e3a813a4001825b82541fd254a0000000000000000000000000000000000000000000000000000000017d9bb5800f36b8312fd3445a90000000000000000000000000000000000000000000000000000000015bb76970047c67f8649de677e0000000000000000000000000000000000000000000000000000000095fd92ab0052e4e5a60612c9dd00000000000000000000000000000000000000000000000000000000c414d5f3000627a6afc3d86094000000000000000000000000000000000000000000000000000000002b12c172009ede9e0076466cad00000000000000000000000000000000000000000000000000000000596d0f0b00566218498dbbd45e000000000000000000000000000000000000000000000000000000007beb01e7003bf7319bc6abdfbf0000000000000000000000000000000000000000000000000000000003086f11008d331294fa7246ed0000000000000000000000000000000000000000000000000000000038ac0ae0002eb27611031bcc3774906c3e08c88b5d21712b17491cdfe047fa41792d82f2240ed56ca69bdc91cb9d2253ea6bb7fa58721106595a14afe68777034b97aef9da1b2ad61e89bf0dbc7e099772c98733df891f0c8ea54f0e18b048fb92fb09cee8c8db12fed33ce9ec4419c210ad55b3ffe3ae78c58674da35a1fe11ceeba8894d07916e8c954e75d503e682d75b727eb97397c4484ddd1b1ac1687d312bfd7b782a175d54bd72c03c7d9f4c96d5e92788531026afefda23033849786507e380573d748e051b7c20eb351ba18327bde4eaaed4581f45fbee6b296e6ff70841c82325cbd9993916e0fc9a13773bf56a6d474b4030255d81a98dff2add45a62d087b6a3fe3beb5f98404fe2a0fec6e02a0ff9fe2882a1f6d0a071010f874d453a681523e7c5af75f01fe41edab2752a933d2c9aa6d21f9e444a81fa20137ec17fe835e2ef154ea09b70690251b474c451a98e2e0479824f2fbad05798d254d61a9276869910844a343d7c2b6052e8c7bc83920b8fbbdbac71073e2e0331c74dc0711a98da61f89c09c9f2c032b0b651e4adffdccb815bee12be6ad65fa09b3d506c01484b2fdad8378806dd186b1a15c6bc8f2285bb100c9e8cb92954902abe937185c26095b8e83f07f0fbdad0241305d5f9d7fcb9139b78f2eec323aa6c3a6b985d13a0856d815701380628fe00dc33714646b0747b33e1798ecb9c2c86080c98614890853fc6f2bd5222eadfa8772dfed788ca957e263ad79543f3ff445928517ea74bf4d940dcd3f3ade13be1610e95c829ef0d321e10e74d4870b3ce9631a3df823c3c77f3da05e3459905521459e56f51b24e1d6ef84e8c7d577c33a9a0af562346e146d209bf30748646d0e93253233cac718a78e861ec7573b9a", "spend_index": [ 0, 1, 3984766173, 4294967295 ], "result": [ "dcd0a0e12591c98a2d6a8881c7a303d9a0107570f391206e6a691be2832bf4af", "09a35802c10aabbcf77dae06741f299bc2f93ca5f25977c83ed6a7d192cbb1bf", "9d47029c60a2d62dea9a544428c76c2751a966454d2098b6607356a17c43c52c", "8fe316a21ed6c595b49766a57574a1bb2c00a0c80a8ae50e71878e48133ae35f" ] }, { "desc": { "Inputs": 5, "Outputs": 1, "Witness": false, "Version": -1046185967, "scriptSigs": true }, "hex_tx": "1178a4c105c301ece100000000000000000000000000000000000000000000000000000000d721b701d934658ba935670869b99e74e137856c6665b704bfbbc3862ea142f2d79c4122ecd05eb4396928ded3430de337873293fa17e094f4d8448a497e86ed07f4f6eebfe0b504b9f0d9bdf0f69ce456aa44e0c557d955f6620dd16b66775e59e8fd6b020f617ac6e68d3e97200c2802b98b302e27027330ad80e19121204a3d94714b122ccde996519afe725cc1e42df805c8e7574ad1f22ce770974957696f4bd5617e1b988d7c45296b8eae5aa2ec6154bce5fe68ef98935594bee11994f9ca98162dcaa7dfe9f83636eb3e4e949443051d46170e324d4ebb015db901a4e6fa2d94d6ff00000000000000000000000000000000000000000000000000000000944fd534689d714e39b73e63bcc0ed267209de8654f17acd985cea178682a69d6f3e0388f49ad04343de07100e4a55fab139497f484a0ef432b02ac4aa15ff9af6a79c11e6576097fe0b5a527fb7de2730180ca5ec0a685ba00400cd6055fe18c0fd3bfedef32a3fc2930b7d477c2c228e26c71067000000000000000000000000000000000000000000000000000000004fb2ca0acf406ea8146daca89cb2329113acabcb1b1353bb26f791f8e660cddbbdea6695ea5ad6c2ac5429b96a4295d230f458af28edbf7f802e4fc0347c529006ff619457bef327dcc8f14b1a703f8cfeee855243a555fc884e7b42f1914c3413bfd04e9851e75e69a013b7ae527cc09eb38e99a9969252fc5132c6192a50c6938141c4e1d13dce8f5993815ce71a60ea69c79486e6edc94c12a9319b39818285740c4c4c4bbdd0780854e61ed2156b0b9c3539bb73b5a94609875aaa141c0d2b45f3c80b04949051bfb9c3f4c672d55a4f440a38464b525778e5500000000000000000000000000000000000000000000000000000000061775380fda10154519ebb2b3f6c9329042bf5b66e15fb04a7378fcdff6dd433b877fa30d197c16a34f1e81436100e40ba642d3705bba492c26d941243536aa945ee6227fa884286cd16b884a810f1935edb0378eca6be19e1f307eb4c25ae28e483eb3c17eb6646e574c90c0a26144b028dd12b311f366f3e5ce59f203a958539af8895fe980ad89458ac205cf5ee2d6719abf1ffb5aeb699bd85146056b7e0e4db8af5fef6086a225c6e88070cbd40576cdc39c9871c7a0bbebbe3883786ce480f5dabb2148b719dba4c54ca00b81cf4b686f140e02cf0ae365b697596002c2b01513914c5bc42f428056c6739c682737884a34782051ae0ce2a85a8e78fa1cbd42027abb7ad79ba5a8aaac04688297addd57062231eae11afe12f43a76c5df5b6dd2b19cd755de1d1112985ad1a7a3a4ce6b13894f51e67f169318d982386b66f10ff9c76f81aadd2815fd8f0f1c33413c2b039260efbcd68257b08ac5a469e8c2731aa7b91c917d9933d24f55c4f568e74eef02108397515d71ee8c4c927e949ba54cf3b29708491a2f77f9e59b232193a22a5d87a86bd47e3f6ffcc47452a47bbbecfd307bee555d58e0a7dc7660000000000000000000000000000000000000000000000000000000074ef9b6e04357b907fc2deda330123eb094c8e8cf937c881fa5c430bcb5330255390144b8bb4870fb37411ea3fa4f154e0f91e09a1cfc9d7d1d6873204ac700fe3a9666995c60afa111d67e1dcd83a687544cf2c9e644d7b34bdf57366e9ab421bb06c43688f4d1c61fc3715ee013ca7ce0d1fcf92200efc00434ff1be2d1e649149c3fb0e1c2234615260775a6074157dea4d1e93b8b816882bdc6ac9ee8b37bd9eed50984814e8b8aa86f16e08868680e370941b1692b7cb049f70b0216d689dfd61da7584d1a0cbe87dbf482dd896bbf1911cb370f50e4786a61964503d465ae85e", "spend_index": [ 0, 1, 1911039603, 4294967295 ], "result": [ "ee6c9fa448ddd575489c1c6605fbb7074c8e4221b064d37ab411e9d40e9b3958", "824e100dea2db58dbe671ed74407eec9457a11f9f1636def3eb7221133cbb77b", "37ea4a8607541460dec37f853aef9bcd1907f35222beeb840fe5fc60c0ff153f", "02b79621a4fc7bb9dd954bb7529425f3bfc3e30fb08a9e5919eaf0dbfbf51545" ] }, { "desc": { "Inputs": 10, "Outputs": 7, "Witness": false, "Version": -2076899950, "scriptSigs": false }, "hex_tx": "920535840a59faca3400000000000000000000000000000000000000000000000000000000a9e8d77200c50866e0c98126000000000000000000000000000000000000000000000000000000000008b19e6900da1887d7aa74b60b00000000000000000000000000000000000000000000000000000000d17f9d8e000d3461130ea4488b00000000000000000000000000000000000000000000000000000000692258aa0097388421766867910000000000000000000000000000000000000000000000000000000022e24c1400e158e46061fe236e000000000000000000000000000000000000000000000000000000000f35b41600425339c4ad6e6d2200000000000000000000000000000000000000000000000000000000e71b5205005eb69b91b3446cef00000000000000000000000000000000000000000000000000000000fa113b30001c1a31129bddb27d00000000000000000000000000000000000000000000000000000000af19a36e0084d7798bbbcff00d000000000000000000000000000000000000000000000000000000001bf81c940008ea6d2007a78de3263d376b5bc87810e8b9bdf0871b5316a7e3ef908fcf6da2f6a2b9f424f903067212284e13c7484f0393dc9bee801f78c18528ffd4717f5af3c481622baad5f08d6438da707cfd0ff5ce38f2900a97816c410d7f03a209670a248b882e20030b5da281c886fb5e2cf5977ad0aa348d7eed405783d49088be3267e13d0c8496b3da2f17b50a19b6acc5e4286caecd30e6b4b8da7177923b41e5a55372260fd7e1b7576cb2606f24333db27a063545f0272b7d5e1ed92040bfec70cb08a21dec01e2c978a4d56ba03255009476a1157ff8d4e465ba1300c8357e6ea7606fef3e35d16fbf5aa62e00d39f17ecfaa17ea3817d408350504dafe86a8438aad424438619ef56bdb49c9c75b16d2b9314c478579556581289453e501496b71a2ac5bcc11e897838bba0b43b782676a1f623be98ed73be1dd78e6c0310cd9b2ce30412880eed4c7ab384f49c809b508153e895a2a74d23f318dd406d402d1b1a9a895e8196ff5bd70407bf13ed8d0f26806391e25300dfaeca3e9f699873cd1798f07a73db45877dd40866eeb01bb61cc9b14aa35c9443a1c5040068d27591d48bd1bd19ed0e35220e312ec8d2e86f19d247cbe312604d1085744923d1dadddaa82518e29bb62b8a9675fe68380e65c456ab124eeaafccf1be563c928b44a29cded0976804a71528984a3094a61100bcc4bf8a06507a2cf699d751c48342c8b1ee71a629281d029e7947a59762dea77b82f52988c418890d2b46c4882d95e820d902d28430d6c75d712e3af9cfc3a4a38b750893687ec2704dd52974adbe611aae0d59eeb5453bdff8065a663ac66a08cece2637773cf8cec3e26ffeba500eab639b254cfbab32f0e1c224f88ac82d742e518f0e0fa9652e1ac2c278c88ef2ffea2c424e534ca1b6c2f1415e9c28435b3d32027eb4c7004db3fe710d99ccf7e1118e67a40ae1808e00126daca873e14e729312b1ac6f656cfa0428551aea725b4d73c6de450abfc540eb757d8faa56e7dfb2031cb25be2c43a50b73984ab718843621bffb4e46ac17dbcdb88fe92307dfb25b68943a79352bcf697c4b3834aab77a8bccfe5c82427d1bf527bd948a526217b8795494ac40eb7779e952686a98c7690822648f5e51ef5b930e0ff50e2c7b12386ae7cbce573ec0c0424cd7a415e5abdbefd943c750077a2e0dd4dc8db3cd669e67d95ced6ce4aeeec807dd04adc444d16cf798201c4978e9e5d31025e5879f64c7442d69599fbbe5c5ddca1ca6d1536e0e720659e94abc72e356b0aa3252fe09ad38139e3424bcdd515647877353adae83b439b29581c6e54c8fd012f3cc61909200781e2c4286fd38cdb551202e8d3a52730424d85cb006507f405162d1c66835ed25bee89122fe3acd80e765e3b0e2664dd769ff0ccfb3cc4e0adcfc9973c4b5950bbeff23d1bd174819a2a05aece181020baf02cf9b354956864596723c4c5637bb1f936c5b8d8de9344c8d733db7e9660e806a2f05ff14e92a8bcbe8d5f23c7749b4e96328f30258c0a6177a45a78da8521cab5bc8760856aa17726a323bd7ebbca1de6c920aa240a2b276c6062b1834b61890c2c1863e2a1adbe800d8760b692edd6762c4a6e23a8525094d0da05c34b9bf454e4903fd96f16571bcfde3870a330482439fb9615934970a55672aef616758ce3c2eec43dd516c10a005ae2a88072550558ca99760a8a1296fbe87bc774e385627cb8bb2a8b3ec21193514ad93baba6e78b6eb2b1f54c617695e40542197ec16d1ac99df4ed733fc8466dfd3a5c4c3f1ddc011f4b45d478c0e07f8933a3529b657e9c299ac5ef3d35b60dc9331a933599f06fef18492dbdba766a3860ea7ed268217c2341baf40b3459eef3c9ea382ed7ff18dc228d365e4964ccca1270e5c46bd381a4f151b8084c64a22e83c331100419430963060ad26897151a78e41be8688c739c86d64cd19181ee1a24255f5bcd5f37f15c859c04e85211ddb6abd218b94881e7d626fa288d7b92620085bb9edcc11c9d85303223af824e59f112350cb6af413b16b210c8627d2b61c60bad730f6c7d41db", "spend_index": [ 0, 1, 1039465161, 4294967295 ], "result": [ "a2a16cac35e718b07027623e243e73ec51e6c6465302cd6a4183dcc4468aa8b2", "6ec7b9f66c1dd580207d465450f9bc88e9b89ddb6dbaa8217bd4d818263977c8", "e9834cbcffd8ed9419d5f0dfc17e3d23d1676ee29097822792c75ace48dfc38a", "f15f04bdb876303c6a20581f561bd525b702fd8fd073a9178e405ed42b9683d7" ] }, { "desc": { "Inputs": 9, "Outputs": 5, "Witness": false, "Version": -1778983691, "scriptSigs": true }, "hex_tx": "f5dcf695093fc181e8000000000000000000000000000000000000000000000000000000007e2483b3fd1101d6690001ecc003832513a53dabcc55b97f41ecd703ae104fe896e0456647f35bd0660bdc3a90d8bcafbc654f44512481794cea474dc3d663cfc58b213c0d57ee05a04ed9a18845a52087b93fa91334b891e42394183ed2ebb43eacc66be1fd4029b5528cd19a8cd749f8799fda3c7a844a26b6463c310f0ce6b20499d1f0e2a9dc12a8167342009371d688e62de4878a9f4fa068aecccbcfe28e59a5cfe0b1158ee184c36bd2a5afe0c26cb430494def39b2eec4fd0ece252b427fec0bea90e5cf595613a5eed4de54b35a89716d44a2d8a79fc39426d57fb67da6cd1b38c61d3a96b838495c4f5aeca6e9d43eb0d024014151c144bf2067bf6d31932ca44c954ccb7c562885040113c920ada2ade923e31fc0581d7bf73097000000000000000000000000000000000000000000000000000000007ede57e7001cd7d0d128797a9d00000000000000000000000000000000000000000000000000000000f949822e5385ca0bbdf7d3f0882caf0d83c26d2036dfa0b8379fbe6c5dab138e30dd7be61b5d85352848215842755713c53cb73b04109852e9806c6794cc26677de7a4cd06d8ad00b1c8365625f2eb9e0e62f57074160bbb2d9c678a973b77090000000000000000000000000000000000000000000000000000000040141ac2005946c4007a4a255800000000000000000000000000000000000000000000000000000000d6f015e1dd5ffa5dd907049505d2988b546018b952e3fb159d4de638d9489ba60bbcb7b72d88f114af486e6538c9144974214c22996633b87b937fafe846616a5cb843b630d3d69f5596b982f3160c3db7b086261310491f65e9350d66532561210adb31471b6d33021a10af85eba4496e1d5b780d3d730ae304831fe2545ad6bdc1ac463342719a2a13ef89bafa5ed0b5e36c08ba70f0b688dba8e7ec9192c9b6896918c9038176b9a52006059b7142789e1b587cd4904cf8c0cd9cba8a07baef19f6b060f13a427ca073e61f05918a7af7e1478771f2f7a0cc81c519d4173c972850226edb725e0c1600000000000000000000000000000000000000000000000000000000cf75aa3ffdda011fa6edc21e87d0b325c7cc142958b9b6613e10da0e532fc462cd39eed889b95fe26e020b4a10137ee033049364482e0c8962ef7ceed30cc4fe9ae6d153ccdfc7a317781258c53b0db40bc2f1d43e5089728ac926f2daa82076275f0ca2c5bbec79d310aa63319cdb6c39ac20a191c24ab5d755f18d4379ba40e0496f425378627dddd02946e82ab8268db208d64d642ed556d0328ca41ee3f4bbe6cc17a10946976da05ef023cb10c08a5a97b29e79bc1884540356b5c92254d84d1c551a2fecf7135ba82f8c861b1aa55cd0f56301e40a43cfc933719cf67e4c6b0c36f9927e96923b944bfc202195b434473d18f0f705b1d5c19e37922ef2f4cb50273b840ba5aafb90fb7b2eb9573da4514c4df6534841f945237a8570100e723b111dbcdfd2b5c6e1d6ba2f9ba9514888705f6dee8b1ba37013ca47dfb63504d6d69f7a388282af904cc216975ba9da3ebaf854da5c43e6cccc208d0d54d6ce17502b86427e8bb52f4115d077a0af341363b5946de9a2449818a4f59159d75087633fbb1bf6e5b022795a9217583e54fabf3170068904d706fa329fd9124d2bf1d72f045d817a510539558e7b2551c11925b06101652b42377dd6482e447b7a16d2c5284f706889811766f0128c367860f617bab532b7bb2aceac9625df264290857a69c8d3fd00000000000000000000000000000000000000000000000000000000c1ca65b1004c9762cc725275cd00000000000000000000000000000000000000000000000000000000cf012455fd1f01f7655f0f0ab2cd04fd4c9721d2f06cdf394184ac47a9011c04ce52b65be28161cf788f3ea2d192fe7b4f4230d3dc404c449ff4a7a29a64121844c4022b54cd54969f763f46222d0e11ffa3e66a87d535488af9dd4052abe49c289cbfcf7d7f649f0e27705e802275e460253a29e6ac2856488aff974ea04e8b009c53ddf849454a219fdb3ae9275b6156fde5870cf94eb37796c243dbfbe231a886cf42343e5f173b9a618260e062f0a020dfce2ca617aeebd7e3be3e586524ced4bfa21a584f5744a84c609b715bd912efe7494d26904c8e43e4027df4d894fdd8fc79c1965cccbf9bc697c7ede9441715335dd3b4666989a9ea75e76a1c3a494fdeaad4848dbe2f04b4131b3a579c3914a5c5227fb196c837adc7bf21a423cff2cd8cb5b71d078639df7b550000000000000000000000000000000000000000000000000000000000dfe9df45fd63019188e354948cd4b72d16860c58deb309e252eae07e31be10dc9901b268080e54a875f645cec2165e958f00b2d8ef994a7bd5832dea1496ebae1905fd46073efee82eb1bef614aff71cce2ecd5029442773ae07ed35868df68b80897c0a65b6b61748eadaaa9ebe4d2d125438baac1a2ac78f3e3119e7a8d5f0d2b4a134c724b5126136ded6842faa8e6a4abf6edb4630e4c878ca8d1823ea01bb9fef5c9737db5671c5f12bdf5aa8615d19bde847105237130bd3952c426d5cc1de90905e27a96cdedab96d44153d215bc43db1e01c2a5940cbc371628d3ad7fbcb1671506246e682416ca0fc5e72c2c5010e9f3270ad3e9ceb8d0505db9f4ecd5342957d5372ede3675584ef74ca12dc7ae5df95d870835ebe6376ff628b4a34541525bd7d5f6271ba67875d7cd5b3654af6a91cabfa23ddf0e3a3816b214046b143f075c9f58671ff9b9b730d606485b6304db2d140851448777037bdbfd60009b7ab63e1e729e607322f398605d7fa164923530a5fc830ba0382cac05055d663f26fe99a2f5dc7df97ecab542daba3e05dceb666cc2b73dbf235b9db9548844ede8bacc71194ca9bfb4ac6e8a0dae54df7dba17332cc4831bba6561bcd4f7f3ec5e92b634390e1c135cda417c587ac97a8dfbe295f7f953d5bca200891b39f19c190596cfa5cf90ee33cddc893ee9a79fbb836bfac4cd0e594036da081013cab6aadaba86b43b288c4233c3d8b4f42a236cbee324c7ed9cd1981c85a4e46986909b8700c08f7162ce886895d49cf471d1080adc7be83394d1976425eb175167ff0bb6c0ff820c833b09daf471a0a20aadfb9fd93fa8d04276f2e48adfcd3fa7a972783199b63e2669380c972f3eb280424ca5887605032ce9ade7fde8f9c61fed04ad62a6b85a40c2c473eab56443a2f3538681a9a8be50c5b4efd6d542882b6fa904969fca17f2f63ccc6da45c05dfcf3d52fa770c2966923f5928360e2ecac4843de70f57fe214696c105ca61e96b1088843d250d3824948529f2a0a77a59d5d4151c03b4a47324904cc2941cf40e49f6d2a20601d4108272605d3917bfb294694ea3fbbd14411959ce4cea3d2f2b68bd5d55c839c0ec89b78417dce13986b76630d44979033fe9f899c0b0d3b88efbda0c5db44f6a3e0dde8a345f922c003c3509dc540b74ddd4c88fa65866b5c465bbe0b2ec09aef7ac70dc67dacbb44d3ccf05642205c3c927d0c545457cadd75aa93e19aaca697e46474986cf788194555e921117731633f8ee7ef0de7143a62dda72dcfe9926958d67c5f61522f31c8ae7c0cdb228a283b5dfada72b94e5e4427647c083e1d45d00c39bd17a78aaa8e4253950b5f354b90f26376e09c8b87cbe96d7ffe53318842b2ed13a3a13bfd138b1fcffd711bf074c8644c9ed0edfcf98e37cc6322f97fe7dfdb3d961e7034687c278a3a03b039ee63726e2cff8f2a14530c639800cb6e3c05680ac03763ba60c4d39cdea5bb441856d487bdc57fc87e0ad23c5c45c117b7fd0f52f5847d26328c55865329a37bf00c42304bfab148191bfcb5acab3f801cc9726af71e89d2033af0d00c5f28fa28fa10225b655cd3ef0c5f49452a392dfb13db9a0647b6eda1c8bd8e4b2dade1bda2e1888fc7e503ae768f3ea27e5a42071d06315efec064371582941157502f8169a444371949083b92bd798139d5cb7e4fc8c440b761cd8bc8fe8808dc74c0c05812bf49f97215994efcdc6e3cc953cc5acbc4e40138810e326af9ae379af0d580351a0f1052c50d93a4dc759dd2345be179c30f5625af069b5f5c4af6ef956bf3610b5f7e6e87ca462b6633cff354a9b74139a3c7297a8bca323ee234f6bf639d1b204aacdd9a18f56e4ba086d40b0dc800a79a80e4b81b20a45d3871d6d2b7e002445d7747b261cdb82704357834a7025663c5a6ae43c0f21ee3b8547af8ba31a59105b25d6a4b47fc46e124a6b92d6be05a7223483fa9df16d6191028", "spend_index": [ 0, 1, 3001707671, 4294967295 ], "result": [ "930292e885c283bebd8ff54113a8eafcbb7ecdd6160d3fd243bcfaa30f60cb5e", "c446abcce18fdabe4b288924b4aef3a7ed504eb8794000ef1cce0ffb25dec6ef", "2526dcfc4befb9e6538e5aed58471450ab49c9545e65469894db81347276809d", "4b1720584038bb4e9feed7f86aae31af7f1420d0dea479084582a0946d7d1706" ] }, { "desc": { "Inputs": 8, "Outputs": 5, "Witness": false, "Version": -216890641, "scriptSigs": false }, "hex_tx": "ef8212f308a82f1ef100000000000000000000000000000000000000000000000000000000a4a996200000e822cc553589640000000000000000000000000000000000000000000000000000000017ac8d47005aab030d2fe79b6c000000000000000000000000000000000000000000000000000000008b7902aa001f25512aff3f4cdc00000000000000000000000000000000000000000000000000000000b2f03dab00e670be7b3e58388800000000000000000000000000000000000000000000000000000000f9ef4a420013ee1575ebc610c600000000000000000000000000000000000000000000000000000000f7f5ec79008c90fd5119b2920300000000000000000000000000000000000000000000000000000000404681a200cead0795af49e314000000000000000000000000000000000000000000000000000000008aa15dc600fbd521f10561d44a64b3e1963bc8df4f61fff9222beb129db5562575437f9a1fd8ca574d8807ae99a9b5cee236a626bf943342c065423e161f267e0027b3feaf36f52719729a3a0ef7697c4409ea4bcf412eb5fe072d5769b239597e45b992c9b4b7a5bccdb37fb3d467b27af3827836e651316cf301c6f286af4e0ffeee5d0434f28db1c34428516e16af6e4ae82c30d56e6c527875cfb3966832873ac00b5c7fc278f3b7eb9e5b05e6af9660e4e4d0f62bd15aefdfb1ff37f77b6d37bdc927a191be7e7959eeca3a2989363f5fb7cc33be81cab92da130f382dbd83674c8eb2acf122ccc06f14677382748ca1277c49a9b247165f73afd00f18ac30a4996825a77a2ad87b86ebdfb7ad14ae2dfc081d50719cf78837f512d5d0bd2c7ac651b53c3fe33ec06952394ff36d6dc5283068151f893047ef6c1c002b52e51039c64d15094a71d39e4b8ff85b2f6f3c1e15821d03483c0d95092f3dd637c98f6176ccae4e22d5182390447b35a92e728576174e7bcf93a81dca7a7993fc9e4a465756fb6e30687858bed579fa3c5000d1f37963fe5d6e62a638eeb8ec1e3b184e0ca2c016113125cdfb46e57ca2082da3fc8148741c8961ab884272045a0768366cb05fe8216a330fc28c7e9850435a8dbbb4355b5bfbe7d078db61c33157dc3b615350e23bf487c372be4421cd89cefa10e365c0188e80cd53ca6b87b9efe6a0d04e6f3eebbc1b2b58fcde6989533c6eeeb23bb2411cc2b01f1ec28948fc8b971a753c30be63783cc33028061fab62ba388b3043f66fc544f9c4ee231808fb56a4c9ea308c742ebeb8b5146e2b4ad972945baf28f6f4d74b275a72d9e097076af22d97e65d08fb0e0f9fb309df5686a51f839fc417a72bf2c49c9c9dfa03a076a6dc81179ed1a831760ea97d2a2621a69b95f603c5cd08a22670408832654819c406b24a88c2d13062ea6949445ff95e118d7a085f55c1787320bb9a4824f6a72c0a5488862b9191873ca5e91258ff0d175df136f0aa8d13b2a7e4369952f7c2e8e4d4b79a0418ab32a6fe8ef92d026545c25cf997a4da4e39c6322fb2be30c818f115edbf6df5e3afb196420fa6fd2068bfe3e111a6cde0c296cae0ee7a54a8c4e15adc38ca8855719d036b27349283359591e9cdd00208717eb8cb42ca8e2347198d321c9683a2e017875ef3853221fab31c84cadb6436fe3cb56c1ad93be49cdc2490cb9968918cb01b294d2dc694b254ffaef397aa5b83d640d06cae8ea97812285e57c3580bda02213c481907a4d917ec7ba2d635ef6dd58a3ccbe451d627e270270c0d86857b7263ae758e0a55b4bb290d48f8588c0614a1532e3b223dde1c837ca086e6753cd6031102bcf57b1b452646bc6716e3a017c9a90d0097333647d7e1bdeeebd0ce438000b026142d165ab676b691175cec7aea89e383211d9b6034b4f284ae651424351bfc70545b78b263c7988ff915a1907ec828da7fb", "spend_index": [ 0, 1, 3359567509, 4294967295 ], "result": [ "685c624863f861c67e4a8210849c73759d3347ba3eebd7fbc562135f7f47672a", "0a610c39cc9ac49b0a7cef972d2162fb0804237112d98a17c38f8386ba3680a6", "9a6ac014df6a98749b0911bf326f7bcb5acefd7ac764952053e924760d3cf15f", "ae96a56a28816b7e586c0cc694d8d8c15004e2cf87f1e06b68994999c4dcfe3f" ] }, { "desc": { "Inputs": 2, "Outputs": 7, "Witness": false, "Version": -1883448568, "scriptSigs": true }, "hex_tx": "08dbbc8f022f54e72e00000000000000000000000000000000000000000000000000000000877ac0c9fd250134ae14a0b9eb05820f80cd61c1d7a6e6a729a9c84e4e2c4e8b61a41aa855ca108a0aba3dfe312988c96136dcba486c17ed0c9e100d1be2520d34e2989eaaa57810b12b333cfab0024f5733060ae2a4dd79528850de0aade918c188165ad60ebd5669288d078fe6b78b736ddcced05873d14775f648b93d319354cfbd90a2db807fbe5f251c4d654eb82d2496a17c28855324da8989eb9386b6e50584a1681546d4cef79a012ca3482e8cf9590f885775db885ecb22bf1672f7952a1349b31d0c95a2ad47c13183edaed9618d50c11f26d7229970d1f8c4bb9b7e8b29554ca4704c0028a0610cebfe85995aeb69981ce506959be35fed6954bea67e9537618a7ebb02e0d96cae21baeb41d05bd2f2f2cb813ad444360714c7729db5f6b316cb07da13646b60fd0de862b92bc0e900000000000000000000000000000000000000000000000000000000f3b39caebb3e523c4a7eb0ef24bb945994e030b77a3f44c82343d4581ee2374e0124ad3758d3c388fc5716f0d2990e263784eda69cc2938631dbfbbbafc2de8aca297942516676c0d33b92add38756225130848ec9f6169d3fdf3ba22a82443d1e01c61022fe9b748b67b9facafa5b35efb5f529b57e771f63fcee5b9122957f56ff47be42e2870bf093754cf096025f219f3569d400dd159c96bfe4f1807f638325b53073ec6f8230c230036db0f3ced100f422e2c708b2d507e3a27c907faa9554fb5f070827e935bf9e865ec818c8b59b541e199f7c7cd377a7297625904ecf0abb0a7756b0fdbfa7e3b583f90f5ade635f885f80713f318c59677f090f43a75d9681e4740c9e1516eb7670af9f50b842536d6d7b0121f56be4af5e9abb7759e584613ea51bd5491bb221bff5c3e0c8b7d2a3968e184506c4a2af09e53cc24e34e300918f8c2f9146d7be2bbd6d25945ce8b2145289e7e7a21f84b4cc4a102fb597787f15896348784b717b2e950619c69d561a71c044ac13397eb3cc4839f3ed9e027c65920bef596251b5b80e90ca7da263e8bf27cf37b1c1ca887cc8bd1646a1308e578410aebcc9bf89c58a3f3317605755de0279f11c6e21c6a38eb615083fbd914e30f3241fbd734fc3f96870bd6ce6d39208fbbcecbff639377038fd245815a52cb4c842cf3b3307171a574fed4567c7f57e907663a3dcd8cc2404f8051fff2dfc11f941043d8605b11386f3ff7e04b59976895688c544a199b323bf6b8e7b023c0796ed8b36f5e4bb1d5a12f9d26ad9cfee2fc4d69d1d95e2fa72c25adde053f7e85e7cfbf6b916bb0ccf993a99808092cda8b14921e2415bc65d30a1173dfd3f830a6687cd9779e97fc8be7e5034ae8ebb00370c0900e0305338651f1a6dc93903ed946308802d38d455c3a137445e36c379e002eb02cfcffca370ae2d9961c6ef7d424b962f455f3ad22bda3cf12d68e081207f8d1565e9967014a4a1b06f5888fde8682fd7fb0432cef9a23bd2bea7c26ad9bf5d38308c6ba2fdc9c50b9588a9ce7e2b92e81b5c6e761255b239a20cb2963e691407fd69faf433063e0a35514e36fca6792f4e65c45890da1ec231f3d3b4e75f7f449bdb8b5fa0182443e110ede564a1671027af992f941dea938e5f7da5dda4ab368c575848c864d428f8f146cbb1beab77c483b4b42c477f817e343655cf3f376cf59e4a4ff553e006a200f5e749eebc52f9cd53cbbcd1852c3facee3563181dd7be278114fabc0d3c11e91c29ad4e59057ca48c08755c7e29c02a85174c118612ab99fac76e1d610635138583d0750cbe836d146a156c7c606fccfacff44b9739ca4c4aeae943e07819649edf8278c55e88e3b8b6e74a4ec077ff5a8e253cab1379a13aebd89963f2314d2ed655ede7f71d608548bf3d965c4e168cf13b1b46ec2e1aa2e006d13598801ab392042865667e7e150406c851c1c869a8b07188d4ae8adbb37ec9041f2a91112d95b66b90ffbb1d1190b4d7d1a7a3318b4a550456c9a74dc300be42359ff834542629e1de45a096ca923a5af0f3f00f33ca699a14c6c36fb0edab108387c6dcdb0cedff8341f8882571af05184ebd9846a1346b80e8fc7d28f69d9a020255831203650b9e91b2577f22d82ca5367509ea0ae4638a4dd0e53df0c570681934e6d149fe397c742750f11ca91efc8864a2fc807db1952c19e9a974f1b597a4db66cf4d371eb579d78aa154829799c4320b70ed9ef733d4ec9e33266a2dc84e9bc1bb0802bf456fd27500fcbb02fef049ded55990f5dc193ea804b498eceb99fdee7832d3b2a560587d96a71e656994cd0388de4ad2012150dd728b288f9e756b5defac7f56f22e770f450c52ab73649b790ff10e9190dd0f0c45a3dc5569bd7bee562e67e9ee9a4972917c346410735954b623547cd7336455f0d5cd3986931353352d02811e75e4f3b7830f7dcac8fcdf0b515918d2b94f2666a7c58e0d8d119cac528006cb0f30cb7bcd1016323f7e7906d1ed5aee15e826403cd3c744ba008d1ef7a2e14cd8d97ed77073d851c8d37c096e1245c704af53c461e561152877945c9be828a1ea32094b9896752086a5c13e75e0eec5ce591f4b5204e9f84fe205d6328c693ef23211baf1d562b0db2fd75a3c5f874ad5a12630597dd94091905f69f2b3319dca7b82b23e4d97f8c84b05dcf3aa0372b64702708a0bf89c3f135192f07685c6093088a6c11a84423a95d450710f5628031be2aa82f2bafbb20a249d8d9211fc979e977895f28bfdfa3c7b74b41aecbf74f150561143cd019417d4cae61e1fc16330948eacd2aa926f0faa413d634a2c496294cccf", "spend_index": [ 0, 1, 3425086302, 4294967295 ], "result": [ "c4ff54c5b6bdfc36141f3e24ddee434094858fb57bc0d0249c70d3898c65ddad", "209df5582d0e9a7e694ae163ddad064a842b7f98547fc16c7273f1caf2102ea4", "b8dcc1666c513171ecdc329d3041f567ceb4045be8f728fe130490774cac4aa2", "6132d4ba22d464e4b5437f79b7e4155035eca1d50cbb8822f2cf343f293d97f0" ] }, { "desc": { "Inputs": 6, "Outputs": 8, "Witness": false, "Version": -2124013575, "scriptSigs": false }, "hex_tx": "f91f66810631a91e3f000000000000000000000000000000000000000000000000000000006456780f00e54408763610d8c7000000000000000000000000000000000000000000000000000000007873c2dc00b49a2ef2a77e0151000000000000000000000000000000000000000000000000000000006d7056ce00aa6eda299fa9ce6600000000000000000000000000000000000000000000000000000000abb7300200709c29b21639f50900000000000000000000000000000000000000000000000000000000c26433e000c6b3e924b4ed2f3100000000000000000000000000000000000000000000000000000000b202ba1500b43c304d08472ab497abd2913dc82c05bc0c7df3fe622241479aede78410e9e0fdaad46ead2cab38c427309fc511f552a2d31e1249af40883d99d1bc8a74992361b8a3e2ee64b1af943efa4420caed82c1ae35059c08d72e4cae205ef4d902f4552831651f31032f957c739aa835bea3968c67a96dd150c6a6267b4f6583502daa96668012c19cbaefca3432c240ead9f5d41ece9275c809b876501564b20cf4b01b084ebc87ca4bc53b7196c52940175d2009ab269a4ff710fda09933a59076511c40208a873da1d9a1614bf906fb448ecbe93bf67f417f21fc46bdb630c8088bb17da2a0ecc3077fe5c3d8ab5900eaee042c40fd71664607164b0e6255e151f125c6af0726d8b478c8bafa522c8ca8edf1c151aa84f61614e861f5ae9a4c7efc1726fcb4e0f0971b87f55c14d64d78d5b07248f0f8ad0bdc700a89ad8df8e2b446e2097a6c96c3f9f1917bfd64042c6f042a69219846da7e074ab3d2015949ca28d1df0d205136abb6526b8ff5889bcfd199eef182d71d1d423d9f8cf44ab1649a9a1ffa86512973a63d0584ee127e8cd18554a72eb9a91a0f19ed29b0cffa7598c408ddc8e811cd35f685545644c8975428b075e0eb87fc1af9004664ae0edd8484e25ba8d2bb1fdb028ce63c738b6c27ba304cdf393c6d77619b929ced4db5702750725938addfca160eb66385d1874c2ebf0827bac548b9998f2c4b19744584824e0bf1edfad072f2d30a8530109cbef822376fe7c2e7f7769849840e946bbb57070b31f334593f3ba0bf01ccdda6b0c390c42c4dbc10b6d4c77204322637a9841536cf46867fdf63801ac0e6ea2a19a33cd15e944c12d3fb47702b3c53f3800bc6a3a6b38d3c770a0d4997414afa5eebe422ec2114d6e8512f67350c14c823e4fe85bacab8814cc2bf4509c294f69f6592797dadd9493a06255d808bb882ecc1bd2a997d499a3d2a03ba208f4c252ddbcb4b3a07effcfb3faecc09447014489a2babe90f00c4d672ca58b959fd61c2273d80d22c21085c17a182388877c9cb0a18ca79b26126b8244a0e5f09892acaeffc14df529febafe6046d4602cbcc1d089d97b9d9275a914ddeb1e24144083ea3e4107bb499b5c1079927a2e46892d54540b783676f45b7ae002181527a3c71a35cfef62ee769b79a41805a6a70ae2c79b05a38611bb0b82de3845eaf6879c8780514862fd430b98d94d1838bfeee12d97aa2483882d8ed993939a93310c2d8822fcd9f72c4adccbe3577f2989a40393f52c70fdfed7967272d3c12b10d6d695e36f08b0432ceeee160db1b775be0f812e0e6898985ebcd51796ce9dc3b3df9bfcd13df766eff953e4e142c381e7c3f32c1cc77e4726ec586467b474bc6b3634409fe14831fde7dae12cf7583f9ddfbe98144d39025b8e6e7f69b0dae60bc0d3f4f7a0029eda87e8f26c3458977af84ae4e7fb6c0057ddb9b48d5eac73160459ee15c7281bc103e9bc72e6389830000c85fb913f2dbf8a1c92413244216f9ff4b34d6a34a2281943f1a343b8aade6cde15e15f4228040af5e546e45da72e1b1374b61a143a238249400e2f5103e25824645be9d35fc74b5652894abfd4174608bee29552b7b88096181eb342424cb0adedc7285add1cc4253b2d76aa112c5ed06b3a103f982cdfde19ae64b913826bf339a91c4791d3824de23822025b7c279aef8c9853ef0cb43c180384c073fd6c76815692659fc15295eb62d1c626f981b903fec6fc6ee0c17948041726dafb961eb249a8a44743e66eeff36d312cf3c7c7fc875fb7b42a8d993c3d49b2c90f5703d0845bbe0ec37343e3b501f56a399910a9cd2d2da42d0214ac553bded064017ccc4c07cac9edbfce92b22a7661011ef9f49c1f0410f2c4a7883319b6aa927ee8db5bb8038bcdaca74f158969a6f0b81e1a00c1e7f386db1ecc07a31576fa76bd2c7f957b926c11ef2ab6a1e8d83a07d37acace1a852cd37a26a5d490818d045300a54c813fdda483630fa92fd9d06af62b3a4801406b2fe7b5b7d6011a57bf135754e05ae28b25d9a14c7404258259b99384c333f13dddc28aa41b9332ecee74f58c80d774dc5e784e4d9a4b10679f6947270b56c5f6997ec141de775b4c53be5abe6af8b522b6b7eb1bfb1ae737fff7f4b5779f3749bd44af958ca814817e5bca716083cc36dab89ce480e6b799d43c4a07735bca9526afba1240adeed6c5d4d2c277e27da4246ee0d7969dec01f1cc026fafebedc9aabc47cb3946b986d5a8e31f1bf99d483f4cd74f0e7113ef780e694c31b552b63b1691f57c02e7607780047161b94466bb0b2d46e25a405022d2545bb2749acc82bedb6c18130d6869bdd0c8c5c72242226933c08ebde16c6", "spend_index": [ 0, 1, 4231503344, 4294967295 ], "result": [ "07744dc2bec2a557bd05022b9bb7e12b5a8649fa00963988c524781e0326c47a", "0b270576e396f0894e3d4217f9ee7c85937a63f0d095fec74174b0dc3896a837", "964ada7ea73231c728f3f60706e0010b67516e8b0069f659440bd2fd799abc71", "086d75dcc9731576f388fe97b6fa83d562c8e51742b18330d0856d3dcfad907e" ] }, { "desc": { "Inputs": 7, "Outputs": 6, "Witness": false, "Version": -2095044500, "scriptSigs": true }, "hex_tx": "6c28208307060ac1d90000000000000000000000000000000000000000000000000000000096f5aa0ffdb4010e3736ac16944cb0bbf50ee66da139409dedc362041859ea64545969ae391984c36ecb9734a42ca92676521cf835910bd259641c74217d715465236a1020dd4ceaf6a6c81f17f0e05f7bce889c3fc10e97fcdc10b3f298f3abb7cac2fae62584a19cf1e328cb4c88dff31ffb5a8e108aafe752f3de151f06516439896c80bcea4c79f71c68a335b4cd167f208d21a997f3640ba9c373410e9c003af59c718728d1a6d849e1945e107206aef6dd4d6d79d7746aa8c50ea2ac5bd839bb24ca291cf37aad53e78d52b0b05b154488f6d1103c50adff728703ea3f4542e14b4b4cc989f8105bca92e67b4e2cbd06dee29a638b514be844b38357142525ba77d561b5bda9811c837b73089bf6e880df1fc02ebd64765b7353aa88e153a2f19babc83d4c060115919f729024a01e25f8bd1455ca6d2a76abda90c9450f4a7744e3964a7e43a1dbbe2d8eb3b80c8ede51a099f0e1bad4db24ac50239fb088156666c90a7dd6d1fbcf38f7c1d3b5cd12727f6afe3c57759b787045bfb2654fcd66e7302386a87325c7506b3342aa7b45fbebcdbb8eb0bd7388e8eb55d078f33760f9737092f2e4cacf38316e9e8033cce9b3a912124f651eb21fc2335847e6ac000000000000000000000000000000000000000000000000000000001fcad62927cdd4fab9908abe626c449532613699ee4dd4a1767012b5da4bee04483c2d036f73ad64a7a8f0c9c549bf7e7fbfe9fc00000000000000000000000000000000000000000000000000000000f4fc86ae37006902b4eeee9dbb24801a0b38a7d194d773efee77edd3f553299a7be77844e580900055aa410fd3a6b92dbd40c0086e458258aade6a33e977b7a65a5973080000000000000000000000000000000000000000000000000000000016f0c5b5fd920153a0a6dac7c870b1be759c7e9ced21d2d7a7f2ec4f3d9ec6d977f204879ef9c4cfafd45f82313778ffadb63a11eee3fbc354141474dda7821646ffc4fb87e45a531018999a7a3f967e11ecf99ded742d67ce91ed31c92d8a041a97c1d44eb75372d6555a9d20c1dc9aa576e3e440e3f21192e02b4001e9b7d766af089c7153dd79a020f9444df960e5bc0881587aed906b66b4f9b92b060f6ba7d15d23355580b97697a9edf34c0c65db5e601513e367c839c78aa408cad9c6e118b5982dbf0ff062a2c5efa0462cdd4f40c25fdc66f727b11988435351b1662b79afdc2771dd23945d617fd8f7c8b1d75b366443ff05764e60ab8ea165a63c71b5255d1e7da579e51836529b24d2469e81b25b0e9bb1fa12ac8e61b0a7c0c8cc85bea23b691e415837ff6786e1fb1d15547d7ee4dcfa4c57e914d142eb37e6d816d4808cb422ac74b0486f5a6d2e3f084610ce1cd5e60b5450d68ccb644e332f65081f6cb873b18b8ebcc3a5a47b8e3e10c1d592bfac9bf1fc2b26e837dc8d5b3680e719789394d8209423a4f633f6587c394255da4d6e64592f94d8839bf994000000000000000000000000000000000000000000000000000000004af9fdc600b9f2b5494ad008ad00000000000000000000000000000000000000000000000000000000cf6104e92b205f957cd7699c242984af2ce868fe1ebe1a25058e271e1f68e2053891eb6888df286721732afc8c3f58e1472aef8fca06d3340000000000000000000000000000000000000000000000000000000087d4389afd340194a2982947fa8f757bda68c65d75284a67d37d5b9921e75ce40afd5bd517c65c000a66ed79a208319f521d6a737434fe9786437f97ebe3ad3fbe8349ecc8ce2df5d69c00cd372f04bd36f5bb2d7a59c7412cde2c0a0b29d8fbe0a9fc3e5afa630a5e88c42dd617f38d6728c7a95b2db9837dfc6db91b52bee2812865e51aaddd8d7e58d63b8f2824e61cd4e73e2236da52fc486430c0e644a6b5940a01723cdaf0bdf79b210971284ad9e9b371bf7bb75c35ee7217a35649c0e50be730bc0911c7f753d43e930100e89ac61e4fa4bccea1d254bcd0ce52e1c8b971362dc02037c236165389f193d7f0be0f7379110c7d81e729f83642d37715b218fdce818036ffc796417df655c1302032692e0030e1a4dbddc5813de030fa52d5d19632fb0021462ec5ba63cd3400538c10cba5e4533e1b956570b681170695dde7418eeb1a7ac830accbb70f4faa19eb0ce2a49ca8e35b30243447bff801b5dfeac06dc82b3229e94e36029500d83a8249e8082aa0b0251e239027ba2b119aeeb3b91a8537a19dd3166f6949947fe6bd115efd3a41106fb98cfe0d4497cac0635c43db73ab70111b402e59b940743ed8d61853f5493797485e3a5e33eddfa6566d5863836f482b21d650e0d05700b0635b0b8851a0c6e6be79027b6830ce371e760ed37a389c589ea0778e4f0551d4ab3e9c40e2990947354c38ebd58fac940e17db022ac5300022b704212647ef6374b4e1117f278857c8d7575345139f14a21784ad6027e2f7ac9d659a3d5c36505c07a8cfe7cd4984db3ab9459bb636e040e3343ed8d7b26f6b9cd3b5a0aa00d1ff62516631dbb43423360fa3762d9b99567fb84b55c91a76a30428758b08668ffa04ffeebf45d78d5c85b469d64a50dba4d14390d0222de714bf8be10616ccb4c3cf1390797a8d2c7f7817242555e66eb525a33f6934a50e1025cee790ca2843dd819f7bfbe6a5934c54420c5e351bcbc959f7ba789fac2ecc5e7260e3f2c1b3affec2f46103642744bbf536320a9450cbb678d27d7d5f4e3ec8f9d5862878725bc018a92eb3797a8178c38a1d96cd43540b7833c0cde3bf66191889e9292bba64ef55241a1acd3630b1616efafa89cfc28f00172124dfad3b37afcc05857d0df8f5c4daa90e4819f7cf918ca0203279204f754089390e14f92a49f47bf85bd88ebb9c16e5335f15fe04ffd7b7f1d621699098b3c685c31082767c839a5132eeb22670608766854ac1745f0872349dffb86099f351186094efba92b2c64810aa05d903e72d0b28a5e53121d437f1cb007c4d0bcdbf80e6cf1ef3ea746a9e7dabc1a66890bd40e732b527c82f8e25ee066e122a639a75eb62562778894efff4683edcf07cdf042cb4d071df24271dfafebd7f952737c977e70d5e20a1480fd39603a43c3808aed3ba9d38bfd66c3b8a2d0f763f5b733075dd6e563052a5286f14f419bb75969fd0a204f430efe4f820a9ace80aa3fb12dfa6c6f6c6b316f1d65c8e85dc819dcf56baba734c7f166238a7ebe5d6eebeb0a2f0fe9c67ea4bbcac6392fb6f3f9ae158b74e602d5a820279a92bfc7ab27d99152b1b2f8139d33402b48ef021d4f4abca738bf27148879f6877a5ed48ea76c110e3fccb59c8638b72a29cf281d2f0a68d14e4b79255e0b4b0a97c65cd207f33c4313ab58cf5a748214931aa0883f533508593529bf05fe60f2fbd4206b87dea735b10175319760b564e231049aa09870884352a721c01a16854e72e6e9e69e611c8cc856847be2c8e38db9c8ff9302df8b94eab53c796fc14752ce43be66b1616e40be6ff409ba1ef87fa8115b3af6d5a1e8e8ec9c35d68126dcd812267f60925cf8a752f730e9263d6ef763540094858f83c9a6dfdf5e2d475a9f2a478bccb83be31059cbaeee37232ee81a4846d187de30e405d4cc8876b83db63b4a2c8e40642a00f5bf318b21c74025ce90fb6bd5c7ed4bad8dd0b4715ad407463a0737e51b7b8f5fcd912cc1438887522757a6ef37d90c9e183c2211ba5e6acdd26749f355fdd7c20f11dd3ffee8ba87191fee44abc5b443a4c96e1ebfc9ef85ff294d6fd20f6fd82ca3907e5c6c20973ed05df49b8be8aa9024d1ab3fa54d994fca4ebfe9548b69c247f6b0eaea3242f912d53ccec595d9b800b6da653fd564bfb9bab0e39e989039132e6e05a6c9f694df5c74885d565cf61a628da54f534eb2956f82a7207", "spend_index": [ 0, 1, 3575252040, 4294967295 ], "result": [ "cc01dc94e18217bd5c50001a2c6f079fb7e37bdd1b304ffc695afc8ec71be0f3", "2a1efbfeda89ef3bc34df79eb7439559c720f2465ac9083beb293f662c20cc50", "8bd0513e5555b8c3692757f692f2d5a98be1db1435251bf8313a4fb5104893fb", "0504e4048cec620be19b025fb0be79c800d3ac8967f7ed5389927bc1c0c620ca" ] }, { "desc": { "Inputs": 1, "Outputs": 1, "Witness": false, "Version": -341052226, "scriptSigs": false }, "hex_tx": "bef4abeb01b9bed30500000000000000000000000000000000000000000000000000000000cd79af5300bccb233201ea4eb65a0a33ef7dc86e238642dd5b75af59bde98b69cafe8099d052237bf841e9f921d5f9f1d116e9037f7e9ec2fcbb0969213a501077b99180f91ffcda99a3ae872ce91a86aafcf0ba5d4195743c7f1d2e37d1a8a3c68bbe9aacfcce85f186fa38c9d7365cea2081ee3ba877c794e6e9a228089d04e64fc7931f04109bb1c0c3fa8b8ddd47b6d89f311abbed387ba1ab6cb0128d5d763d03786285b0760a0abc516fbe28a8761a0fcfa6b0675c783a59ef5558c11850a2ceda1ee1009cbec3a5934217ac65a3332128312aee121fdc0e9c56438f", "spend_index": [ 0, 1, 2487922470, 4294967295 ], "result": [ "7fd2725ad65f970b0045073b678771bc28f6c3ffd68463a02b3a9b8f5c135dc0", "351fd112af9b166cba8ce742c2527f244b9e9482aee818b23994b318d8a5c615", "89d41fc99be7e44d57175f4bf9f5dcdaf41c78c6604f45df8aeba2a2aa917b65", "c4f884db7b13f039dea9cdbbba05839ad7c1c6c86a9e4075d0b840cf79309fc3" ] }, { "desc": { "Inputs": 4, "Outputs": 5, "Witness": false, "Version": -47377281, "scriptSigs": true }, "hex_tx": "7f142dfd04c83cef6100000000000000000000000000000000000000000000000000000000ae4c929871f6604b51d016cf732f8bebaaa4321b7f2c64c14fd27ab201f245abef6e9c5730b5332365eba96c9d962618dd666ed5056d435d194f2977090492b12e6fd8544e355cf26af44b8ddd67169f8fa7e96a301782c1af391aaf893dff247ba1e7fc10d93e60c7066d1edad9d7a286aba60b47123a6d8ba46924ba9e0000000000000000000000000000000000000000000000000000000088a4000d0024c83103137653e400000000000000000000000000000000000000000000000000000000385cd66100a46e22e9dd035d6200000000000000000000000000000000000000000000000000000000fd6587f7fd4b01a58bbf41399dc0de27960de84d2f4df493b6b2bd1007c2293be63806183e7ba57765f361e3e074683490712d1ce48019dab7dd33cf2c150566f3ff34f20c0bfdb1fa52f58eefbe85bbe548c9caaff8d35e2757de8e2b38f0388267b3a1ebcbe276c546b57b38ad22995f242b0e048d48aba6642339c7889f2e421c4810ef9657182bd4a21721d74e7e118ece80c6a3b957b45c08715745253412e41cdb8ef1a936620c4fb601672d5ee5fbfe0b067735c97ee69f90294827286dded098a1558854fd1569a72e8c3cec049f2ae8a09299e38c6fcb5cd1ecb2e813c24c604ca1578215b84afaa7d4551a7b45dbf3d82809f8426f60246fe9353aa08eb8e5b75fb20e79dffcb2333df7a3341ac0c8d71eecf76bb6ea78f684787c3409112414bdaf31f57b83674fd47477e129978855eaebf0b4ee7f3107332eab11776d4d8b95e88ef2f4d5fa4b212fe91a6d58df8b54055ec18d52a3fb686ac85af069e8beb727436d52ef0053f809a6f7eb49d8a2a158d5025d0d18fd2b654cdda4a142114932a3fe778f1d8761114667d64b6b5612d90115f33a814a21e54e09d87b1e501ec6dd114c2992de6b6d076bd7d9eaf8c4fc071a95a92954bcd743b7a67ee40033dc4aad439bb89f445058e06d0168ca9bd5195d32c029379ead3b9823a5c53fdcf8c0f679b298a4772607d88fecca682405ee30750fd3e93430736417bac7a2ea7e767d7629f2c410a6b355bcf575bad8865cf6925c156cf722f1f6f230562f487f3de732fecbac36d065c82a3ea615b1481b5e873cac4883aaf24f8ebcef166870ef462eac18f18567851ec1952b1bbe8eaef01a134fc47e29e81bae2156e72f0c24631dd04b6a2b56dd5f8806df36f3dc175148840ff7e7ea02f6ceb241ea2365257decf29030542a208a4c3307bbc98f5648cfebebad4611b7eb35cc8fa403d610e2ee1c6cd20ddeb7d9bb142d44fdf4fabc095d70e849885d780aa14bbd3c6b3cd6edba384f2f57fd965df917caa4295f0d9c5070b19f242c9826e59d4b5a56390401bf741ce6e11c5fa4dfc9e229877a04950f9d4b480a0745c8ed95e3d42e92f311e3aa16f58a29b81f0bb412d1f26b904030aa17c532713f37853c0a1a99661f46cb90dd47047165f09777ed09d09779b15588519f40bac3798d1128822d12d1a623b374a385737834eb12a65a128dcc18b83993161dd902ec2a00807ff7de877bf4ce017c4f8b8b67e60b371c6c0b7bb7e23d27b674344eada4eba4c4fd109bc8f77d296919a93abe1f1fb9bbf3b175abfa3ad6e1c6eeba6711bba4a05670563dc37301085a553a08addd120277b2b80d5bfc0db9a816e1b6485309e686cf6333e184c061c8e53c4ec83968be78da016721519b40aa587eec25458b402d9365c983df46b918b947d5e7bfb6dd9df0e4a179e36bd3f9c6247b2fb3fc3f6bb0cf5185ea308324902cd1d291c2301f65c63c6d727fd4961dce3c9ee40a2c68afd1bf543b7c9e09ed1a16c10a18f0bde29d5ded3b4f0fdd9dbdfbd9670bc1d44474d34640105421f66fe5d10cc3702aec23f163f13fbf9ab3e8be57b5679f78c74cfc7955bb251fff9d185ffaea26bc4778e669f2a3ce0ae6be2a920b02a7ffe87d3ba46421234f40ea33e90d5729940e425149576387d3494b9a0cc8e8b5d9f605dd109c9b11923f71f6b587796adc342d28ea05b2c53a07efeb1c01029c08c861ee73fcfdfcd0584919bb2566a20d51def2dbeaed78614b34372af863032b36f9d0652a5390fe4a1299bf81c7217921f35de1b61b970d8a859b8842157c90a02732b3f01b89d3d460027650e0e63e1e8498645170b16e971d36d7b1197fd410b96315e6591a7c418fafef7c3d40085547c3a1541e25c4c4a0d041ccd64ad9fb5b4c62077693a81959223d81402eb7e550ae48e6bf2a2bf11eedc7efc341d8abe82ab66b0bdd53d7", "spend_index": [ 0, 1, 3740421989, 4294967295 ], "result": [ "4e54c0d04fcbe2f8563227e3b507bcfc0eeaccfb0bf210f51d7c953687b75ca7", "dcf22f32f8bef20606c4b2ab7231419160c98f127968fc2e3ba863c16436f3f0", "1b4456e430861141b7fca2414b2e1b87541f97bf0e6f059a397e48fc172be181", "6df11c86b4040e32099e38130058d13414f088a84824c233214620e958994d46" ] }, { "desc": { "Inputs": 6, "Outputs": 5, "Witness": false, "Version": 302150619, "scriptSigs": false }, "hex_tx": "db73021206f6d0829b00000000000000000000000000000000000000000000000000000000029ef77d00a31a210425fdede5000000000000000000000000000000000000000000000000000000006dde4a06001a771768e833772600000000000000000000000000000000000000000000000000000000d5dc6bdf004d544772a96dd261000000000000000000000000000000000000000000000000000000006b14449300f2dcc2d158f3600b00000000000000000000000000000000000000000000000000000000bd121b22006ea7b3277d157e050000000000000000000000000000000000000000000000000000000016e3e1d80096225cf5056aec98c620906e73c896add447eef93bd791d8ea403cfb28e25f4785114d9b180a314bd6712bdc6288a65d59a3c0bcbc78ec4ca2a870ca97b9c89791b3a2a7886bdbdcdd110235c949e32f93670779ffea13aaf76869ba36c388e38670640381e78b4ddfa859d4456f0aba6effeb378e0867868db0eeb5ccabc0f3380d9bdde32df0e27deb31a4eea41319c8e506206916b0324d3cb4b740adba3e1943bfbaddc60770cdb61c4acec167cd789dc921bed5718ee29610b75ed9e28df5311d9c3e18e255d5e08a13562fc603650c92593491346e0a78a166c605c8e877d3751dc11d3486775f356909d9b616172829bfbdc854dc858db69f3a6c0efa46c949b2815fe19ec7324bfacc91644f49cee6448535d08fc86d2218707752982c14d70e6d9d3cd0d10c8626a70cfd50b45a8b084b673f42a8e730b772a2e9b090460853776413e5463f98d9e4d377865679e5a9f9e8c422712b32d8063e06ef0cf7f037365f62c134e941dfc1dd019af9256729ba0dc24a60f34fe3910685ce892e72e9e67a35af173471aaed7b11f6a34cc9117140d106976cbbb825e5b32b478b52ba37862e046fc8215a992c37c8f314c6c6f54db4db2a29372e5bc8df7979487b3a094943f981e8f608f73eca10b8c98be884cbf61b6ec388a89489b8312b3c13ddbeb9dd68f7db35b29c47c30d63205a3ed4d4fcf41b37d6915d193dee7d2950c2c5845f4ce9aca00a440d53a457cc1454afe0e3b7ec978c2208fb55d7f5ce98d8b708b3181111c78ca981fecffbb4c733ad474ca7f1db940299108b145fed8e06b783fe266359bd0a3e299aa0d2fe1f1702c93375827228583ec86739024d72d7fb55b62a1bb07519b1f9ec558e2ac3240fe7644bd200b4fe5c271e63c897a952a0f19c39f161a6d8c391ad032b52413178a0a1db8edcb298f4d0126dbed8d7e3d4ad5a61747d3955565792842be7004ccb5579ca2d9c55df5297193dc6fd0118a4c6fcde5aa7fb22559a1e6de40a75e7c0c4b1d9523b2abb145d87bf7fe85988ae8739e197c0950dfe8718f9d1eccc0f6094993a39fe4db61b0e5f8a1ad1c2e3fc619e98cfe73eee0e048f181cf2542afdb9cccd59608dfdd3e4c775e592660084eaad78b4d9482436f7cf8e8fd030017b887831d4a3261690a088e9fedeca9fc0cb8e9e23924a09727b3c093ec8ddd667112c9eac0a33947887a994091ad6600b43df4515a72119b5ab2cf156affdd068d381761b12117441cef46e1588f18a6ba358282e73b7cf83fc967de9d76373a73c7decf3ad86017e5b4871337adc2a894fb84504de61163601e8984c18d8d238cdf376deddd927831f455b5c8897ef01a8f7f75f05dbf70ad405a1f0cb0c4928cd19d486d0154e5de27d5a0cdfd1ac7149d99a8296c1b000f8f11dbd8109338fceea23b292ce5a066869cc1a6dcd56908d613b80dc0d2900c8e28d7afdd99638f5912cdebc3ebc93e8", "spend_index": [ 0, 1, 3924639277, 4294967295 ], "result": [ "c130eb91cdddcae416e509154bc93a25ad565328d7ab173ebadefadf5e5ae33b", "7813f516c93db754f5bb5c415ea60f3b23600eafb55f85c82e0808f593c29d1b", "cb64ad463060f574be299ba9e7433bb25fc20d29ec3dabfaebe87d2047f9146f", "da80644e069e1b695aaa1c44fbbc2be53b7a5b8104f28965182edf5481fad150" ] }, { "desc": { "Inputs": 8, "Outputs": 10, "Witness": false, "Version": -1687061332, "scriptSigs": true }, "hex_tx": "ac7c719b088018f7350000000000000000000000000000000000000000000000000000000060ee53ddadc7f6e76bd1e7a19cc794861844ba6bb84193fe748aff616cdbefcec069fd78f98637b764b81522e34f02f600e0c255a01d8ea4cc243621695fbf6a556801168bcb1229cf436d3c589e4f2ca7f015999bba2d22ac41f946d9137f5c858788b7838bc95c38e435ad4a7912aa82043b1c5335a3e9d5466f26dda631761a98d57d6a43814cd3379e66c7235809f61fc5f888cce6a52db6a97c7640e2c9822c489eeb3f69ebe0f0375cc0865701a25a7c1e7dd2ed947a1c00000000000000000000000000000000000000000000000000000000f9585b70fd24019e7b1d3ceefea1103dc596eb827f524acaa0012e73c35f4849c3bb6bd8243898ef39dc4cb2264017ef1a8c0da8c381e9190d9d1610871f64ba9103a9828c14182c7f9d9b1e75cf4fa285333c00ceef4aa5a0017d3a04256a7c1aececdf5faa46dbd26ad8074277c4b44f257c4621c42d30404650eff423514e767ed57375172015f389fc8c988032420aee0ca83284ae543ca172854e0c2ea60640d52ac8f6b0f3530f0b22237ce5ff2fadac7dce6641eb2c8bba1e64216b413f3a78068d4f2f791148a8916020ba45735c8acd0bec26a79be1d90b34d960dc58cc6223fcc45d72ec84d90d38ced9c3f1e924438d687b44992adcef46b8411f90bf3f784bf74c29409278a3d769d2cf5a95cb03e74d55d26d96481e49b40a574869ba8d70e34af1f197713757bc2cb64d2740000000000000000000000000000000000000000000000000000000001d16dc30c0755267c7ed369038683eb583b91a6502c6221e7e447e7686dee46f5691b355edba357cf34d1451d64db554e09505fd6338488a6179a524fed73d39cd4327af7c760e3c7aed42f6d7b13f28ce0bef43ab6c5239aa67329629bec04ab57e4a2b8e4e8de786b7a689b95296a22254da1c284f08267a20ed790f5f0e956eae97876fb2aacbf89696eab0d63a74591f7a5bcc8277648c81319c2739b70e05f8b4b721ee2ebc025baf60e88fb41842b5d1e75acf7bb43499b0ded5a32aff3043304fa1948475de4f504f5f00000000000000000000000000000000000000000000000000000000ebcd37a1196e15ac4a12c4b7b9fb75bc7e9025137b360ee837e806d8f62eb3ff6b3ab00b939e000000000000000000000000000000000000000000000000000000003a24db7af3386cd1c52714962bbfe0ad27e211784ca2428c5042a0b3bc986884d746b08465ef6d15f40f684edaa976ebc352cb25bfd702a8cf255008df17e2fa100e9fa9a6be9d3b999b87d6ce1cf501e9afa374e4315673686fb6cc45e94ba6074c895d85e80eb90a3ffddbf3dbf56c732769cbcfd535c1b04e17547a04e9cc6a712cf62c767449bced4dd3b293b3a1eef8a59753b095faa4dab37da86af77c811c12dde71037500562ea0ebf2026b4808b845f84e2d2020b693bcd2598637ccf13a824db3626d242bc9d8d540271a72265e9d9876c7ddc58182c023dba500da6ebac6977cdff594dc4965097aa26901774da3cdaa1dcbd7b6b52d99112a99f000000000000000000000000000000000000000000000000000000000babf8dbfdb201bf903056b264b4f95f9004cf116d91f9345f3345eaaf0257f684f211dfe3b179cb04af1f9ed6465babefcd3233f255435e276755e286d6a4b5fe33e1a4bbd44b8b2c93661b2ce5866964f8cd2cb23768f59e0e25406e7c35ceda0b82e9d13194ece032bb957fe82559c6d89b36deecdbac9a52b8fee109bc644b746ae3dc230ad1c623eeb88e1d1833b3700b35c99dc7466b6877cae1e6b0a2979f28b4f9d3e6483a9c9b3a18c227798bea93efd6c9cf95ba0effa4faf9dfc213f8856b55d7eb7c72608c6b244621ea350cfaa01c2414b9678b77e0a9451127b63cb5fc862288bb844b8db8471b97380bf7c1aaa809f3552ba550a586fd66b26be432ca1e4f164e62ae3481502377ed31b0cb5d98052c24f9bc8ae49a873161f76c8784414a9ce487e8e69f8c0c2d4858552867d3ac64b6836b9d3a17f439718f1668f3063930382b598db4b275fe26a5697d0267f3d9d0b1e09a7371be7af6af8edc053d94de486840d3b7e22e79c1897b07dc6f35168e9a92ff07e544a5d7d2850be99e63a0cdb88f9f7daca9873f19701d003781460037628ebe09d771136cbc77a4c822d7b1b19d99d6507941d55a113aa60fe41541ee377445e9b233232d000000000000000000000000000000000000000000000000000000000cfd521400b0835175527d7a49000000000000000000000000000000000000000000000000000000008c55f71cf4d538093c313f44dc03719044bd4e227a18cf18d93cdc7ea20974ccc70f1037d23528dd50cad2894129ef893a62a96c7e83143288055ffca70277f7519deed5f0d925ea761a7be719c8eda1d35d4ca46a01e8a511fab67e180058e8ecf9f97a5b14972521c6e14ccef9b784a264b57dce5d3321ca4c5f417dc90559e3aea31a34c5e01261e9235614d8bf640d560586495ec6a5e3560e08373234717d44b14d1d17a7435400a9d82d26bbac519dd097e68fd1e62b1c82387c029396758950607cd43ccc0d67bf9752b99dfa87689942fc250399285818be8162ff120f7d410c6a01822f131c00e1b08f3a75d4bb0d3375ea78bed5eae296a20a72a56e1c1ab71857c85cd1c212492883e8f34959209c155cc9791711277fd392ba2d790dd766e3cb669cf6886aa2da75dae2c24edbc8bf0701bd208e5f8cda68901dd3d6801515f0af101b3005c935850606d014380a0927122442baaaa7021db4a1c7dd6e791c1b085001fb016228e037768c0f08d25b77b7143795abb8e80be5d3d3d12aa29d02456d291120ee9defe74c0a4738ace82b7e9bc3c37a5f4f7124b8e39775b0b83b6e47e623e387133ca355f52db30ad68a25f5f12d8eb5df9caf523c2aca59ad02cae6cd49e6c7823780c14ae56ef23c6c51c8aaa060f60adc3941e97088604f7af91101796ab38bd6bb481c8a4ca38c1f987355c2636591a8a295551b5c31b12fa682cd38ac13f5c04d67b61ec26100e53e2567ddb4b4ddd26189980a776d325d2b16c36ec5998af267823747eedf445492a6e3649f2c06ba0f270d9623f94538510ac54a0bd110be46788222357d6c0194dd75460b11e3b218a0160f4ba445c5649bea0bd65c6a85cee24937e4982167642ba2caf30aa92475a55bb8715957e1a986153569a5473aed2dd9a4d013374bf2bbe64a9cf003507abe599310d8a39a9423c89f043123462fb254c4a0d42fdca3ec712cfd966f948bcf1a7e49d8f46d66a88fa5e50f70960e456b077f88f2ee011f7c85c83dca4bc31a11d35736f2d07f6f3c4d6ff9acdc68cdc95a7f1ab69c40e8a798c780edf27fe7e1cad06c2c7f6e4bc5ad9b4cbdb47da45419b63a76ed4f107d7cc95956e6ae0633677a7b439877d5245635f4e0632d5eaaea1738262a98a5324cddc18d1b65d6a7b3d000c7c2ae907d2bd74090612024bc0a5a57b72252a196f1e77a32cc0b0cb27279534b5b90dc7b9bd3b70931a46c0aeb316ade6ad82a7cc88a91ddb56591e92e94976a261064b32722bb16f74f0e335fed3bdad50bffb94275fbe5966d5ed5025ee640cd549539b9a46d5e554dc99c994cb98f887533595ed95f40fbb7885254b2d27fe97c6756c34640c1a25725b3db799a270b0045c4545af52ecf5e5be50cb5fa8e611da245726e64a767b6a81a9da3073187e3c8c26d4081643d8e6568d5417fc2046ff8ac317d805c610b3137f08591aeae5452fc2a6cadd9c7cefb95901786fdd69dfb8a2fa9df5dade44c91bbda7d9dc60652ee8d9ccf611f72bfe2bf1a63fb1ec1105f3ac821f9100f9f26c1eba6260479648d261eda942020af70e5ccdd0187a3a71258e3ae599d5f2412f9d79f42eff7686a0ac6ce1ec5db43e83a1a3b37c13903470f88657e50bbfca4b789d2af610bb6f953b0947e1309581b4cdc80ad4b315411ada29248669d344b51b33f01749850172ef4fa38476666af61893b5635beb8e620dfd6bbf1b6c8d311f2e5a5b1691e2b72890aea7c7855338182d6c6e602abd54426f1f981babae8d5d08feb9422399cb2b451d364845f992ac3d69838f399b97d544346d98fe72f7f08328d38e854af402ec81e91c561bd062f5d21282a23110e47bd3af73a5237a750e722411e20ccbdc263c7a0bf39e9104592dfec629ae55852ee0bbfa739afadf79adb1a6e9bcdaeb5a5d8be5816ec6b2af6b1bf69cd5a74a8e203de40f44203a47680d8b8818393a749134ecb3cb9be883f13e7eaa81b1e949c16edd8d0bf53a8cac6ad7516acaa5f27d5e6a43587da16688e25c202673106c3b960b237c1c78ce7b4b98213333b77914dab2c174dc5856b7aa6ee1d42b06dcca012116b0c8e13d652e2ad030d6f1cec0fd6926b96aed81e96ceb43bed04611dc88279807ba111abf164c81273eb8546d27d3cec9844e652c791b76219c1ae5175e34812d2a0ac039289faab7f8388e3c1d0b2cf48c3b0735748427f9b74532406a2b5e2eee87847342b607994d2160a1fc9cd897d439a00f598bfdd10ee96c52eb97f28d11ca7cc2f23cae3663645c5e3d2268fe806cc67f27278dd99b714a5fc9c3f42423ccada1a0c92f55dac82975e5efc4017840074c3c3b2824c44acffc30f61c7e576432f4e318076719837bcc4cbe0ddb2e2cb53781674b04f62fbc4357a1c978b0ed54fc5bbc73981b2b9572bc82bba1c5a6c2527832729919b4e77d160d00fe00d6bec1db1022894af82f77e8dbd1c2cf744e6fdaaba9c4e4475e1cbf633861f800b4e2731cd08c8c9810ab2f205e7e4897b090431a40ffc246b9feb4c3db30277f3a37f4282b1038f8f1cb6e84755b59d9bacb22e649a56c96166a0cbd72698e7e2f2348a11e88d77c9a6c0b99e8e8ca7fb31e5fbcadb641b98dfa7ad9032fb85351549c4219355eb112ad37a40041e3cb52f83f9330edbe03a423c083f510af680425a0c9dcdf93ae6753a33b5446f7f1ff028a36c06a0e2b0310d45c8949810f77d356a67cb0676baa54f7b7973ca5f96926e81e7d6504cddbccff719d6ce3e6050264c25bc3d78bebd1dd9ba5958202cdf6f0953469357a19b1ac4e371dafcc0b6b60ba993ca7fbf8b85a342bbba015307be43c0766bed0fe5b2a24f38ef53ebdfae738a3f9b049a1226c1bc2fdfc45a9a48b7a5596e9d17d315df626c0e7f702f6f391033f2e2081fb4d7f30c5fe8e9d5d41b33661a6bdd9bb13ab0c953391e9552d638b38b9cab98b53ffda2ebcf648a4f8f82dfa81f8243e501320d5c3f5216ecacad8837ba6b23e1db21c8bb9dca41c51a93a29d05a5692bde298e8430996d4ef89239ea526a9395d38309ded67c6f1692757584ebdff6116977e82bdf69698aec3b7de080af9baae11e95eb6a8af80cbb587b8d05401b71c09e2fd94d0ebd26d87de8430bbbe011cfd24c632dee2428e13740785b2f628d5d2edf88b893e36886ac56abfcdbd0dba50bea6f41260c0ed55bc62153a28b33732140c7c9bae7fe5714e0137c1f7819bdbc918b9fa8db7094ab68a26c7fa302c66d9076948c9de16fec03f1560d217bfa08d977bd7c920782a1beeb143313", "spend_index": [ 0, 1, 1946888704, 4294967295 ], "result": [ "a968e612c0874ba3edecb15319b9c5655f1bab0396f581c8c6d036a681c44ec7", "f8aad49ec5c23f6887ff71fae9c60b1fde351d9acba75e0dbb12929d20d2eec8", "a2127631fe7b2c06edfe99ea1573ed54d73ecd214117dca3abd554e2745cbb8d", "ecbe851e616c023747a2cff919fddc58d58d72cfcfd4073e89ed4916990fa69d" ] }, { "desc": { "Inputs": 9, "Outputs": 4, "Witness": false, "Version": 466173704, "scriptSigs": false }, "hex_tx": "083fc91b093e6908ac000000000000000000000000000000000000000000000000000000009dc406fc00bd1ed399a0e5564500000000000000000000000000000000000000000000000000000000f9025e3a00b51c5ebd1689e28c00000000000000000000000000000000000000000000000000000000687d327d00502897bc2442a3640000000000000000000000000000000000000000000000000000000020b3964a00cbf69cf982a67d4b000000000000000000000000000000000000000000000000000000003f37248100491e232e0b787ae100000000000000000000000000000000000000000000000000000000a697b480009ec707e1f6ddf5d50000000000000000000000000000000000000000000000000000000017a68c6a0015eaf38cb5920fec00000000000000000000000000000000000000000000000000000000274717c900b98d1d47f3ae766000000000000000000000000000000000000000000000000000000000351dc86700c92fdba504053204d7588ee516c8d7f27d7ada3183ab69b437bc1c247fe38b45960f2b79020616dff306e6d97a49ff6e26d50b2e03ea2d7d9e6fe6c1e39c3f481e3d205a48ad844ed0cfbbffcb6df49c399851be6b4c6fb2f78dae553159e76836efc3fcb3c0c0ee1a1c647e6c54adc34e5b85d18c84912ba431746d453480f1354a1e1466e25662a38c204521e8e5d9a56592ee2360be0d81d16b13988cf3cf7f6bef2aeb2f9cc875d66e93fddf9c2786064ed48cc60a572e5843c5da56ba190171bcc794a88dc36e0a8b9e69bbe31ef43b43aafde09b6a601986e0a871c83d02a483f8e2be208876186e745102161268f69e88df59884922690b08ebe8cdfb5984d79a8e0e7deb99599045d139bae8ed217161f0cc4c30cf5a26d5d2a75f5c3fa16b70cc9cce715d7e0c5a3980ca5f32696c4b6d2db4f5b78304c5449e0baa041b7719231ab9fef77c1829e52c6fcd227eda54e66babe849fc057aaf9dc406e9acd8842fdd1c25844970802d0d75e29bd0bc11dd9be6c1801b7771c888019845f32e83316cb172d211fd3a09d70810899f973c23ce067fde902eb00b84a7749e5d95a54294c3b729b574ce63356bc8882a71a728f7667beb7691f7f09f3683bd5033ead48116680c92208ffe9e3cf6e1893c628206a7eb58642def9e072ce1a557b15dd86960752f9c9573a1375cb16875556f8f43565493a334b5802f526b601e6bfbbff74d179060b879db6b90ba3d6a2bbca1aeabc85ded93a792ce3e3ae4ea8b6fc745c263b3a12e4c3caf135ea2a9c77587d72557132fc222343d6c4b1711f442463da69e9fde09050a77dbb6410a5e004ab8c8688a5832921c0bf10a6d4a186cc3dcd09c65d0c9a20fa81d3c364252a1457176ecfdae27dcb1dcc713c89ae4407c4501ee133b0bdb910ebb21a589b604e975e003f211d368e77e776025c8765db287e9d6d43dc622013f04712c29289d88973485d7f3188d86ba86326ff11dc11f2471646c883cdd4d84583f0b11b90603979bc4fae082776b51b0e4078d85e9cd8956bdc47352904da4dc55ce41a51e97b24f130f454b5be20099e8d2c7a10d5e98b568c4740ba129127e991c673507864109715733683ae996585f6bf3d8430ad85eddf50326f687b6d852274f8d7296f40812761f1c89ca8b38008457d0c794043c6bb6b8882f27", "spend_index": [ 0, 1, 514404503, 4294967295 ], "result": [ "2a5a5d8d2af0c04eeaf2d9e142ba09054cda8a241fe9528e36760fa8fc98ef83", "dea1e91a4bdfc44486a6de284882c31ad06af8eec2f504297d418d97d21a2a71", "601e9890eb3c45ce8b96634ad59aec943207e81da307268193391049bfa7e1e8", "ada6d4157e399a0b9eb1572320ee47533c95432e06ab41bd074c029d40fff18e" ] }, { "desc": { "Inputs": 4, "Outputs": 10, "Witness": false, "Version": 233800700, "scriptSigs": true }, "hex_tx": "fc83ef0d04b7e52aaf000000000000000000000000000000000000000000000000000000004203eef760c2d9d5d95108bf9500964227dd7f892fdbe8f89de24ae5f582cb1b62e5a4c8e22e02e339634d17b7ee8edaad546eff10f9e4c2ec94adcace4be3429c3e23e5671aa48ab5219492079b5513ab33b5fb9c9983e86dc0a158f588e6fb5a001fa02f9d460ae28a1ba3210000000000000000000000000000000000000000000000000000000019a9fee7fd5801730248089cf34c385a872f5a1d7f3d7dfe9d63fb2ecf32996f18a2adb3d5a9788f1c1a870c52c0b15425951b365092dd6e471503cae974572c586e945120e380a7c9760ed66fa5ae3863b156e435cc73c5ff29c515640ea530fd4f5bd11ad91c8b69d66372f6328d67a1fbba2f643d80d289a01d55500a45f5fd60dee6febe6964b2e716693ce33f1e4661ab450fbdfc17d418d774299f7a9f6378983f3fdd525e873b2fa8a1776b7afbcd326f80e0e22b3805d7d2799fca6c95ff1a7c53df48f4d1108f4986b1e9f1306869f0f026bbf3b2c859e3d966641ea4e0a49bf2bfc05e9ad33b15e053c1ac151cb28f5138664d91581e55c9fc4c17b3851928b34e0eaa2b05c4a9cac136e02abd7ab514ccb474c89fb6789f809a2529be7ea9e500b38f50d668993113c57d60623182c3a2081ad6e359a415f865f5a65df2085ba8c8ec6c7a7297915372b3072eaf844d5a29ceceef72fe73e4cc82d3536078b4beda000000000000000000000000000000000000000000000000000000004efd6740fd4a01cdd04b07fc9793e79911a0e4fe2fc5ac2166d7a857124945025cdbb8ec5b0986c2258e1c28fc414c819f702d74d873595dcc2910dcf57fc7b27363776da98e60fb085196bbd9f67e2fc0c70cdef61aee0156d38143d57987d8bb2ced0934c8f6b070215eab36432c4cd05adee3c3c0e5cbb2eb90c50b7c6b277f995e22831484d0fb4a8497d86dabdc6cd7682c55f422e3958de0c0b64ab58c77c27efc5b0c4cbe1554f002586de4d3e35b21dfb02fb39058967579d7e780e19d591c73ab0a48b2e0d6b95f708a4b8857ea4a39fdeef37ac7bdde08642c5dbbc5cea1dc767a576b33b45c844cde2f55a064da242367bebc319117c43bc962e273babf68c98d14cbb4d512b7efdb6128a58c44c7114a9600acb792a129bb568d70ccf4ff3711e16bcd86e8b009011ca257bafa003c6c89ace435785a3243e3860cf626baab93bad428b686573b3b1732563a83701aa598868c0000000000000000000000000000000000000000000000000000000032317a0bfde401d7631ff85de0d890f36d4b7a1da07fa83d05354c9d44695b04e1732027e732c1998957a43049603ec3a3998a1c3764490a6115f53f6f001bf281ba504d8a4c826d17a1686ca2cfe7a488fdd8b85b5bafa48a932c5f11dfe03293ca59c47f742251ba60c5a44b8ee2f15e9b38121e4d90c8def01d1ceaa877e21e1547085212ab226af086eed854528618d0e19e6924d5e8970b5f7bf178e94c4cb63208d0c316946c56bb46b1ebe8f23f61bde981d661ede6c7fd5fa27f948baa7b279353035570c993920091cf6524d110d44dc94bda9caf2483d72ef3f570ce9bf39c65d605462c602061e4abede479083e0eb5aefef32ce7f5e9b83da0a11523a2a20908e482598ae22874b29fb2d4a17296f3c924a42d84893fcf2d626e949377d001aa2f0020e686ab764aa6589b303a87923e3c166db609a440bdc4eb5c762c596128e9cfde3ac55161236a001a9e4b583e8f3bf3d5675de869f721acb9f9a80741b1d28875323658ffbc2c14258c790af3c9c58f6e1d229200fd3bbd8cc0ed54270bd792ef797a08aa69e132bf2d3aa809614b6e1c086a812e84250c58fdc5e9120a1d780338716ba27ec941ea97c5d0b3fcfe030ed4385a2e070806dbfff1c32d8102c8feb9d65fdb23bb81cb1e5285b2ce322971d1e6d86bfbaeb95fb29a22e25475769276f6edd89aca0af57943925ef22541c86c9ebb6ebbb38ac2140948c3ce50c34a54d14843467a7d07b70cdec88ede17fd2fb146d65c9ae8cea0453850672616803e4bf80bd092199b4202f86b14a2a976dade99795b977d409897e0ca406427d37a45500c41208c08c4194587b5dc9f90e542e78c29eb4f6f8c283f7233685dc3a34394c01e8005b7b02c09b852066741347b42bc9a900ad970e4487b63c7710c7569025cb4d025a7327b00a926f02be4e4c30198656c510cd5219908f7bb6e2d84a33134fc66c7de2e5dc722b73e39480cfb3069ababe48461760b80ce298622c8477aa3c3d338fab24a3848594c14271ea483347a1afe30359b3c9ac1253dde5fa7012ebe3d169e04c85cae2dff4636628f4087e4e2f96f1dab62e7b0555a63d6c25e50c2d3c045865bdf76b1e7f730f3222d3ed3e50742d6180e2d73cfdfa8bcb7ed37336a4826e84cabfb61316e454255757dff3e4c35533b7f8abbb555c2728ab5edbc5472e362aef4920c0899271d1795e1490bc621e71c671301c44961e6eedcd5400a19122020e9093022cc01095419de6583c49de37d7fe720ab61d5b3f678e29419df8d2a13739e5e26428520c8a48ef7347a4ee8e49637a82ca3cc8f885c32303aed568d82849a8559e96e158b32bc6c2d74b0c66c73fba609684e3d01c5e1a161e9249bd9239d57e84ce27fb766b9787ec353d84039a7ff4040e8975c57572d6d382ba65ff6cc6c6432f1f924efdf63ae2903f959daced0af629f8c80ee4d61707eb4b3c030de99b6869c01fbb1e07bf7a5321b352f99d922eaac5cacddc0b789d245eef8eb7bf938368df405c558f7ac01fb01a78b72cd7cbf02bc85d60edf5769e1b653b81e69133499b915d0bc442da6ab8c1f8778148d9cf2da1ec862df77f2250aa707750bb606acad444d1173ef1eaf6a82f892c7026e0c0ea1a0d18f449c6cb6255b95a11ecddafe4ab15cd483399baf1150dc79b5f294e6eb8253fcebb293d21de6adccbd4950f8e6f12f3aca441efca113a7c59c1badbc8abecede2360edd1acc2fe2b2b862dc48ea4535e42f9fa64d1b3f27282d0b6815cb7e3cdb12d032bf562b039c499ef735f65dd82b58f8aa65007dcae541db4ddcc50f935b8f24eedfa5b208d13000ef9c6725a7f85c75cfb9a1d646b675f4bb171b7f446a24498ccd0dd2656dacc9f72e330c8e697b15d5c88c6effe101a8b7ec63352b86084f51c94f4b3dc4f58292e9ed61059e8bff5c8d3533627808edfd6a16f07436f131007b81b69024a78dee9b3adfbe56a016cad6e93829e205e7fe949a7cd8ec0a84f0d4f6482302b82f03592279d1900b31ec56908ebe11442eff5c4f6a2986910273898f433e2856843a5598126576166aa0edd4e38a5d074dd2d039e349cb4b17a498ddac2da07248c24bec883ff17e9988ee69556425ef25537d06b7c7360e983ca381eb6d55328a2ea969875d5fad6c2bd2593d4e9ec42a51fc4ef43c818702c82d7af73a492dbf992760d2fffde226ae9a65f14019c6d451ea62adad3e8e1db773a901ecc1fcb8c376c0b899dfe802315228ad19dd6749ea0d1b57bcd7662616ba9b99e822225bbdaf0d8a501afb3151c9dad127d1b6b474e1b4b4c0a967e067905518603124dab7b59db38d8a3876e24ab5bdb987b575e9a986652c1c7c71b684359a84a48332479706fa34582d1e5388763ac1e5a9e9962797083827a545cd82a9ad1a4f01436825ba24c198e88c1c3ecf7861919908f29d0cf0989af3d11d5c42122edffc91234adbb830ec89b4a5db9df532fb94d768ff597b3bbecc5bd78a709617e6ed71a26784894d751d1232a851e84b5dc943916e4733a303386d669f6b3f57934044aa5cafefc3a36f0fbf360653eb2fd5bb600da9c5f06947acfc48b98cc79053d3708436dbf47b5f3dc77be78230387c81e41095762a9cc3c53ea44c3a49516886dfb8a41050e4be03b31385cf4b51af20e8083edeb6092b2969a8a9e974fd14c93d025c77a1caaec8562a1bd1bb44dbf21286da4e8c97a93f575ce407d0a268a31c52e7f6d98934195c827fd4c91d798a2f50ef12b7b6ac88c01f752c889e795921bf829b38d1607ce1a84e978f5f4d39ace0ee956dfe86f6cacd46ddad231d4cdd81d8cc097f001de7008605950f862a888f32bde2bea7adb920ab999fa927b04e8d592efcdc11ec62e3a7a7f99ba26695a1a2e8f794b9fd5e21540d1e3ec03cd8efd4d5337caee3a71d12d28d2bd4e791cb7ac7fa84bb211ca999d991f47b2a2db39f614333f74ec0183d42be2b31131c5ae835f2920968548e2834d88f58e013687c2ec4bf5ddf0a1ca1d8ef2f4073ed281aacde9e16ce649b793bd0f9eaec438abd3e7f7c935c8a44d220ce46cd5ddc6d8af38d400c9431fa5028e80fae7e962361082922cdfb2b276f88fe61783e1b9da26edfc65a3839483186b8725f78f515cb3ddd86db8b79983aadc5e9e8ab689c240431cf1e9453298c66964ba0e32e12754dc109e4c2fc8dccabba837a4b6fd00182a17e615f9eaee345faf7a99d981b4ad04b22e62bd5a5268cc1ab37ad1b56402defd4d13cd65c33c7cfe0c9382cfa22504cd3d789da2f45ac68037af47954d5fdeb33983b7c14ead5dd99d6764da22c7f22e119998b58593f4c15d73acb636b27d56992845c868d1b46402c1983083d6278ff19f8503383ab0cd7071da63a4851020f74efae494f346d7acc626b4e097997661d24ebdddb17176b723f3c311486f86bf9e67ff524837be585a48d009bccfedd923255b44e2c66305d7b0db3113b830105d4231cd357dbbc3dfae5eced32e95cbf95a85e967214285eb1e4175b51d92348fa5767b053611bcfa84fdacbff4d6206e12c2b361749aa5c41944b2946d90c02f3cf463474c365ca4eea67f342e08b84240db736f08807b11ccd4d76670a60337932ef31bd5d28fc711332d46b983", "spend_index": [ 0, 1, 1012000868, 4294967295 ], "result": [ "fdc72b5aabe68203dd0dbaf37a1ff78c3362791bf9527ba8de717f493e233baa", "1c7402a155fb9201e164dece687fde25a6b03f39133cf72c1b6c3a912f357baa", "42c0622a740320dff800c460722a13359a020425d4a7f1ffc0f6675026b22334", "ff35ef313d52de732a2678aff944f787a5d3f018cdb12115c19fb28578da9d2d" ] }, { "desc": { "Inputs": 10, "Outputs": 8, "Witness": false, "Version": 1064018199, "scriptSigs": false }, "hex_tx": "17a16b3f0ab40e831d0000000000000000000000000000000000000000000000000000000044bdb289008d1755433928a3a400000000000000000000000000000000000000000000000000000000d30c788a00cddbfaf7cdef7b6800000000000000000000000000000000000000000000000000000000460e6b8600291cc340112862b900000000000000000000000000000000000000000000000000000000fa10e4d900b9ce1c6bd05fa09d00000000000000000000000000000000000000000000000000000000dbeabe9200461f00e8967ebf7c00000000000000000000000000000000000000000000000000000000f4295fce0006df8f31488df2b500000000000000000000000000000000000000000000000000000000f0c4c7ae005cfca7cc9a71195a0000000000000000000000000000000000000000000000000000000048f9d0ba0035b65c06a0712f9b00000000000000000000000000000000000000000000000000000000cf7dff6500d925d393cd2036cc000000000000000000000000000000000000000000000000000000001e389110003de7c87f08011311cd86f0277ac857453c60d9dd63b5e7f0ae592aeef838bfed1bef937defd8b275adc462e498ed93153cae785c7c015be5a7f09f209e842132640e471f23547ad76eb5c6fa4e506f119f9929ed3427358d90d88c8e92ed0afd8cb9297c705bfc0fb7191d6160819f3ecd86833eaa4325a8db1cbf33fd36bc8ff922be21c123850c5e521b00203e69064a4634a5b448d012ad88c37fd30312c75c75bb6f8072ad9a6fa2c490d44a09e083c5c33ba352ae92a7f25fd9de3954fb267875b6121cdb5d0f8019387875f6a044bf95994b6c372a5f8824b1c426c84f9e3745c5410180f79cdc820f19470cfde0e6a5d7c4dacdb58ba5c9f8d7ee2fc85db3bf3d580fb0179e0bb7c45b21c29809cf13c21cad38fe27f49593f3b110ceab98da43c4c451258d81cdc998cb157262d3ac3d9f6d6d15a86e6373aab439be2d83961d1fc0cc1e7870f5833b05ae4b1e557399c408adedd0fbf60287efde883f67f64a3c7bd7e24943be1123ba52f55577c140783b1a20f774b5f099cc6b53ee63449e95dfed4f51a281e20f6e7efde38ac79ba32684727d3f7b219044cc17b0517b2622098c6144652e2960880fc84b700c55d4503ad6d4a481a0fcda1fbc1e90123da7ac4a0430f349ff5afd4c2ee2ef713b451f701b80f77b98d61dc697237612f0982770c49d69682e1eb009ea26ea561d47f51321e346d53e06da65aeda464ee98d27a769bc92afe93d49892f3e7abea82b459b7339eab64a7beb08c44854c309a768d896ecb0e797551dbc6d21c70b488017b9826fa06e681d0e04d67f85ceed3fc406b252b5f74896b25ab6fc67224a6e9768155beac50d97b66f13d4cb47a45fea4dc299f5d0282a2080fabcb8cdef66f4a10767ddd274d63cda14c8db3ad697bd2a43590bdae80fd469518a61abbc73450be68855ab442f2a2b15690f682bf7b1c8489f34cafbf7be712b8b05b495eb1d1c0f6b73ac2e954b639e9334fdac360a7987f4ea1dce69b234f22398f3f0caa9dc7c831348aa5641c8ce7133e2648d0a3b52c03599454d01fc58140dc536809a883f63293390faf3a4587f72202866e0f4e8acf47f4bc4c6eb424a526a9adcd36b4541171209a9f69f30274f2ca27cc7494719dab7070ab4df23c3175783a18013b9d69c811edacb2f4eab5e1f118cff0bb2f76658dca537725b3bc8f240a320e32d496811ad9a68e3224fb58d7d3e4135045aeea58d49a6bcc6b95676a09459242da680c4caf017b7d2415708a141d64253f50234207205712c117c67b8221d2aeadaa3a62104de2b31632b82cc1decb5e69e16c5c942b57cbb999c354eefb6f09fbccd59ea85ebf83d48eb06d5ec7ef4e07a80c976f953703d4a57ae1e8dd20ea6dad831d21ea5add18aa169f66a886b200b252ca5991d3d25c56d17b6f1558c3450d6e3e758843a2976156813d4d896a80bd13187e20047108a60b8e349c3b649d51e2dc0b9309f8ddc57c8fb590c74e1ecff4ef21b8b8878c155672b1884a07fcf96fa4a2818156b6d006816221bdd869ad734942935b10dbc6c5445f6b1948f914ffb0a55861a993bee37f615f80654d5514d1540ea30918fb1ede5f37cfb3a38201f5cefb3082e3fc80d99004077da7a9bd7a4ae5f2bafafcde71ce910df384cb6b6013ad9ea302adbef6147e0f380b71274b33e76016276ebd61df07c1c296cc71bcd425d3286beeb0bbc2dfe5c1031a0e5700bd29016a3303a048b012c4d8a1a11fb3bec23518699c7d47858164af9bb581fd3a0360e5ad16dc8cddabd6aa5e7ccd0260ff50cf04646222b08c853ff8fd4582e83918d665cae48a924f947d02562da8a00f2f19b1da5c1c6699b6c92ed7615e81357a12b1b66f290c4b82001916fe4b4a53a1308803357258c4a4c4e3cd8a9125a87f3acd4cda0c67b99851daff19108f1ee8939e981c6bf0f8639d8e1a51645405e78b8d07d4396a4914e8b2f0715520559bd74911a8f16cc77d46b17e82b3d6e29ab4a87bc9c0b71ed69609e745dab8a6b851e5a183c16c301d631f02bb44d2ddb08c182611b2b338bc38c09e4986d9a69fb08010810c82d5ccb737cb4fe8177a00930c4eaed5d0e937129b7908064bcb5abe64333eed5ed5d2891005d58de559d2e8626768a84234b296f2a5a3fd8c8abed1983c1b8c184a98ea23f7a5729beb24d1410090755afff465d78e17f542e0fc19a36344bad169ee18e7cb200ed08f1abed035b1284af52fe1f25350af3fc0427a7b266ac5e58f83d1570016f74db68413e12571fac80adb5f50283066a509bf27fc7ee459184a95c6441bc005bf320deed8946251a8a82683278c14798ff3d9b2521187e104adb1d520ae90b38f8399e5e", "spend_index": [ 0, 1, 3173180552, 4294967295 ], "result": [ "3771f95a8979cebe0d1f1b6eec2f54226d2a432ad54d975bd71befb47810a34c", "5bf8f06db72fc5eb93e55cf6725d504aac10a24e5cd3dc9370654758e9210756", "19462d64e577214d14f1550e312db8f57feabc5fdc850d51585e7405b03d3692", "e6e719ed457021afc2de1271af2a1be2461627d047d0948e2f7f47d694e92999" ] }, { "desc": { "Inputs": 4, "Outputs": 6, "Witness": false, "Version": 563167293, "scriptSigs": true }, "hex_tx": "3d40912104388256aa0000000000000000000000000000000000000000000000000000000065971d1afd0901d31e2e46c0a53e7534c44895bfb8ccbd34eda968f1efec0770c1fc4b0abdfa0c79d6f7d74c05842a6061826a1926c5525ba7f89da09f8fdda8466582b81f203e39ca696f1ac39008427ed21d407b95714ac65c1abe7cfc6903916c42a0a0e8274baa6084a8e317d4df7ce2443a85e5a13722547021eda174b0b3142dcc50fd489bc16fd186334f893ffb16d1088bbb80248afe97202d455f9bb4fd7409ee677f9a5506c2217392b62a2b419099dfdea1b0abb6c9c179d6698ab6ee3f233958b511c220bbbd70c51c2800f2e7ac473ba9cfa5c91c979e1b619dcfcf4b9fd8b1a4f9742e5cfd90ea357781a68193f1124405faeac1490136644536c6dea31869b12889cdb240434b12d994798581ddc3cd550000000000000000000000000000000000000000000000000000000042c08f8bfd7101d3c5ba9fcf3d95716ba18eecdfb54561471505c26ac9d6c3d72e97f8deed33a5383e7662f8da2f812f802a6931a01368048ed1a518ebb4dbb8c3ae0dde3d00279bbb9edc3199eb94495306d0cf67caedca41958fd89e65c90ba8880cc5351f2e966fd8e6682b9005d99cd193b8fb32f39b0ef689699566da3eff816307574949387abfd7d4da1749fa7afd7145f054c34cfb45c59cc618f947650450111f25fd31bc800233bbda6e7d7cf7577192f0f4d6d7f78c771e6fb1a9e84b3d3e9ab60ce8289515f8a149469ca67d8f2c10cc9968c72b203fbb6cc239d945f5820a21f62ebf419f7c49d3bb79b3d51feed9dc4a3ed93fbe75438a7e282cae27b40fd3a04d4fbe5566349f2e3ba757c4e9bf9e9dbacc2fd6e32bf7f53410714b660965d197c6f091251385a71321f949d2296193eb186aa23587c00ea43cab68a5def1c58cf6bf08e34fe4db6d69cb0a8ca400b2fac82194907d2a09f78796bed876256b74a8c0f253db856de71d10ffaebd7b037dc5b67b2ee0b3434900000000000000000000000000000000000000000000000000000000db0adbddfd91016851b0c4df06980c4e9ebd072d00019865043f6bdf595c8f8dd2f15d78025c7f6d8eb5fdaaff7c3b83e2411f851be671bbd8e3420d367be250c41da4a58ef721db4116381fd725d68bd560c71d146ca59211c2331885c7294ff7c829ff2b00942b2eadf80170854e68be35c5cc921724f68a6ee96c306c68f9b9920c1e68e23901f5e5c170ec871e8132006d762f1a6130ba934ed18f27be027d34761ee5c7686cef5597870d9b652d4711c155d1aaad9bb7cb9d5e0b16eadf6e19af1cd5539efb13a222753da6df0a9860bfe3e42c8dd8f791cee12fd1b3483391afffca1d0d9722975369efccef028480adbfae107df62d18a92e33ce65e68d8d0ac212259755a13409662ed350c6314780348527a3189aeeacf1ef3bf0af72a23e9937fb8945df0514897e131ae1bcbf30113c3d5c657e2c80a3c666e36f730c68ee89c58de8f0ddfff4bce478d4b8bf9d92fa9797f0431d8df0221d6daf47c90e998c0761718a44a4c11f4bd85e6a860c323203391fb78b2002b4efc56fee4380d176df834e935a32bc75c5f74d8e4da1ce671e3fbfce1f3a306469d9b00000000000000000000000000000000000000000000000000000000024ef503159da57602a43f3d2d9001532c98ec774edce6374436d95e3adbcf7c7eb75f17fd05599270f4cc01a0674e1cedd6c19a8bb079bc927c16dbf3c2264b6def9d86f0857d4e23d190ab958fcfd26e518904863dc91085ff0fde8beb21680de4f0602805a85d3620c00c8bfe332e6b2feac297f46400d5780a1a2d46be232f49f4a366db1861bc87400259795faec7db3d6b499b2b3a60d8f637716d21ee5b267e9de47deaaccc913cf7444a111548e4f7ca7bbb9eb58c43395dbc70332fc3affe5fc1031ceff43468411f20bc3981fec2b5f0ba7ac6c269aa004a0952609dccd00b63e7701a4daa60b06452d2bda5a8449eaa5fa9a188643c75a40dd55682912d88c4d61729b578a1a26454f252982490b7199d00a6a0c5b5c48a0852e7c3415b572049683dbb57ba527eb141e5b09b766ecc40fde226055bb0cc8ce43ce3b423332ea000e610239d70d88b76ca43877297f5435bf505940e3d623c242b1e1961489efe107646a8c7e0ce837eb4581dbc7fbd9a56099181ad82b8d8290b9d18154dc34a3806302d9adad751938990aeb2818b20fad15016ace06919a9adcf24e45f37f3e94a8fc209a6c9f07d932bae5d1db804a06b06a004c7db146e9f55b2fdbeae59e6e84f844e15560f376dc956369d15c6c11bd3c720b9eaefc5f5e61950db33fc732b0a1941c9e524715638f2183d49fde432d7f2df082b5ddcd7a4acde97d06d5dbf43b82f2d326c85d81f49b1aa39f3889cec29490433541ab03f0e8e23a04d2affda88df42fe602e40e5064c27af0edc2488e4a7f4623e664dc3730af3776247b975e98868b494f865c482c879dba23861deefe7a0c2a4769072cabf7340aef83a3f1f9ade46bae0f00c0cbaccccfd601e17d9c7bd678582af88020b799c04053181c33093f61fb8927b6e032b0383a61a9d1fbbf585301b0eb8ebbb7ee96606842d866d393eef4b0eb066e47814e277cf1c4e3bd10c608515b15f5501d32badaf9ace6285ee6652fef608bbcccbff61a55b15b2ac6413bc8ef7232cf413326da9ce54e4e4e605d12f025fbc5eb1d6a8694721d18431f3ad5e67fe1aaebd39cd51275b68f4a42bdb6d7c323690c32eda3682e583b7b542c41694cc4a8a0de5272c81c09152de7790ed01e3809ea25807f296db08219773e5ecff9967208f79353dd52b2af31eda542d095c189b843118cbbc5c9e990866aa5aa406c8ac573148557cf384fe950fa9dc3db0314dccd1e9a07ab01088bc32af3010b335f0f2c466710837f9109b13f23f4da88981109b629a66e954025bde287daedc656726f08b5d2c71cca97549555c895d265117203812a7cd687c53056ba25f924a4bd3b0970162b9470f33c5c2912e0f178abd5609bfc898eda5f73d54ec474e4152b205c8cb5db43a63790fad88d76c3f1b28d41ad9b80dde740cde498d4e7fb13d7794c2491f524b186d7265873a016fb6ef7911c1b665b3cdb8f28037ace8e1dd55e50f601231249bc7d663dca77fb711084da39cb57076a3baeea27c67a418c49d1a87853eb20bfb934a71ac66b6e3bc98cf781519bdf8bf1714113edf5cb6108914765202004744a3b0832d37549ee983f4f7e8bf0602f405524a046c80b93f3f4f121310100227d653f48e72cb6ae007fbfec63235432a543bc98f7592210eba0f8f6c80e1757460727660fc7cd9f6339381189bdae7e511f9b3e7b14c46562a2c6553aac2b59d6faa4c4e2e9627c28f42f2f914be9a71f7880e4229be7d259a0047bd33f6276915be97d0d84c1bade71e32a368a0048f405990fcf8362a4576f50d3d387d8d0a3914f91fe80c2534b9dca75eea410643c5dd660a29acb0759b0fa77e7587d65ede0d6aa9993cddfc8b8fc0e30aec481457cb5f412b04f3445b0b275e0ab96a8d590", "spend_index": [ 0, 1, 3730060837, 4294967295 ], "result": [ "24e96b4a4e3f89c2bb481a551862da16c22c5f6c438ad890c0165e3e07d74fe0", "7a8618b8e1b73c23865ab6852d76b972cd89cd6d917d1282c0a158c7078866f6", "6aad6da206cfd5fec432e5a6c3f90fe4696497c1c74d9921be54592795aed984", "969a11f68b297b12bf6a4d26829f9360da3081ba2c1ff5e2c142d1d1c5a180d1" ] }, { "desc": { "Inputs": 5, "Outputs": 7, "Witness": false, "Version": 846211581, "scriptSigs": false }, "hex_tx": "fd297032059d8f2e4a000000000000000000000000000000000000000000000000000000006ad4927900724e9113e1539ec400000000000000000000000000000000000000000000000000000000affd749a006c86c97cac51bd0400000000000000000000000000000000000000000000000000000000a95230250073aee47e2c2c13d4000000000000000000000000000000000000000000000000000000000cb58c5600b5a792b6d0ae8af7000000000000000000000000000000000000000000000000000000003fa6d19f00f0f1b7f707e7783686e4dfbd51c8fe857be958399ded2f893d90665a96953c95cb37d0d6ca11d5338967f9ea564774258038ca5132d0157c1b4088a4b6bb4b1bf46d644304ec66c9c6a19081bbbf428aa322c0baaf9f98dcf29a922a2f7ee41187112b587b433975c77d87d88fcc0be07dd76e6f14032e78432e7cec4ed15a77ccf3fd575d1fa216c16c278dfb49cd45cbddc73a8a9833528844e834d7a8c9f44be368c481aea78a6c4a32c950960ffdbf4e14e43d3769bb28b5e9809229561e8c0201dc8e5d27574565e628911aa81221755bb7d470b1c6d0bd185f862bc846ea1cbd42f30cb2599c50c38ab47266dcd373b4233f9fadb5afe00b3ea9d22cf2b4431d0bec7a5686aa8b4bf2a01ae8f8e7b91221f69c9d88237926274dab45b0fb2cfc7245d8cec4b8324c38f7e50f9f93eb5bcebf24d54a2ba10e3c88d64a889d7ef4e0fd4a55fecf3d8eb2dbf582c1275d0f9cc2cc3f1ba6bdbb33fe2e2ce8478614477363b2b5f7229fedafd3ff9d13ffe353cf49f12284d77e8a6943cabbf7ec295976312b7ba26b96c23f6aa4f615760a61e471ceb1690e54b30592fd63e84ad21c71e92fa8d2f9d541f40724c8daed51f21a7eea2568c7b3774e8f6cbe9ae1d65ba0cb826ec9c235c1839bc2fec4ffeeaaceeaa0712046d04214a5456421e99a2eb10b18bef429997085f3fd674610dfc9419551191f003e96125299aa486ce35448d2df6e9aecde943f740cd4fbe2b1503d41a2a1233055f64f1ae44c9a0cd07b3871e72eb80e7e5541ddf87f85713891fc37f27077d383d68815c7a628e05ca92129e856f3e1493b9dd49c4ff0b4ff42d81791064b1093ec7a6704bf7da9aacd5822ad1db5d3691c8ee2b46718fdcb111286f5c273e136ef6db90601c8b349d7c33632ae5537af353a80a359ab89cf1678c05b28a702e374b18f7ae18bd971e8776fecc319986a42a95a39366a5add38c31ab5369b6f9c2c2b9947af297a229c21c5ca69a83283c5964656ee143c575e3b88915fbb3d8350a8f6471ddf2d0d4e26f3a4bb251c679a26a764a68e2de0404569e316d663a04283ffffbcefc3487f2ec84ea96fb0ba8a80f96a48ce4d8d42d1f44e3ca4664afb94cffb0e518f691171fd4bea22c006ede1c9ab558b023474ec51352bdec18b1767c031687dbbb0e9ef59ba9edb00b249a06e20ca17c8543b6394e1e20ed1078bf9df0c1f98a032de907a3fee041093a1b7d1824a97269734cb907806c1d3d45ba44c9770af78c118258ca24e5d36c1e6a39f4496fac8f0ee866ea8a3b513b3ac5fae0444044c02374795293d50663cb7bb01855b82636271803331077738d6983344b4a13b95afce8510a709df3721599fbadba71d8fa1562ca72689e64828c305efa2dd4d57523fe6d46a0443fddf11237a222d0eddef737c2c59f27dc6b1092bad424d493c3c57a5314ce22f11f555b96967442556bc30769a9ff4ed430313f99a8e1a6a31c8a4852731d6be398e9c42dd8537e56aadcf961cf6668a5b123234f53bf6afe930b9d1461a312460b43f713dd7fc9b136c531c94e06f878314e7f0c0ca444a4e911cd6b9f4fd949c27226d7d8e3441e5f15996c437fc7fade96ee41c64ec0f8bfef471e4df5f734c66c00c7c78506bcc1c292968297f13ad096d90d9f2b4c3b26a2c414810dffef179a98415aad4a48bcfd130d8f46d23cff68a04e585a67fb0a38a7b71924a2b74e0f132d7365abe6b8b0426cefeca897d7979405b97ccf843530fafc3204459855c5c1cc655aa630f37c8adeab4711ee9fdafd851aad34c4ca3afe979dba3f2a7b0c38028683683d5021ef8066314c33251e1fa4399b33693b822a9810b73cf87d877575e4a09148c23dd63c34bfaf2c47af6133d0da81f88a8e98b85abcc00106fc3ef5b7321c7a91163c73d108fc7f149de4dee0b608890cedffa091c76ccb5497b6ce70615a12fef85ba29754b8d23a50624c00d11c9a128b19dda89c88f669e46f69dce3471c8c018b224858a563771acb6cd9e01ea94d9846f62807758da50fcb345c8dd486e9a3716633824b8139fa8f28e63ca", "spend_index": [ 0, 1, 131671016, 4294967295 ], "result": [ "426d67aa0b10f1989589c3dd19384a15d02bf6c359eacdab6a5d86b4ccafd4ed", "fe8428c7b9169065fae17bafeed4219d571e91379a51fd8a415db0b875934a26", "788e97595eae8dbc90753d7b2b36f2bb200f359fce4f30691c8990100e0ff215", "c23036b78b162b2dbcc5f598a6ec0f5d17f154101a940f6d503635d2e0c0f39a" ] }, { "desc": { "Inputs": 8, "Outputs": 10, "Witness": false, "Version": -1574382780, "scriptSigs": true }, "hex_tx": "44d328a2081b94443300000000000000000000000000000000000000000000000000000000a886751464f9f38e242c62b656610a1f82319272a176345cd2a998a58370215229be9127c7738443708ee88324a59b15e0205aec039f5390c8d78242dcede6748609a6eb7ae09a75936050b1e6ed0733b04aeb4bbf84485b966d192f5eb19b774afa63158934da28bee5be376e5524d3e40000000000000000000000000000000000000000000000000000000097b8e2600011ffa1143fed34b000000000000000000000000000000000000000000000000000000000680196edfd3801442fa9ce30ee6eabb973b35ec0c9841fc00d64cf688b14c4b7817de9b3b32a90f59a8b5c7656de2ac7e9e625eaff5099488fa9451bae856e1d582d8abcebd400b34c8f236306930cb5c02150a39a028dcbff4fb0ab95a58b8911da783b7278f3efb0c799a18075d61bcfdf9eb32420451d8251cd4bd9678993994649f58b3254b45adb9733ab37cb2b3a0c1a008aa4c38c583cfccec7fa8fc4b83fc28ab055f119f0de6f46946b9f5d2a6eee8dfb4a4cd4e031bebc30a8bc8b3308740955ffc939ac41dffa12d385736e75503abb6b3c280e6cc625f5bebeb7bf2ac66ca18c84d3dd12adb02a5537e94827a6e38f49ab0e4874601c098c89d40a59704d192716ccc244592fa4563c9d7db718de830e0e4df313d06257cd34e0ee02f4b3f7a6b60e39eaa35e76c8484c36bf323e3b628e2b66188569d9414c2e1633d23c83f3700000000000000000000000000000000000000000000000000000000037fc715a00c349adb6ecb8c9280000000000000000000000000000000000000000000000000000000088c15f4f009a3ed5e5fd37193c00000000000000000000000000000000000000000000000000000000b4a019c1fd3401ea4bcaa791a17606d3faae9e9a73e56f016fa9ada279cfba50e41b15b08d9d76d494a21b59c99a03ed56a240bbc0deb9ddecda8cb1a54d3b12b3602a60f00fdd69057d7d23e89fd451c3eb1985539665d46818c24612fdd8a524a5307b3fc7f4348c4a422a428200ae9d1b2763e054d14954653d17bfd9e94924c91ac732aab35081b1cd03d68803b10f2b26b805ce5141291f2e836651e49f5d60925e4b61cb54cc7fdb857cea50a0a089a1632cb13a2b07fd16c490150e71b59677f8ac627afbeeacc5072685257458a682a4804e8bbc7b3fc8482ba4ba33cb12b7bc2d54e3bbff7bbb8ac6d7155791520a4ff2754df67521b1905a8af5ea0a779dc7f9d1dd65a6a0cfb4df5fee1829f08e3b125ec2527a923339e3e16b693c1b69b32517b6641505d223b2d738ede86fa5a60258e8ec2fb96eadbf11983890373d00000000000000000000000000000000000000000000000000000000f8283babfdee017b298c98616741fb4b87e68170dfd1dc28eb90035346497219c02896a25e1489ca35e164b1626d28960f88f7d2589f086f3f43fea33ddbe0462cdd5a94f35c2f8d083fa67f4bdc23395ef4f7b46ccdd5299781503240707e0c630529e2f794ca19292ff002dd35271adf84251a94fd399cffc0b99d4e63a904d3c8f5783ed87e2aa2a77648da6ffceb55a2b20e2f2df1f49f5b6930a73c5c2360d01c7ddf1b69a2b800abfb9a8550ecfef567146e5c14477189e87e7d4147afc52cf5daefb5f3771adfb57853e560adaa2f9ad65eef299ec873a32985de4181587bbfecd50f72f335738f7ca54eebeac8e148fe5bf238be288ebb548efd15e06722f5a8236113103619c100e45142c6e0677ded1ee0b3cf47a58735e38b8ad9d2cab7ab46444b529eb93ded2b15f9c0e1e0dafe27fc78f8f298d1972d955596992cb9e04f1471b7e9c8bcdd4c3a6a03891ecedf09ca3cc0d3268275205c3581b3eceb46a0a1d75504b7248b9259b55172865451b506decc4e8167ac83cf1cd60ace255aa7c1cd392b07209a8dfc5ae296c33a631a1ebca89d0a1142f5634505d33365d646a9a02c25946f3c08a1cf1edf7a51bb7cdb212f14b96287a8fd3a32450be5aac788aaa5bddce1954acda404d6cf92b080811feedea53baf9c31724466c8ac66b3f9d066cb128bc9974e94135a2220942e6c8bb05734f8e40a00000000000000000000000000000000000000000000000000000000e939c9f200f34e11770a159c56ae33e4d155c8d9121a9088c37c866f585b375f63d91083287016d5747217a0dcbd3080d36d7405f475a933a7e021381f95837103207c98f7b3b80e33971c6d84b489a51d842bc38d930f1865ae1e9282f1edabd7d8e4a4f3626255380114f3efa6c5fcc031be7d0c82cd04cc952a9817eb7fd36bf5ed76ed16533371e97ccd869c79eb547eb2ef4f62802eabbf560fd4a96a99d93a745077b5549fa3f55b1aa9a9495fc38f113f5bb897ee969dd7853b3d063287eb3e3470e2c87a29fed0fb76a4f97ffa1bcd3bbb2e32a82608c607bb5fbe619f6667c8e84727aa6542b8c89b932991f22592fd0fb95fbcb6985998be7b4a2a2961c9a37dfecf69b63444716cad444d17475b1b1de727f0757ce053f24113725ff4f451fb74e8e2c3e2ec02bf0e1bdfbdb62fa864a0f9986da097f06cc1f2ad0d875a0fe71cb1767e395600a1bab80b9f9b7a827993c6a9e8eb6501b441b6f20fb45e8725df5fba3946024cfeda5e7276438135aea3da7ceb78a7be58e7d9b37d2f36d5a9a8cc31807d74f56d6f8911e255ec2623b1bbe615831cc64695d4d16d8413b778be4baee7019b79ee3404b8d1489657c8c7da55e55c71f99040fb0af185bd9679e4ac1c846983b954b5f3bd83655f281a13dfbe9ce548bde41227633c433af464c98864deef1caf123e1ed85808c001acf0441f8473cd7b97798fcc7add646a350a06ae7c7af6c9a60872371273206d2dc4522d545c92a36969b4f19f91ab3bd87bf754f3a9335875c8777a16d83138f2dc1c8f6823af1e080d7d164eb7369fbc7646cce618f41d8da6eb3b5332e8a9310a152a64e4ece54d6d48fda989f84adc261b307f09e2b981c06e9a7f8a11761f7263bf55c729387ca1fb70bb5aa73e59c8e2614a5b408e48cc3bc346ef3f1ba49b1a7dd630738083c44ad54e08675d6e6f3587b8561fa42877f3e8790e16fe88a54ed69ce6d3599f577bf89c371828dff961250bb585fcdb521a43cbe45eabad3cb17046fb7ab209f17dcd519e22f093d915fcad8b85aee4b774a1895bf6a910dd9e1dc56fd8a075ba89f0aa752bca314a12a9b5dd8885b8dce3d4cad86ca14044a926648af953b273b9e1fa9b85f0795eb4cacba1231c9ebfde1fe89064adcbba3dfb294696ac1c964ea008758dbad14768b6d582307354afac871599b075e457c8e80f67ec373c1dd2ee83a44f42eae8e52c7b2cc37fdd4779bf8d4e859e637dd1dc42a9418db9255d19a494d8afbb481aaccd8b424afccb4701ae74384db73f9bd595924abd0a090cd2360563dee0adddc312249540f7843dcc89f6d210c3a1ea9d5d4ee111c04a01bcd96d232078a7535d62a517302a3a6c3b792ebd84cc2defa7649c9118a37eb69273ea11a3f180525aa5f035f9133f616e8f70c49baeaec8ce5aeb613d58ed8a9894e42b3f87b00f386035229a16a0e90b479dfbd69123b3575b9976d96f04279cb272272d37bd67c8336ed74ac5f0abd2cf9dc437311315b1264936454dd1aa60dc5f3a00d91b75124f90962835e8fb88a19f4089fbb593579024d0c6530ce0a3b07c0367fdf9ebabb228d66a27b6e28dd091690045200b230b7ae83b5941140cb56db28f5fd7a97cd4c34720543a093ce486794bd8ac80608e0c18eb7b6a7535e1e6bd601cd4bc258519b8c30b6c2fd70cecdf105e395e79961ed8fd39d2ecae4e10c1fab97fb8c471ffea6e5cf4006a0bae56266261061d692fbe2c3bc19a4ff3dfc51019f6cd4bf167eb79e182c6a8e3fca40e22b8b02ec8ea0ac6ad75e9db6f90da6de1e2f4dd334a46a0d71e7c5cff5bc7618eda63792330c5ce4a5bb7aa2896400936f29ebac089d4644b98d60f68c7684af6f9605deab295db64956af1e005ca3199a5a8041d15636315a8811a18f3095fc95e4a95c61584bcd466ad77ae40f2eb0896435cbc91eb5ddc739f0d15ada9d0b46b066b55de82a9c3188c5ad66933f86178fb512c18c2805b8721a0c6dbf2e79854d076dde7f54430078cae232fac81c24648a23ce29358628a76cf26d58ed796f0f3c7d0cc5a67768521e20b881633103ec45c52c820d91b6211266ef7a0921c4dc51568e9f836d458ddbd025fff6b52445ff707e8af0e02c3771411a63c95d901efa7a4fd10fc07811f517e52ecab1b1680106eb7c3df88e2bb6d22a4f69eef0277cc509130587c807f682645f16400ced744f1bcb8235f5b14f5ec6d355dcb934766c1bf20a380262734deb57cfaa6993526923c0b63593d273a9713b79bda14792b8952908279eedc11a6d3068242635af8655789a74a9ea299af963457e671ef6accf1754af7cd5d0b1ffb271911820b75e3ec2f5675ff743d113a465d314a7cde8c6bc80e731e427090252e91a7f105b4d1958e7971aaa7760730d01d22ecb0a9b33a14e7e508452259e8ac97ced7cf5b604ee116da49b27021fab72dcf595fee200311318193061756315d4f3073c7ff7c03494241367e72d753ee5cee93066da766b883848c58327eed8ee3a43faa1d48484228f648966d6b29beba5a6357a1e7b3f90f690d0ec98c1f486501abb10ae7f6ce9502d587f161b811b5ba44aa33f2f2bc59f7cbbedb53a9ce3bfd911f2dd7e59f0b0ad885044a6e3c15939a853b3f82b72d1f542599960ccb04c04e6a40835d58c82e3860d477c5e33ed3eef6d984a73d38537fd5d890caec9c0e540850e3bbdb53221d387278c19a4270e58f7b8eac4f41bd3b85566a879bcb6598e927f0dba5b8f33db8e24a83971be4ac8b5b1d3006be3c997948ad83ca681eae944fe1fd7e98d23a15f1de64f7d747a812aaf50a6fea45cc1757a4bfecd0e8bd2ad71773a773e098928bb258078c30601a1f0c6cba095a96d77ad50a5e89554498c532948782527bdcd8538c114f98ae43ea365915de277fab9eb401e4c9a157ad0b015e03c32428abb2b18011037edfd64b", "spend_index": [ 0, 1, 206680780, 4294967295 ], "result": [ "58341bcadf24913226c239c3f98212df4441eac171767ecb3bd9c10c3173b869", "8503f915c572b7a17e89e3016c2b332b4d4b695320dedb09ff14c68cb9963bab", "fb7524262bcbf4340dd6c30b26e19ff8cec3e48bb4c0b33ed059c4a82d2a730b", "722b46c18def320f4abefe4537001b871c159c85cfccfec43ddfe59551edd7cb" ] }, { "desc": { "Inputs": 3, "Outputs": 3, "Witness": false, "Version": -1982256653, "scriptSigs": false }, "hex_tx": "f329d98903633f5c0000000000000000000000000000000000000000000000000000000000eb79ff340060c265897579fec400000000000000000000000000000000000000000000000000000000d036cca500b6a3d11d12d5c9fa000000000000000000000000000000000000000000000000000000002711f92d0087209da1036b4a21a0b2cfe547c8c8ffabb4a756d191e0d24c42a9dbefe8559ae663ae6cbf2580e602b0536e96921deb78278aeb52bb18128f75397415ec434f7524be2ba88ec85137ab7413f06ff04256b08069f4aae1919d9d1894deafb4fc8b302497d6995386eebacb2c3f14fffac585449eca6a9e50b40312debaec965cd9df71ecbc1bbc15a140ef8bca7649ab68f9d79db5fc980730a23a3ea5530a4dfe867e7c767c6aac1056e69436155395295a8e00f1d9a4be8bfa11726f57c57c21db2208bd30a33f773980db53c93f55586dcfa9a42bbf55896cc9b93b15c8cbe3334c332e38af044b0e8ef21829ce3ef4e19e1fea2e1945d4471c1dda993dde26c856ab40839ad349600153a51eca7c8667245807be1df58e61ab6f3ee44d007b2a2fe91d43e49cdd5f9494a106c62810a79bab090846168697070c6d3dc5c1809459d1273906e482197af5312a61624b6cd9d4836183a16ebbd237ac52703131acda724459a5a8e6f6185ee4a22c3e2a299816ef19d6a8b07bba5feedf5c38249d67c7036c8439a6476b9b6504f137ce251d50f32e069cfce6ad0859c4a3cdacc8fc9ec92b7172cadedc66597218c85c1c30dcf1ac87d363895f946b81bf8615762423c4d6e680250cacc6b9d97567215134973765fdd5c7342a5fb40cc8ca5c445f1ededd874cb8aca04f8da28f367f0adb81a30b4531bb9dcd58c90e4c76c0c0cfc5a8abc8bfa1716e1613d8a63cd8446f28d4c7826c901f1fd660d1c097f2e956ce5ad240411dfff96fafb5f125f3557a425d7ccf5899bec1c1470fe93e27f29b273d3fd323529f9b498e93a7f6530fb9fa674360c7fedd5697979b10f65e938375fe1dbdd7650345a9c00a2226b1b3b00772763a701c50ce4c", "spend_index": [ 0, 1, 1790497802, 4294967295 ], "result": [ "f03f41fbe6fa92ec2305822d84f8951c10b434d32910ff87688b5e0954483dd9", "8d1ee39f3f10d26642ac461076cb16b9fb79b5a13803f887235405762b460193", "60318fe6ebc4f4d78b5670e4fd932b32b2144c7f0893894fb7c6da3f1fdb6e7b", "3a7bb937b729b5812da85c294edf30e930b9c9b79ce4c6668d87208626552a18" ] }, { "desc": { "Inputs": 9, "Outputs": 3, "Witness": false, "Version": -1503121461, "scriptSigs": true }, "hex_tx": "cb2f68a609e5de017500000000000000000000000000000000000000000000000000000000d09e2c75005dee941d01796ad30000000000000000000000000000000000000000000000000000000056b1ef68cc0c10a3bedfc6217be5c1971491ae6d8f63812b90d946e47af784edf79c999d365da76051f8ff09ad86e0ed91177e5b75f97175341529bf4bf3e33432958b1fddf62c6db571f28ea06c35945bfc100540cef9b6ecdd9345f2f615102185ed0686662a6ee2bf34f70b3343a1b484571ef1b7f51f0a40e550a2f33e9d95ed3e2f95d5520b051352bd822f9917195d2f05e2a84e5dc945e94076a8aa5770a008df326357eb34177a78977dc0ca794b84105040a8aada606401f8232e3dda42660aa783e6523218143ef279042232e95bb0445e4fc6f900000000000000000000000000000000000000000000000000000000e6ebe4e8fd4f012f3dd6f2ab4c101582a10dd8f65c9c3e584f17bf7c167fd6c5f3bd3b317c3d978fa2699d67853c33c351b432b9f3172054e7aa8a4f54019c88572c06ef175a2e509491f23c51fc28384f99c6aadad951d45f4bbd2ce1558ead4d687d4bb42faab7755f525ceb1f43059a62725840f8e9539c4f4deea0111bf4c4e6531677c66df5311049ac9888612dfc39b8629e6a44cff527a0be982527906a3479543ca2d6f65a9e028a4cf7bdca28678d63d321520225460134992c56d77809f2e8eb1b8829e26f92b5be1cf0e35085366b6514fee542adb64ec6fc224a58de6acfd22374e5fd7d7e63de0aa53f9646ebd9c373e01a680c32ed65aac686b5c4a32940080cee2a50cc1d92f2fcc4b903d29002b3f20cff6a73783eeb935275ecb29a21bee39e50fcb97a30500fe35ac0c63966b68d08417777d193b5545cd3a57a56c2ee321bbc3e0fdb70d51b2f86347668995cfd0ab0d835bcd13700000000000000000000000000000000000000000000000000000000909ab41a00022fa8390b856ec4000000000000000000000000000000000000000000000000000000001166674a009a5886e8859d478a00000000000000000000000000000000000000000000000000000000799b5fb5d025f4015c024ec5146499032e5b85db12b613a37f9eca6f0daae0339e5b388f90454f9e5526f69b73ed8bbbd3da06eb5413a5a7e562355300982afd5bf1eb141cdce722dfa113ebd32928aeaf331ca40f788e9388a0e72fc65ea6338104aca1eb8eec4c3da4447147543104ca5b64f06a8d6429efe123d4b704079d786294dffa7ea6349103639bb5445d6be9bf00e5b2b04fe48528f6751685fb770cff6a09322675147528cb93b733db529aeafca641a728b00e39528af9dedaa626d9b6503f5c8953c4dd2f9334af98d73429b10225522feaf01b4ac33500000000000000000000000000000000000000000000000000000000ea307843fd6501e76f82049eeff7f492a0e5ab9628cd4b18131adbcb67ae132c3ab6aca8dcfbc8857d65ca2ee39354a8abd325f989bf53aa3472e057c78c60f68032c1fe9b1ff518d3b46177a63f879116bfc138c1d8800143927d931da826d389a16b828e78efa3ded11b5a02d5201233c9813b7ef1101812ab4187b44969b6ed2375164823bcb896af25a6cb2ca6f658cf7d65656845aee7ce3f115370dfa65952454def15460f501d41d72c8dd5d24f05c7a27bfb653e36057c7387f040997e908e98a2da052acc094f1c72473095dd2b0f0388c800458cb869e67fffcff7024dde61f6d44dd799148b99823d5829f907f6195ce1369d918d44d926bc818e882412f852d68be22621c5fd0d1489b9b886950933baef7e087c8d1d9432edc50a4ec45f715b16fcc099644e6ea9f698a0a11768797dffd45cb5c40c7650c1eae727826e8dfeaf6d4f7db6c88262f21a9bc3e2a4169f1d6ca332e51c5254137861bbb7f81f5876c2d5b2309053c013e14085a2350000000000000000000000000000000000000000000000000000000086b313cbfd0501c1823923ed8340dea30b27639a9e04fe0a05956a720ade237611f42d73e77bd3db5249e7882591f38bb387f3be852ed297cfbf74268d51df9a91f1daa838a932cf8fd4e07306041c582b41786add151d02b225bb4a1deeec7fcd7a4df2630907fd5d4494b5a609d4945bf684ac0610ca35366e8d2b113d51a1ff1f1e1f45ca772f23ee577552245c20ee46593fe8a4c856ddceb1b964edabd8dd33367213ac7eca9fd43441261425a3b01d98ba0c21a316922baf7cdf1695cd277e7a544ba701c3a4ba8de3d1d2cad9b0af19e95288474574394e12121f2313861bf614ae244f37ddb3c8eed5b30bb043f239296579c39385106a206e430c950856b8d0ea237d4f5554851dfef7064b186d04bd000000000000000000000000000000000000000000000000000000000409078ac09bc4f8cd9c964f9c5e4486e37161f169d67b45f0083fa625e05fa4c38fe6cb6dca359ee8eeb8c3f59d0575415c9439bebb662ab770b55df602dc9bd3057638887ade68586d70ff0a5c6e4d3d8b69a4000dcb221683f41a675410019eddbb530ab5152bf57b9aaf5b77528d29e5cd052f1a870aeffea850a75f060b66328b7eaee58b381c083ad7579eb2efaa74dc01f230e4e9635a27f38f73786b9e773b0d5cf640c9597a70e28e83ccf9d5d54f34aff383e7ceb72de13508c57c69ddec46df91676b8203b87c4e9c53038d04c8d40bfbfa8b032e4a17379eb32f8bf1e456bae2bcbbe5cd8e26aa59a85b733215d93dcd3dcd4f0013421268d42e44c858dc04fcaba2454e8a08b4cf156f1e36ef7d3485eadef5e5c7ab87aa1f530cdc8a314e5e43bb44fff91c4e2639aa59b8a21507400f3691688a7a43fd7d54df22d556d17fc8b39b3096282bfce97d5ade0d3101985b1654f8c65269ec354c64861ed6f238fe1aed2c21abdf0ee5aeef56b6444c08cbdc60e6996a9d18ae6724ccc824474efd708272a99c19104545477a16c1825cface71708b5df88f02331f4064c8f0c63b7bffa3575667fe06d6e631ab8db726ee012c6d4ae840ad51fd1c46805689bfd7559be84c00e167a1ade51c3c6192ca0363905a8f396e42cefdb9522d93a7752b6c0bc31e0b375d2023cbdc66b39e0c76378ef4039330bba17f6ab6fa36eed1acc396c3f6d1279c30ca8b6a06bf911e59b5cba6e344a013aed80fa048391bf7963584500daa5c6b3dbfa550a46f69f0bb049a37d3369236ea94bcc5175475abdce243fd1dd6202691fe588b701d286f9511202bfdabf265601cf099e4efb8ef631face8c4e2cfac08c92e1c545fc83b7a1c23d3c0197bd0c0dfe76a7744863e9aee8eb1a315ad0cc9a7f63e02247b9e0f82ed9fa62b684d022f651ad8a8b64feeb2e17ce697bd66bf943e2cf286f015f5671ea22269ee9deadba12c2ca3873ae4f91c281c5b24b6782aa6f54c83730c855b4c0340da726cbaa4ab5a4b141809d83fb821214dc60b089823b6dbca1b944fefaad4ad7333c8a5e65254e40d2fc51283a76ecde81217d067d87b359a66a363e075b6fbbcdbfbc39c7d5eb0a5cbc01d6e940d72dfa81a73da02a1931b1c47b37066f9156b5da387c641", "spend_index": [ 0, 1, 178805667, 4294967295 ], "result": [ "c0f082ebcad4231a1fad70bd0d02c5d293ce82d7c7e7db185d5b2554b2f4455c", "65f3fa82949b8689ea3ab6107c5fae7127547bddd3c8f70738905581994820e7", "85d973f15ced3f6133056c16e5b424872150e735c7b19a0045442f336ebd9f5f", "8fae3556a0ede99ae4e1bfb4680dad9cec44f64de26afb93e3ad0f871c226cf4" ] }, { "desc": { "Inputs": 5, "Outputs": 6, "Witness": false, "Version": 1575624129, "scriptSigs": false }, "hex_tx": "c11dea5d05cb981dc4000000000000000000000000000000000000000000000000000000000c9b9b0200b290a7ac6f849bb300000000000000000000000000000000000000000000000000000000e91bdc03007f72a0d3acc43e6200000000000000000000000000000000000000000000000000000000b6b1ad2d00295bd546d097890600000000000000000000000000000000000000000000000000000000bf722469006fa6c23036cf1e540000000000000000000000000000000000000000000000000000000089e9b7380072fcf87606b2e599f5ccd68544c897d63d66776afcdd23524fe6cdb266d5c1022e393b15e3ee17a96b56af1d9aa19d9ff7ce38f2bc382c3b4b21fa6555b4af8fdf82e3a559a6c6ed58b0c042c4d281f539a0cd9c5404ebe7f8c68de5dd1aaa31d449a6b22e7c353d4f84a738a944c3dd42ec792c28e7e50b4b25b03c4e86c7e3ad3779977943bd59d7a06a9e0090bf65c3c224dd9ff87d7b7ad41c3f56b6d391fdb3988e5832def393ee04113ea86e347a304987b08ab59ae01f63e01f3b747efdfb2bcbcd03edb079dccfe5c2ed683a671780f86b3a3646a566e0d31302c8a788110d740f48430a499f8fb8c445d6d1f8c3b3e07e94a5583cc4f539bfcd9a8e1b160792164cc7b9d60642e8e50c4c46d9590ecb8dec0edb4724e092b8ca9204099ab8bc9f7fdbaa9fa4b5b08b1c87816812fe09d5d4334f64776faab8ec65b8c03295fc44960faf95d6eb60805ff6a3f2fccc6afce6d49382909c1841de89abdc19dc35b8114b0845aec5f4b1cd7ab335f0c31ef279e473e859f701172f43b7c77fce8b1126af6a4adf0862127d3e4ae3a26939ab33865468723fc52e7f06221bc6d2c3ae9a9268b266cb6c79605cc8aa2797beba4931b1d95ea442894acd628a631cf9278971b41040da8b69951830d870ccbfb4e14c6bad6f478b860c576a63a920f837fb311ce454a471fb51765809d682b3952cd2afa0f317f2e4b78e3bc4449a89c10350da53a331c082b6b42d4675c99208ae204e7997723d3b289ccb1bc297ef4d59405e0edd2ae0e34747c07569b477f38b9c6863b778f2d84c20dcd7bfb4440788a6214d34ee7c8083e4f1f74471ce772b43cfc236c750e4fa83f46cd676f6a66bbf9b248cb105ad129968547b37092688c8c8dcc09ed8c4a32446c8a4bef9f3e37817a5c02128f3032cc8b4229c047c84e2167852aae160fdf153418a6d26acbf78994e902d18d83000a0be6f0a8034495c73b32c01e35f7b9d992ee3feb4bd48f0c14f6ca7e5cc606d9f6fd1fea227ff025cb5011ef6cbc90fd3eb56d6c5820355e2a1e8ef3dfb74dd78ebedb2edd1f40913d6f07acc44a6f398f2fae987d709c8ca88c68d614f6454ab8ca4cefdc57471f2bcebc38cb511253baac79261b04ce77b423b2c9f0bc51d784f75c16b78501772e4ba06dca487a1b990f7102d1a4f9e3669ff4d55b4831a4f65c8e7b03d0acee88b7118c26924109098272ff1cea11fb4ee9496d53189fdf8297df6fe9be7ea9c0691c5b1b2fdcbfae3d962087c340180750b69ded3b7588326f51b80d1dfba75c7be4f00d0d0addfc2a18216b120b3944590d2a5a767cafc86798dd75f59e29bf23a942d6d903ca78d3e8da941af499d4761cbd4c005a3679c8eb5324d88af0a1bc29be3721452ca50a2081824a288cf0e91f71a820ca781bbf90bedb0cfefdfb951ea0e975116d5f640c781e7060a521fd3655f8bfd185966e89f75b4163802287305aba751220d017fc89843f5e6ec6069404a67fa383be88db9707cd3006e4c3dd25f5a533b762b21fa06dd152ead0a659aa3e085954ede15dd0aac553e8c3dcc09450add4f1ce86e0d0dedb3a848bef9d016147b51d8ab928c2fe100f5d5893c6babd9cfa5b66ee80d92ccdc358330711a6237c4db067ee8347a1c7543dcf0d82d51ea17f75c8db0ac2354282c7eea98052a584a2090b2a3e81d1216090e0285a8498e7c7422c7d95541a34b9650667ef74fd06fbacdac9b73880813bf645e33aaa3711021beb326e8abd9b96b47a86770ce6994ab", "spend_index": [ 0, 1, 1689259243, 4294967295 ], "result": [ "bacf5ce1b20c30f37c9fd6bfe1ea6a0bc2d11ffbef851bb2a938774ad81e24e7", "76a6b018ce73966a14dd33b530cf7bec0654bc03c1069425327c2bd8ef8dd01b", "2b9480c19a30bfd2d71bdb6432ee44a7a44c1e19fd5e50422e98453a27c4b361", "292235358d40ba53a6087432aead647aa651f3f415f876da958fd814d09c561f" ] }, { "desc": { "Inputs": 10, "Outputs": 7, "Witness": false, "Version": -2047477303, "scriptSigs": true }, "hex_tx": "c9f9f5850a71a2521800000000000000000000000000000000000000000000000000000000a797937efd210139ca4af1285756ba497203c3872a7a74b940f5691de5b47b685708a92a2f2faa74bdaf7ba88ac45e8f125a3a1392a52b7ca7f2379af61d8ba371c8a97c28812e62e0c4180d2938353f20b276e5753a466f15f680dedb499623a659052569a57d3f946dda1f587919f424682c2fcd35b6bc8fd9d3ba1472c19ed75e922135b1a4752b89512c7633796caffe25f7c5abb1e4c45986822921e2ed8d4e653d1232b45b87332bdf367248654e48604bd9b487e6786ad47d9b77dd3edc2e3366fd43981a54b1cead2da51601ba9f3a0fa0ff3d890913d43d16e5262beb7cc3be424755f453cab87e78281689ce51c1025e64493d3f958bc0ddce21d75fd82fb3215bac54d40fc8db06a19994665973e5f627bfce37f6e7b608585a7856900f58a67d89344666517b253eb1a800000000000000000000000000000000000000000000000000000000c568837d359b2f75e75b3d39b5d95ab308837b50b6a4724c83d8884e52d24ddf11ee2bf8e2f09a6aa86e6849a218598f427f899017db9ced5e37da0d3121cd256a7400000000000000000000000000000000000000000000000000000000eb5cc6273221db095a626ba6a6f671293cda3558d1c3aea3562fa80f535882e63dd40ee619b3cf5ab55338c5d64b3b041bf99e6b7912124b9ff01b549e13a1000000000000000000000000000000000000000000000000000000009ef30358fddc01f3e13fcea1413e057861d719e571ea78aba967df3fe4f52d13d8fc72f0345ada8ea98a968894cf0d59586c298dd9878d6bdb01877289328be0a280871f629984afbe1cd05e016fa0f38123bd5c1ca1c5fde54beb5c872e5b481662b7b86093ef6bbd3e59529b02496ad66583e73ce2d5af8ffb787dadc5483180687ac1014a22a35c490aa0be5a1326619057de4a6b5395540eca7ce0cc2df05878744ab989b21e9d6bad9fb7d5f658d777c4c83d11eaa9eeeb74eabb2e335f3ee751c9c294dc3c920b9b619b0242897acab50c722fe78a2dc2aabbdbd36b10c18525996f558f7d2cd36f0be38692dfce12e5b507be796ccae0bd29b293c4ad831e7bd2138f06576b395bb0182d67a900b60e588152beaa2b66bd9e763d25b2e586806fd09318e68fe9d61111884516b860d8143014d36f43ade13a21948f6cd02dd4724ee4d9f348410c4187d6236164361ddf614d7c9c75fed4b022ebb131b1c749bf3337fc519b2a6021af2f575183e587211d8aa70d1e5bcde674aef5ec5a8cfeff8b0ec44974a704d4b199f943344dd610c97c6998b7eb4b7fd6f946298946fe4d8c2684beaddb47a7219b1370a2a0dc97d3f159885337dae2ed4cb067ee9040c51ad1a557c3134b5d88bc88dffd39fc15f550cc5822cdf287942d05a60306494a7c10be05c8f9b000000000000000000000000000000000000000000000000000000000694f038759e676927bd0cddc680bc3844e849de663b85aab13a5738e4e8edaf7efd4db889d87bc03a060118f8a6e720a5f5c9825d110a181eb8a2be1216f21198cd954d2fce2581b3ff50725960a9013a8347f270c8dbc899a7b20f101f67ff7573d32e63341000000000000000000000000000000000000000000000000000000003f46ee457c3eee443ff1a0a98c0e17deedad1445a18de5b2a734781a0cc5de3a1577b4c11cbd94fcba823aa167ffd6282a805e8fe896e883ac8e0f9795fa0f1ce8cb39042e724417cdae4c3397cafbd9792738820b286a24e9d1e3b4bad3db1ad46f232bf8e79da2cd1f5f0364c6c18c9526d856e725c3285aca3f0968f7d71143032a22ad87a2b12e00000000000000000000000000000000000000000000000000000000edd59f3dfd0301683b3db9e8877da4b82cae60088f4cd57375d6c182831acb9d86ac0bce97887bbc3eaaf0644bc87ca1e81274701718d2000697818b8124aa686b06a2ddc3ae69688cdc5c024a4fbe59616c22202cac77ddda4b52909b166d651ad5122c4826e2b555ca52d75892de41d4eb8e8cb2c17bcb32e6dcb327bb36effbbbc8f23757097813095f6b3b1513c36dca3d3f8c10b6e87884c18c18c83ff27588672afdbcbc7956e63d38e265bebad4a2244017fcd2cf948c9d0f8092fc61c29245186a53a87b1956fc7e0e2492b1381c057a56df789e9c0b7ebd1e54097a6a1005cd59a2c5be167a8327019390aab0a56f8fd4aa82b381e5788e60ed8975dec6fc047efcb2bbc597cd00c4d342aeb95600000000000000000000000000000000000000000000000000000000edc15b9c0047a68fb336095ceb000000000000000000000000000000000000000000000000000000001b0abbacfdff006803a5b4846ed22ae9af55d16d338f39d56b32ff7e6a42e8a030e50a2680cf3414b7b8a2010a8ba6bb70265aa6039f06ceac4a9613bb5b38dcbc56eac41d420548e9558a16213d5cf7c9fcb4606070a1a1f9258ef17c895c0bc00c5f630b702fe0e425b6990748ff78bdb27d6512a4c9f326dfdfbe71e55f15c7be300d606aab1f5c4176931a8ee3bcc13f8815311529c7c2ea41e3280f7352a296493d2824269660fd24aa943608bb9c9a9e80a82bf4853f882ebd5028c79007b91f430e106899a0656a9ebc4455d81a40158cccd76b92adcb5051920e5b0f1f305140aa3a284c3da654ce887959ce95f1bf095dafed6e4e5e78fa1f32e8655e68e980bbbeab28fcc45be2a6f0000000000000000000000000000000000000000000000000000000008f7fd2fcfd3501cd53b57518f1d683ba3e7395986dea55c44a344f653788a3a820a9c695dd3d92df0d7ec6f010559dc6423d4d6a1e282f7a3b74fac6cf91d6b7e61e0c7b3df2ec7ea3dedf627772c0644f2ce93abc90be91bd66426f11f1a1bdbbbbc5adfd0d8be28792bafa71603a71dae861fa62dbd7f7e4fc98261343414e332ff5708e3c97c04ff418e2b2ec185d1b8d1d589937c12ca0f2bf62393c9e7ffcc910d96ef652a77af479f9646957f137af33e2e8cc58e5d81c80605283ae26bbe479d6dad6c651f10920fb383486616b90f2c658c4a39e1cd13afeeac9a5a11ce7491d7cbab2808663eabede07754429ee753fd65973ba88763881fe948863d12189ba885a3d4bb0a3895fcdfcf83f2e20a3f47d3121278aa64fff71f49e61cf0db1dbfa0fd27644cb79582ef0c4c81a088abc64ee0f332e1dd3ea8e605ffa07958d3b14523f0b48c82baf8901eba24111293e08901beca34b0642739d825930c604dfbc401f30ad29b6e97b716ed98677151242c9a109050636c83eed74df2a58ba5bd6bddd07bafad4e39a0d6e3310fd1de8c6a0264a1c536083f69f1cf4932ec2d34fe1a0e85f2bb796ad86ab07142cb28b3b91f3c178b993608f7370416baa1d9ab723a9007d083f07db387d6c2e53edcafc8940b945adefeea701b9509f08b512a4135fc00ce68807bee85521217eadabb6d45e37746b3151aac0a18a052030c18e9173b48ec6f516c2ed7d7804706b052b4301a2dd3dc8bed99ebca3f28694850c382f0a5d226128b055a8080826ec21b61a70c74e792e617457917f31bcfb17aba58a489354fa9627dc2a876f65f8f5e5ed4710913f68aba0cc20f6e6c4df1c51571a00f5c5b552f96c8f48278d2e7d68ad0c5e34295b899223a1a050d2e9068fa1532f6856ada35ff0d46dc30bbd1a360fb6ad6d08d9b1c409be3cebc63cb049f8582ae4b1ae823e1db92bd1d63d2348a8f52ca9b0f17d4773f013c6f481c5ec94b4798e1b2cd4ee8aeb145c9abfa4dfcf8c94c720721d4ad0482b55338df705638f45cc8159c82df07f7ff24630a26eebd8514fa62ea0361915628853d47f3b9def22466c99d78f8ce43d1937d616547e50f6aa1a7fd89da71b0585c2918d9e1f9f76050a983712f449f74cdec61641da51f6a511738de8b1e535a9c86a782903dc1bb6c7c2352e1377404458a5cc8f55fadf06c3c1a13508e4e4946a5a03314124621ce0f679b816512345d92fe6cb00e5e54692f813c454b4d3457a80de5462440908f40dbd9405177aa97603acac2f6d5d455676291fbf033b2807644dd91de143d36c438574d26bdc85a52bbfc8d4dd941073f44cc821d802e47b393c4efbfb1aab7045697df1a9850ab9806ccffa9250d6f84ae78f3e5fc325013b83f27b387cb2ab37e2569467cf0ded9c6e570c303d8275f0950d7f2645f299ef2f4157f7f7d5bfb330c094d83b15fb2cd6ab743ed3322917dbacf75cd00e1de5aae7d40abbd6ba08c22e2eaefa687cf6ae33f67bf3bdf07793e8e10128ba6f01b64758a376e9a08e71082e46bfe19564d9eb4cb602311223a756a87d1499d316f59260dc315c60532af3fc7f73eb3513ae426e6fdbc117e49bcd6295ea4519a02ce61072b4670874975bc86ca4c27018ade97e38a902a7fad9e41135078951595ee5d7121fa6b89eeb068a1a361659a0941921c4a0e5f23db42503f88e82dd955c6f9789d877e37fee05f44fb9771904bc6de7566c7d05b3f254fef59fec0a1b2a2e35f01ea60f8b3b1dfb0037dd51b33a3f97cde04bc4aa9408a40563e078005f00bbf94b1d962679374957a5baed6f5878ca5aaedd2e316c1fd4a8fff61d9983a938cbba3973d958d3d104485d53124483fda8a348ed4e8dea2565e8d214d3175befe054bc59c51a18b2a6eaca3d4e6720a4b14390eff349df23c8767748137df6cda8972b3d7e6c599bd39879f38de3a774ed8cb8f623f50eed76534d6a94ef9c82f369a953cb61a11e1aad8f206b8435005db4e81d94bf2b641f47a18a0f44aad259d958790ac964b1702aaebc4b40caadb03a665374803628eba669ab4306173a6baec79b77bc1da5b816574c87769ebf7d092f46f1489f8121814412ac036ed84005a6554a494cd920ebb5d8b804c0f65a7a43f33b471622394b4f35c9dca24d876aa8e5cdb09c50fd9c89e8ca616b2563bf03d31cd11e9699cf7f8081587abaea378b02d48a7eb36bc8de395c6307da59198dbc8ac1f29c539f8307df511739b84cc56bc31d350d52bce9955d6196a3416b50d38468e3bcedad775a09bc32926359b81b3b7b60aa814aabc4800bc3c3e75b71e0e4c47884a8bb3aa678aa87234278e2fbc5da9af56d14541f16ffca371e041ff605c06bf82230ebc54d62ba00f92bfdbacadb827016ba484a74483e0de639c742a2d5e24e00de9e6eb63776ce742bad238567137242c4e5c6fa8f3313b5b18a1dd8380073bcf39c700034001c5723f50a715d06477a93ff8286eb0f4cd84f4ca0b4e9", "spend_index": [ 0, 1, 1195087093, 4294967295 ], "result": [ "6aa6c8f163ed519070f1b5d30899f909846523a9f5d52f82e307f6e325c9892f", "8afde97214a02462a752ac79057c77d71b29c7092d41566c22ee2006289882c6", "6ce7c0be2b0433f000fcb0c4ba54e1dad8e62939a65b6b99299fc2afec725bb6", "6c86ce104cef982553616b66e045d4966c7c8c29039823c9d42420baa3f07c56" ] }, { "desc": { "Inputs": 1, "Outputs": 6, "Witness": false, "Version": -261671089, "scriptSigs": false }, "hex_tx": "4f3767f00142dcf017000000000000000000000000000000000000000000000000000000002cf836ee005ceea6cb067075c902188b7267c8d41847372c474a50b5fa4210c567208035b741fad25c6648c75350636ae11e4e5f8d1bc3f506dd8e9f736b5005422805961b87890e32aac131083f174433a492531c52ee7d23c03dad6eeed7e350334a1d673b5bc8571713712466d613bcc63afa94e31c5d7024da21180feda39b66f5948b7363bcf687bd73cf3142325a267423edda2e46bd38e5450913f632345d1f87afb0e2f7bde2821ca24f7b35d315e54c89c631ed909cd7531e271b820475f9f59858c53721404c59c22de68df078cfe67cb555b965f4fe79066ed4253ac84dc8c2faed9b7be85308eee3345f411b7fcc082c973ead339c527b9f41580dd57ecd2b651e4f2021cab0df68deee19f4f8b1d3f0dc0ee245827f9e15776a626e784ba4e25e5cac87a4f38237f86582f988659c8da97fdd6635340833b47b60d7f355f0a3c594adc66088617a421180617f4ff302be83d8a869ce3b5dac88770bb5fe367ad271d5da178c8427cdb57f2bf52d09e53eb52b739ac3f8ee1f7fae1f7ea2f40b61f7a25dc663247287eb37e9d07ec12acb11218417fff27e1a23b0192e6488b7e0acf650fbee9440109b59886d16c84f86b287d715375c60e69853f621999e780254fecb325460c18c1c533ffdd325b6dc7ab559615974a4e869e887c215a25811e44d14c3e1cde85302b45e4dcf90d6292a8098c30d70ec66ec9de3cb989ef335f85589918c77ee9476bcdc2f77f75455c647a4fa458b2c5b0107c800d575dcd7776500d98dcc87734fd10c7bb8ea57bb1ff34b124144c075e56272ae8b922cd0a97592d820257fca45f0d4b020cc56b75bb755301717b62995838bc8789f610037dd4ce3f4f91c9050127373f6f25b8380a14f8b4a835401feb2588ca131c85e4a0ac5e4d2d52198438b4ef5fdd9494d11e919f6a9ccc499de66092e2d5b815b1af828b36afdff71274bb1e765c118585874d12a1f93f19a7cc490ec809ea923214f526b6bbca0bbd44363cf74cae4853ccc3631c51deb06c6b84ce6b1c7f8891d5d86457c28835bb6a6fcfdc3fcdf5e1aa01ad043bc8586e03aa89de83b85d55fb367efd4fb0f32512fb352d2daccec669211147b9bab8b84c93c3fe18b878ab6218b2e93571a75b9e405537f6224058482e6334269dde4ddd732b4226d3292038fa94cb7c529e270e18bd1352819c8da36327eaa4004505ee199b3a4a6bbcfb243d33e2070f284304c58ead9dd512b1a5f616134105bfdc27689814da6628ff7decda254d51f56d48a18aace93b425ab9a2e850b8b3554e2f4f3ba93ced376ed2784dbce2ac333b189bcf91fb6ca0048063114a1a62aeff98b67ec3901d1e986cfe63e4979da9f13c642ed55a0446ac66df97231f3d025db73d707ba8eb6f140b9fd562da17a8d4050be92438682fe6aae8682488a579ed8302ea51053bd525ed16fb71045daff0aa5778286357c8a2eda9923d11787025945dc3c2ae1e55bc85f4128c5502cbe1159affd70b6320b2f6081c64f55304f3582a42eff01da1231dbf3b4411eb0f12e03b52f8170bf0c721920912ca9337754c7014a4066ca13c032269bf59a4aab7fe7ac4265abf5e34d983da5594abaf4eb582913e3f712ea08c3f861c6cec3e182fe3a86903e62a8d0dddca5a8348507ceb9c819a20f7b721bb11b36fef9e22e6344ea75854cc8c7964ff8040a853e13138fc1d8227f6e722805f53345b7b540efb48b0f49cf60107f3885036111c3351f42cf92220c7193e45dc57749196778a0dd60d267", "spend_index": [ 0, 1, 2550797592, 4294967295 ], "result": [ "ded67ed13e00b640de7195e0da96c0405467542644a4794001bfebd0c6a2b9b2", "2ba50675e027fa8ceccb9244f4fbd5fd0d2366cc69b38a3f3a5ace71af7c6ecc", "f13c3dec9ac4a80790fb6366a297cacb6493e44382342d780e5b0db737216fd3", "e0e7ad3d3908da50829786291541fc8015d69fdf65e4b2727e084aa5327c32d7" ] }, { "desc": { "Inputs": 10, "Outputs": 10, "Witness": false, "Version": -314128345, "scriptSigs": true }, "hex_tx": "27c846ed0a80c6e24c00000000000000000000000000000000000000000000000000000000ff8b159f0074cb1b9d5e00845d000000000000000000000000000000000000000000000000000000000e6d24edfdc201a28b5437f918eabdee7f036abf5d17d23e586a13004aa00252ee7eda09b265715050efd3a7ef31e1f77a8dd599aa4c8478a07833dc9ff8f95b9c60da6eb33b24fb516703eac7754f660014ccae667be1c5f72718e58074f874216f389b797a611691471f3594eabec54194be149927007950705646c1f3d45d73363f5c8cb62ade56260034adde6de77851bcac997abebaa10c5ba7007d234e11d3d1e190cb721744a744e4374f7a1c5e2460d077bec111dbb0a9d3bfb6544d4b469fa80a4fe5915a4d0e2301f7834cb149637627294b80ecb3e9d5ed92179964231c9aa680911da5f0d1804bf34534fa394fad36c7d974f2d99f4d0382eb640546e2094d6f2b7a6277f92b22f545ee0c1c8415a8a0a9bafe84e2b9dc72a1818c5b802bbb3e83bf9333c40a55321e6407e9a24199e40a3b6b390f6a58d54488560a926136ae70a57817c5c99263201404edf6ddc0abf690fdfe4e28741c482834aa265cf89821d2ee4c2a2e303b4e5c6d60859165263d3a3a10973e85da17102cc949b8f58b723641c5081a6db6daacd766dbd2464f14c0c80292f30d77d31179d87ac7a276d8994af4ea3b460f9a4da942497d638e22eeadd1d8a99d016b6e723143f2bf0933373229a7c36a876418b200000000000000000000000000000000000000000000000000000000d11eaff8b03747c37916c447e0bd12088ec8991503c5edd6787b75aaddf5fa306a25d779522788419be153755991799d8cf6edb31a99de4c285733a28521b2125bd29c0bf2d59372af22fd4e2ed4c22782d55c77fdb1e06b05d94f4eb2d1928b27cec8e0c897f2929a064abcdf36727c9141febefbf5a1c64fcc80fc13384622f602ccd0ee18b0c63981ebc4ab01ac36b60f7fd20ff4bf192c2b6bbfb832e7b1644cc23b724f3972d0d8bb5beb2dba946559f7978eb6d33e5d9a0798ab00000000000000000000000000000000000000000000000000000000c7ade67d4a901eefbf3adafaca07900b372acaf84573def30025cd8ad79d67698c9394c0bdb8a7e81fa893aafa2cd596cb1e41ca96c376601e618c29defc023dc73ad746d3dd2586b39a2307e5c4a6a385b3e05b25a0a0000000000000000000000000000000000000000000000000000000009de5f8a1fd6101794a308c3a3b17197dc5bd3bc31c1a13faf76290c11e22da8e5243e7f9df2de976c0d3c8cb3901adb94df51f822f21c4d105f186f9e818c23e2c2a61002f518715e8c61a4fff2da5c967bd145121950a8192fd642ac909c810f6e50d69f224a2456bfef2394a8c041b92b51d752165d5e3beb68c97f2774e87ddc6775fae42c6858026f3c21232d45fe079acba4df781dbdc9c5971500846c76a73094a3f0272b0ecd56d9eadc50e4657e8d04803bb1fb8eb161b56888ec4a59e2b937e832d2cf4f89acc88a4a283b798298d01014c2a6755779a8fe9e3cef6409679599bc668017fea94a7d34fba2ba1d8ae20118bb1b4c75f1477844685dfeaa0f669752648be407001399045ff125bc812e67ce6659760f7ffa10330cf63933df273c2a732995cc88c369aedf0adfe9298c2004697bfc63290a3eda5eb32da15d28505534e1a652694f6d69eb7fbb925767759795bdc475b558dbf8c10bfa35ec9438b675758649f928c5d1cfe42000000000000000000000000000000000000000000000000000000009585b4aad92dd9dd929b8c4541a894d112ec4c345c01ce68b81ce1580eb15299b20929a6d0941b889dda59444eca47c462072e0822c8aedb88e0c37413051f74417c85c677602c715dacf1ef27a6b6bf96f2e757aa35594dc4768a7ea74c820d686612e656ca5ccb186cb0239b569e807161fe27c7094923f0055981bc4e96f027b33fa3a5dd431facd38f61127178f613ff89cd558e74aaa34b7ef87d7e4b58a8c15f6ecdba9071af642392e70f8fd4a01b23e909b321965f2dabd76b9d745d4cf7357c012f882f7fc14384c31e149b876675061a580f39072615918a45e11cd948eac14d8400000000000000000000000000000000000000000000000000000000489fc2b600e6712876383fe97d0000000000000000000000000000000000000000000000000000000096264e77d6689608c11c1b96feed680b3b8495660dd2f453007831b97d9d9e81761a355aa73e51d3f2f21874d15684065e4ebe611096f849e1929c67178036eb399a60f53d2ab4a4613782d16e98112e8dbae0ac212a82197405cf1f0f0f8878a8badca09a6c2486123c8cef6dd79d97eb02fa9d6e8411a1a9b47eb012617f3882d289f753a42c35783f32045e0663e09a309486590bd44c53844423b016bce45aa54319db1673cc7e7d6b74fa943af69c6bdc1c0d5bf42f63b3974ea79e8cd363d5a478045842bf211b0627b998b04251ebe163ee93e5484280822687b00de3d99585000000000000000000000000000000000000000000000000000000002a8dd8ecfde0019bd51b99024f038464fc907f34a6c795eb4306462677d6fd90208dc2d8171303cb23a999425899bd694b5ac52e8327d274888b75ec09dc85b3c89e8dc5fae1b15817f2fd6511f97aaa0889721003c629c0b051abc0cd6fb0b9881f95cdad9496f466ae5145b2ef0b53ccc31b7458fa376b4ed1a5c56480bfa12bed0eedf90085c901c29413779848b57cdb1e11ab3bb8101bb942aafb72dcafd31b4e9ff2e5d6ae15fc93a3bb1e1b9b44cfe7d9e9a32224a98510c4efcc1ec26db86d9c80abaaf7c806d1375e77daa379cafe1bdcc35683bb1b361552cbbad843a0833e024d1ed0f66df9a6627e0353c8c6fea90c03a42e1d018ef833bd56623b4cc1c91833c6669de6fe7f0644af7284c158ea81c09a7e302d6b46eb91aec4499a8d8cd1b89baf7d40c408d173be78351705de63cfb5d34619d380f8b425c04be8358591a3d88c19f648a62d097d7b3119ea72d45dcfdb91f29e52ebb8dcc49afc30b571ff89aa82137e3bf54a7e66d5aa6b2b638991fef76057b1dac2c113d6e2a8cb472f145fb22fab646e74d6d4835f0c031965ce46ff37eadaaebc8d4cf0dc8c43476a0a3b098ba4652ff8e2a4e33d5103f884036aa7577ead93a06e24469345162975412508264b8ae7d7432462f769e300c2a63f3174e803a48d1735e2e9b8397ca6ef96d41350c4ac9122000000000000000000000000000000000000000000000000000000001c1e0a33dad3591fdf0a81549975be8dbede186c82ea288b85a3b73542057a2a8410f377acc3d5a8042a3abe9e48b889999fa94e632d20660039ee5be42fbcb1c7c2a064f1b245cc8f633c1e0d57f485d68e278e42b162b7bb28e096b85e7bda65957e599bac7bbfd4c9f7e48fd351755dd75e26f97b7c377d2ba4f54b6ca34d265f5b2e47a95673780847257ec6aa89fc011556d186aa4bcbe244b258ba65231d1677c13255bb009e4ed81d14d301d376e35f7f1ab917fd7881b276fb589eed0f1ca2d27b693c209dd3146b30abd12784f1057146528e3d06cf7fc18a66afe5fa780f0a46b0c476e11c0e11c85e0edda9a4558e8636df12ea5f709c430306d9e6f68451a5e996c6d3f3be7db5508c86ef151d8d2d0521c47a7ffe10e3465d313bd9b2aff8f9812248de032e270d0780ebfc5e38c3a08a79e94f6b8fbe455337cd84ca5f2370969a396cbc0fa242b2ac336051cfdaf04970158076832e55661d55935931d826b977b19b8688b367d79b795ee9be443abd800e36b2e38fdf717654038e9ddf3d7b251d9b2bb7f34996dd88f352ba3fc3f4b097fa507e550a767e942f9bdc82caf841618ae5a129bf1224beb2e5ea536b07bafbce673d10c80add70eafd3b58823c22a9667dba9e3f53f96a41aecc79b85c18093923dfc3b606264330cea38dadf45fb42f8ca5f6b53ccc297a66a2131aab3c0e332d75992cfada18ac24bbdc27ca738b55cdbd2255ecb7c112bdc2ca2af7fac32aae75ed02d0215d0fb92dc55bb67c1db0d470256f2ba0cfa216781bb4a025e5a7aafee3cd3f120ec9106e50bac17eb8c1d5746b94e425c5bdaedf0b337f1c042244db78da9f42940c68cedbac6049e00dd8658deb80383f9603ae735a6f13c98d42ddaceb6490b5ccd732fb068ff83ad4c46dee5fc88e865f33dc1ddd00213924837e4e77a29a9aaa962e9eed5be821900fe77321f0397fa0cd89ddc390414b59d73059014a29d6ba0f51d19331fe7906b65d9e60430588b9813cb7a1d1b0cc7d4af69be3fb459168ca33b835f25377bc7de64f1e334465bcd92f48476915c35e188a20021328dd6ae5edeba6ceb11f7605ba708aea7cee409ac7ae52fd79985eb6c0937f8de27c95db4d53dd88cb49ef4d4ba44aa06ea60ee849f2aca8a300ce85603512b7741f31af9e9cb1c0100bb0baf36e82c72429ae9f56fe6c28d25bc1e80797d966c8e2b6f7393a3b09e6c76ba16432bb4a9f8c5e3dbd6395afa0755e050b4ce2b8c6497f366f4278bc0f45cd7c88be082d7d4e271232f54c09a1e155b2445bc579e090748be3d011d181c49a845beade68a6f6f8af6c0a5596380a9fb46a81c03402c17143999436b9e57f22e2e22d7c568c917f6655b03dfbcc7b5d4f6ca236079e2287338b971292e06c6f5dc4a3e2d4426d49b87d09a9f432f40b90b431810d88c6d18e4a13ac69b78731c06c0d3ac81e572228332c200f1b48b1501880c0fc452ae815bfe794e332de32d1b6b7acd263c8840d834946ea5e174a0650a2dcbcace62cad3f70dea795d6a65610a242b19733795d4baf645dab1ccc035c5535fb0584aafac55aa591f71561211771f8dc98da6074a44c524721a5bfa8f5a46784aaf9e07859efe37beb8abd97becf88a0e6eca66b42f100a41cace723eda7b91e8e7c869d83cbfdbe8d36ea677b736671f85c4c55521ebdfdd8aaf6dcc519f803b9cfa7b154f8ffa39fb81471178f88da7fad03407835b4b767b87655b5e44f261f8eb334c4dc96e85700d30d30cba2a4a254d86174ac8bb11e9b9f2eefd27638883ac8bcf0e4949096bf00fc43cf99b44f9fc12469c5045738d3643e72a029d25b323f1e3ce8d1645033f5512fbadf30eddaab425e7a19a2d9e23f527c4a85b1821e72a56c0ded32826150a04da789b01e6f934e15a5d32ff5e128edb0108d2a6f7fc4181ce9f7053e26d7ab2437ed5764788ee58289ee36f27e85f0ae48413a52f15899573c3500e39f66d8142efdb08d5313a69370b2807e0130d26a82ed3d092acd15d7ea314b209efd385cc49b64340ec654403c763a039a05bd1629673e36d5d4698bda16d0d08b265955524f14321d62c880de15f2431ff99042da3d686767e7bfc7897e36b2ef3b2008f47575005ef0c15e4eec0b788cb874154f8904f6d0922ac6c811b49d5eff4bce3c2c466323de1778b6c369c821242de0f06c773c66fb633a952c423aff0d275e5eb1bcb416345098d9597f6bc089a82a84fe4e1454a187b6ea4d4d08f705f5a5c47de3a0f54b3bcf7b8de10cdc6fc467ead97147995099fc40ee0bad50997ad02b29e75da7814cc67b296b2ce61e3d5e6fb962d6819e997f8c59420cebf26f4088b33b88e1e3283829c0b291a51b4031ecf974ded95e55c88219d1cce2f0a6d06990dca93743651986a07741aa668d2744e71d1035099a93a6e57a230dd21f8c3feac40e20f6285229aa295ddb27788a23d8fd005060147829bb5ef833dafbc56c209341cff830ba840c63bf375ca20b51378ae80c5abf8d7802506640302feb0c0b455f0dac44cf9de3726fd65f4e9d35b92567e5e44c45376a089b426ab9760754b004238f210b06c693bbe73947092457b0b770af0a951b2098a4e2b86cfd6b8120e34dcd10b6bea9acd92e0a92cc56f63e7cc062eabe9f07f823ef9ee6c587d9379e19450c46c8d35791b8f9095a5f75202c78dede7088c77484726bfc91eb3268ed9a9598b069e232cc0ec4dc02bfcdf697c7d6bb9c9e51da9b93a05cdf0187b7228debe65c1ff3067616c4e7276a460e8f4932329867102ee8aee94c5216757ff47a79d5bc1c2c764593fe80bc04771b0326988c067579752a43e647d201405b2ef4974833ccd876b47a4a06505404dd4be1cb1b96d1df0e4a1f68017fedf74803eee63fe3a9fe32219df72cefd86367cdaa378f893149d106a0e60ec3bf2d9abd50e8f3330c80b577d9acc3c70335fbaf3c31225820c85eda9d0e968c5e06687f77cfe8810013102b63f82f9a8a166e9bd06f85a8b99efc4106cc83d2404c8e709fcc2e6857d6666e635620ffd2f3c8c0967f0f402877c12a269b124ee1b6b4a3173bf5c5f47977b29fee7690997108bd913e9cfaf0e056b232167aa1bfb7b61629d1bddc4ee80a0d11716dc6fe897ee47610da07b27fb38bbc71ba392731d1c658f6ed9d73c891d476382d3a67d58c9ddc81c7d290041846f4fe7d81981d4ed47217ab2d843d5b8771468ed90cc4bd8efa2ba44beebe43e0651bfae5d1f2ff43e1e7", "spend_index": [ 0, 1, 790666337, 4294967295 ], "result": [ "147d7ead14620070d32f02fcdc3fe3bd2e312cfa54382e50a92f7eb14b3ad43b", "5680032bc0edccf216420a54fc533a0d53afa6359d2e5b7d5fb6f421c5f58067", "16e4e60831dd39d29859ecc35456beaec2c0a6f72ab0a4baaadf6c4790e41699", "6e43d440e6c62d883f20871bef73df87a78cb683ab96c2f478a639fa5d137274" ] }, { "desc": { "Inputs": 4, "Outputs": 5, "Witness": false, "Version": -2004472070, "scriptSigs": false }, "hex_tx": "fa2e868804fa32dd1c00000000000000000000000000000000000000000000000000000000df35eeeb00cfdaf51a02780b1b0000000000000000000000000000000000000000000000000000000036ce5907001765c8dc82fe1264000000000000000000000000000000000000000000000000000000003f6763b3008dbe2fed8c76a4fa000000000000000000000000000000000000000000000000000000002fd35f190080a4b52705daa84b4f702ba527c8a2d7912a18b25f27ce07a923ccd658e3a93d3251bc3ada48464a7dcab9d4f116a95b7afb86c6cbaf720104d337c44a4e46046e2c1852050aea8af53b85b495aec3ef5fef0395e51624bf7f17df2e090dac7b1649e2f4d85cf82bf488fdb1d61836027cd128070545313e1f44cc6071a66f0075b2f89b7c20c216a3bc885cef83d594db270884d4adfdd3eaac8e35954ba19e7171d6cf23fdfa2b3bf5e04adc6b64225e6c2d3fadd1c2ca275b7dfa389e851201d8166e1998a741b7311e41989c61fb215b3c9a9e7144ef55e81a1dd057c88373d17da92f6c869d537fc808420f291ec329f5d91c26d02d9fc28bd54be2d42fb88c12735e1bb0e7f83d916198868259b5eeb4128a843ff48c6c17b430a636a081209523cf10549b7abca424368c4eee8dba7d57c6e69a6c482c3cf3dbf020c2d7b0a50a852a99e1d516007fd6dec5072461eb19812194fb4d870e03e15acc679203093fe771005afc7c8ddeb22c4a4ccce4944307e1836176843af4eb2be90fd26cb90be6b4ddffb307751fda4f7b9161ddb31c2faf5704e9ea5b78954ba695e06c7ad2f4a8ab0e0a05dd1d6da322c857cc0b149fee01b54b4a3d4640931874e5a92d8f5cdf6124b7a3c58336f7973f250c66e7d37f5e73c4954a91f669f54dfb544e3a019a92ab2adbcc30071411ace79f4a039c58fc56ef33e7cf87f65ea9f6e2bd21b0c2f88c43f521ddcc7dfb0739bc70d85c1761aa3e2474a129d0bf16bdb9678254db8d39cfb669bafcf9076899da38a64c3386b319f37431c3a195ca292ee99e5b1082c0fc6eac72075af73c264257ba8733a900244f0fcb3797307b5ef30e644f73466aeae75fa0a2cbde0c12c8ee2386f966fbae9d6c09366e803dc843e02c3b1cc0e09e27f4c7fedd506b18ddd5b67da189dd3134f8a896b2d8272a3e0d38b7195d7b45512157d9b868ea79b8c2f8675a8fc1151947972361caf4629bc8c7700ba977794b1632930ae16b47eb05b6f4bac7d731a36081dc5bf2fb15dde1593a08176bd158787beb7985cd1c49f16084e4c257070f71afbd0a9ae3945644589396585df6deeca13dfd547cc9757a449ccf0785676666ba67db68b608ef89a0935a57f7657ca145911ba7b102c8c54498e03e66e2e1de762a53d5871e707e0404c8d72e87643d6c9db5a2a53bc82c56cf4474ee01fbb08276b103c13d8b1375b46e56659d18d15d135cb339f014e7b713bab7713ec591e10245e175638f4436363739b79c4919c4d68347e74b80a0199311bd7150a246410181817d2194472d302899dcae22aeebb04f8d4d1325feae485c435d5534de05a367cd4ca2292f909982a166e8dc6a2b7f1c93fc02b0b350215d3c9b28cf1758ab0c033f50cdcbd75e44a14cbcfed6488dd8cedf6c3ca1d4f47754f2147d884f7ba102ef5faabcb39fae61c14ad46837db28321eb9d65dd365a879efadef82fb50fc", "spend_index": [ 0, 1, 4101939609, 4294967295 ], "result": [ "b9d8733a838d2cf61fefedbb592286444de3440832fc73d1a1206d7485a9e3d2", "c48192f629740141e47599ebbb22a0931225689113e0a185f55f33c9d5be87c8", "68eab01f3ac6ea292425ae8c072fd2a0945bb497aa0f95aeb42e7fc58edcdbd4", "c8c9e45933f973233075bcd7142e3e74fe8429ce8b41c0b74dc6e6425833eabc" ] }, { "desc": { "Inputs": 7, "Outputs": 10, "Witness": false, "Version": 1446712085, "scriptSigs": true }, "hex_tx": "15133b5607c2cba0710000000000000000000000000000000000000000000000000000000040609b0700424bc07f98c5d920000000000000000000000000000000000000000000000000000000001cb98a6cfd5501bbb59547dd3d0c1e66b56c839684696ae9d554693f1bc92101826a61a876ab59fc7004b7710186829a8acc20bc161add3ed5edd3ed495ebf0037c66aabf2e6fa0e7b37684735baa980583cf96620e749393a728302b093ffe5611005e4ccada468800b495f8c4bcd638c984824c421ea4d9819b601fa2aa5740aadcf5dc670ff7ead04e1f6814cfb0608cbb8bfa1deb4b2640bb4178498659910b2114184bf9fffca8d82f7b80ed103106376077a28a75c4876713b88bf754679ff1ba05b9582a0b01988943789c7c925c8f418690aa8a7ad3c604ef67a528cc0d7198248b64c0e526c696609eed82875163929fec762220acd0b0956d29e1fc1e28bed792ef5192a099e5ee5265c18f6300c3ed1ccebc47719cacd91cd5760cd23eb5e280a033aa743d5fc01321674dac63a64c5fad5d67c54a4909e02e265600d5b38736275d344b3577af0b1a95a4b2cc58a6ad01821d828f859243f49e3571e0f8600000000000000000000000000000000000000000000000000000000cb7e89001e67dd4e9f07e8e75b61b1ab092976d27b9160d39acb4def7327e6933516af60026fe2e86844b500000000000000000000000000000000000000000000000000000000703a47660011f2a8096bde483d00000000000000000000000000000000000000000000000000000000a1f21b5600e65010bb01c62adb00000000000000000000000000000000000000000000000000000000ad72827680c77e05d377624e4ac98dcd221ea62c147897f9a9ffdc3898c4c572592fb31b46a110428fa3a7f8cf7a6f2abd247275330847d6a3aa164ecfd6e9bd24a8c2dcc8719b6159ac4efdb7f7b551e036bbcdae61c86017c0c716fad801f760cfa1ef8afe3980cd3d8e1b3fdadbe01eb3e13bd628e21f521073feebba0247b45ee586edd13b3083d22d7836000000000000000000000000000000000000000000000000000000003800dca4fdb501bfdd2976bef3a9c3f25be5f591f0557941e9dba9d44de758e3393e564f0396cf2cce34db3f9e74f8455b835925e5472210458f7ea6fd7cf6e7b49a18ab0ed3fef33dd58047f9199d0f17ca8ef0e1711bc2b82cd76e88314f22c71c87d07bf276fefccbacb0a4b5d2ae64b0912efa400740edda8dc5df5e45d422579928423f230a5b84ed0704470a5804707a331918b773a03559bcaa8af9d38544f8b1e515083c6fbbb4f050447841c2be6bae82f8af7997dd36703d418595a47299088d5f7081d24547cc93ac445e4406ba3350b4c7d921a19bf6eb830386f23b7419c19968ae6a8b801d56a8b616843f41d7a14aa8b48a3a7549cb25f91cbe16bf4e8cc1c3928afce289fbf3891c10e3de8f5157c6523af71d5ea32fb14a00d1b3ed6546ceb515c0652171f97efc9f07e493d7cf2b90ff4ff32fe906d4695cb27da5c505d0f30ce50d2b7006a4f7490c44b959663cd23a3b1eadc2d2bc34eca8031474f3790137bbd9585ab386502153ba3c8dc27e7314226d201de0966ec277f67bb6707257284885526ec3b1007f0cdfb7cdfa26d418b396af6667174621bfb3fb62b44a63ced32d591e477996581bef111af87f79a56d23bdc24aa8f70a15318c27d9e6bd0ec87c000217f88d3bda5449272fd5804bcab488cbd3b06ce64b77893f9154f0533e0388e9bf89406cab037a6698c8a97170919b49c99ab04746a196466e4927afa49413dc0e75c0bcff935676a27b1d0b21b5b72336a075c4e518a053d66e210f957420756a6fc5a3ccd603c00481c4e3017305731e1c1b3f21dcecc89e2b7f3ad48198263d0b3c41acd65a879b0e08c2defa57365f778fa539be998fdcb3e71b00318795c3173695014dbf44b31322ba18f581388f57a01f444896e2ccba15d10197fb4b92ebf88a30600c4de35cd5d95fc84268479cd00bbcaea2069e8d628a497a2db2f3fd13b4f3065e138601bc9d3293fc2ab76e69ad43820a8567551c10f1b8bd95deb63f6faaafd03d14188c8876e1a11b12d112f0952ee0646f06ef53b4f5dc7883b65828e08d9fc205502e14603e8b443a1a50b7c76fbc780eb3259513edb6dd031e9eddcdcc67f5b87ba42700c4961ae4862e6ca7fb666fe80c436d3317dc5a761a4913364676739014b0cf6853871cfb26cdcf04c880e57df20e5a63a15b5e0e293eb88953a392262fcc478413f57dabfbe45e33f3c8c09b9758578020c83cc580fff6a11cb3fbab00ed7a0a9d5730060b382759354b1548d366659b5d499a6f995515c42093fdc858b5006c58a80285004c648071de196466ed4c18c428926626c980c30c5f998ef72e53a05dce9a24874c5cdb7866587ef5c65f0b0635213e9a4130dc7acddd6febfd0c760112ead253b9c817292569a6db8dcdc7e907b11691dac626093f998c4442b8d7f55f8e3274b49dffe35a3895800568ecd1f6a3acff582d3dbfad7e315af69b204ce906f7e5d2c76a7a939c7aba20681678de9ca63163971ff46b21eafaa0844e5c62c84d58e9322edc4418967a0b2f4bb68d19383054ef11620778594623f8b0abfea055e3c9384ba15b6a810c2e92b8586fb77bf469412435ab40dd66cfbe958106afef14757caba6e0940d353fe3582a7483422a30bcaa35a9edfdbff8280f6adc10ba940b77daf81b3a6202a7c8893ff04dc0b7e621f4822bd96f08e378840a6a1008b0f64b0b9c2daf75f8a783deba984d3892bf65e99c02ab2f10eec030f74469ca2bc66703a177891aa9d78785f0b159a6d24b97766b806772f188d141f56a50a5d95ff8dde15ae6c2e43e430ca6323ec8384adab59c7c13ab79b3a75e1cefc6d62e98746cc0b35d8889bce1ab448508319e85c55fd0b86a8bcee1c27e5912dee8ae70380adc787b20a7ed4d851c62767ffee4fddc68020be50f2a745e7b2bdf8fc787ff0afbb2984a6828fdde02da107691467a3fc5264e17d1e44cfd9e7f0e4612a2049156f87bb0fde500b3bc2c331e05e0f9b72bae5cfeb27aac51a34ec72bff597700803446e862bc71dbdb2ef4cbbf092bb98c8a0c85036aa2626e84cd2aa596c60c36b98263fc2d9ffc75e93a94bda39f8f46b3bba37c3572e675be8c6ac8f29282e5002dfd857b42715c40eca3f6a01078c4e376cbdf2803bea3067f9232678e696fa03c6e00b552058ae5ffc0b1137f8470a39d0bad15fc63e1962e45b178e8ee73b6e9eab2b442634fbeed3056850a9e2e3cf13d46d5edca466c5ca784311d5b8f6001a7ccb0864edea23c8c5c3c886ed58b64f3d11c07465656b1ae6d5f9d66241799fd27030b0779b1bdc1e4ddfc9c546208de35cffa57a5325c758f9f80ea4d7c06008580a3958410f38606953061938942dcccf8eb748b6d16123c5361a3dd3996b19b8a605d437b70596fc8a2162f94510b5508df825f07f3061033f5813134d9e722952e0cc546cb189349b6bfce54df36711b66e480782e30f46d2a0a6d4f10b623c51aed726514efa70d303c53c8be54bfc1dd8acb76e0529aaefd2dc1775a5cc07f16af88680c40037d362e74207d0114b0556a57e6c5d2ccb4e7d99426078b4d260df66b2c8b02ce0349cf9be23acf2687b50e78f7e6422477b87f9ed1f63b55a7857c508b2adf6aac32e2818322ac12503edbaccac3834f7fb65314cfd183fd7262e459ad68668ad40d0005f0f99d46316b8f2448f1e38011c8bbb2ed3ebe96706bea3629143ce484ebc6756873ef4b1e436a61497e1756522d7530cc143ad7aaf2b5b6cda40bcd97117daf5f7077c6dccf63e330733a05f782e59c5e95b251755454963322eb0ed2446db1232144113abdaec6c0e7df67d4d4cf540564b898fb865fdcd0e3972afff8ac7c0ad6dbef9ce053e5e01fc80dd044351f5c0cf926a53036758f2a03d9561c95874ec698685d97568b137fc706bdd9cb7d63c225aa88a28d120cbcd52411dd144041f2413a3ae274e5111233fe3237fcf0ca8b711291319fe64067492bf87ac8395687a2590fe8a4baf463af8613ce15553a64863e11d3289f80e7ca37a01c95cc9221d26a93210a379c9aab597374417cf63051d5a945ad6f3b269523ab30250244508f2f1459bfc72250882b79c3e649d2a7faf898b915c82548a89de799f8ede390a2448f054007eae584964a7697a52cd9034778db678ae018e47d08effde2a1721c340ebef76f191ffc2211dea913b73fc8fabd74823c6c0d33a7fb0d6f7444efd03a6b5e37dc0ab8de7fab309a642c72ec1972054de15fcddd201c80b9af14b3a555af753dbd117e86fe7f5600c86571d70877321d68a8bd20b76d0c71c91897c142b54460c6982d18547f2a95f0a979368380a5a4111455cd830e36a8ce399cf578b0a54a1581f89fc1fd683503c316b83b0878356c42b7a4f01c3a85963fda197500d1f21f1646c8915800985b1cca2b8ed9e0331cc4db8ca8953810bb76d83e622fd33f03efd5a338f6f1a56d77480caec4ff1038619f78bd86c8e0d5a1272c132376c7d781c8de4d01d0948890425559131755f4d397d37b8fdaa0254b57a804c4ee77b10cc5898ab0c93f808576535deb43a73750af2d63", "spend_index": [ 0, 1, 3610166742, 4294967295 ], "result": [ "a581267570b10d637e1d7b4a663f015e9a74bbfdeab72581ff16e76d8b8c27ff", "a43d65c972980ad3ab70db2189a1ecc389c33052c22e96002b61be966c644832", "8d4b10716dd0b940ae288cb38754cf4ad52c821a5be584182cb1fb3a24b747b3", "bbd663277ecd2f4b7e3aab477f2f440b2b4469184d216dc99a94e71f549b4896" ] }, { "desc": { "Inputs": 10, "Outputs": 9, "Witness": false, "Version": 1429618895, "scriptSigs": false }, "hex_tx": "cf4036550a1e69583e0000000000000000000000000000000000000000000000000000000053b3ac7c00784308065011639b00000000000000000000000000000000000000000000000000000000231e523800461c627a3e23edf6000000000000000000000000000000000000000000000000000000004c20eb8600fcf2862389a6d9b8000000000000000000000000000000000000000000000000000000007e59aca10059e33d001536c90f00000000000000000000000000000000000000000000000000000000e843c21100cf7d3ad6a01d60d900000000000000000000000000000000000000000000000000000000558d6ac900e06be76a4fa0a26e00000000000000000000000000000000000000000000000000000000530c17a20093edfcdca778c1dd00000000000000000000000000000000000000000000000000000000329aa83b00167d5bf0effecc20000000000000000000000000000000000000000000000000000000003f779f7600c27f2f4be65470c5000000000000000000000000000000000000000000000000000000001d5b9e7e0032eda9a109ef86a95031d0431ac8c79237de2fac720028f16a99c45ecedc6cbafede718180e04c7307479ac3f2f8daad7f99fa08476b49be2c2cf0f455f59ec467f3dbee8cd7443e5bcca8fcad104b67193dbaf24506a3b63207264fcd3ecf49609ffe946b349e529aa8935fbbb34ee04153b044c0b6038d41750dab1a558dd73c833419bf138a08684202495b94182f7b2abdf139bacb177288d20fd574be6eee5dbb2feb90a788e4c7a09b6f50f0aa37ba5439b2b15d0b39d41bf80884bbd943bb60f2bad7a6410a80bd9712e3e20c2fcab17daaf3332cff0e48066f56c87b47280b1119719d8bc26ad2cca7bbbb6609916225e9523e4d6515d826c528cda7d41d46719006b86c448c0be850874ab292a534ad431aef35ffbbaa1f6568b284c003307ada573241f08af8deb6ee1836f5b26fc2934852fb8f1c50c94dcea454299c57d91bc303b22386975f951a5c3181f5c631b11d446d5bedca67e4f5d135cb3fb95d88785eec8edaa5258d4ac6cab78e8e0c2245f4a4dfc393044cf0677832f752042ce6412092700a8367bb83b3ee55a96ef59b9e3eb80131db57ee43d04d6dca1928a958d82a72ab42e0cc74c880161aafe35571887d42bb41b807651bc9115b8a7266b22ce3655962571f05a794528b47f479023e513c9ff51dfc19302a8815774c38a294aa883477bc8ac5672564ee530cfdbfd464ee849750e977baa3d23bfcdae91ee718a51ab671dc195d9180d506b8562167c9478c6b2ffdb0b3984c3ff19f785a10903d7489fce9de8f3b5ae99d2fa7362510154aa066c30d6356386fcf44d985c9a13274036084d743e3143f95f50b5331798f669f9c86e7ed96840d4c881bcc2dcd9b4aa689f61c196f9873ee3c814b00da14edf52b422173c8f7676c1c89763eff57daa598271a24392a2c87ac24abf4ecfd00190952f275499159640c3faf1dc6ffdbdbf3e19d50f132a8cc51fd16a669d8f44b88eb3df1d181513059cd12be4f1c78ff1d4c39ab6fd8be05e9897b33489f1ac730ca61277f2c88e0da172bb35987edca8d4bb8310741afce8dde16fa2092738162561724fbf8e848c31752a86620cc50dba829ccd5698c351fa760dec06b787ae62c45a984252851a97627bdae70c378be540ca590c4947811668128ee312b480a95250807e8bbf26492e7d6517eb0c866cf24d879c83ffa01e96b7bef2be2a1255ad93811b9223ef2699dba5e28870258d43a7d3f2054b96364d50e200c9d2abaa6195593ad62d983e0f0a2d1d9a134bf185cb7808e6680a69091860268803d598ad1b14d1ea096ec63b347fc4f0d026afd93b674e943f44b286bcb5645ebc6ade6c1d0e1665efd0106fc781d2e0d4ca62c3214c04ad0fbf7d5cb84dc4c67d47365911de440ae9ac26ac463eb3f1d940bb9f3e4bc88af8fffb50af763a3887f5b06d4465aa480cd58bf6bd2d246a1fdcd371ecafad2aa8a24b15a0a713d52dbaaefbd984f64c85d6fbf6d936a646bf954f8af97d82893dbc4792ff2d916bf9a68ded2e1d749631ec9355ca968c6c22fc8c2003e9591a84b73be95d8ccb7c17d57898da59b3b5c6e4551ebc17527c352a4066c1ca758285db0a187aa5f6b9cd2a41f53ec1f2cd0774761d869d8bc475dbaa93eb173dd5d2a45d8126cdd4096309576faad4a7b8082500547c1ff8a0e001c0e32cba79d8ddf227c7822aad8d6562a8aecc396578e6fb2308df5096f27622f2628a3fcc8ab76b79ec509138f467581802eadc736690c050a44ba18b0dded1dc036b9883431c824b75d56f9f969de7f28e2bc40cce434303dd8853de7200c633254a7ac883f2ead10fdf386f951b4fd7de6e95374a049706bec917df236028714452552d0b68f2ac3e9551b2b8b40e2f4da0322f8d10a002cd9c686bfe8ba1e2b1b9d702f089f238432a10d7873294a4a299159a3238fb1146910947758d581d37efcb209d1ce30ba921048ab2c988d975f8e62aa513b67512d7e0ab1dfbdd64cb2ef3eb2f3a2a6880ab231db4ff3422b08e64dfcce75a8b66bdf82b5116e4567a8842e91aad3a23a27319b50aae13d6bf67d3c38252ec8e3035c90b6d5bcd5a8e771dd5163c2e8c409a02c1c1191d024b0df3c84d6824d8eb9888dd9dce0783c75483de2ec4a54c30116e1252e960e7cef4468bda28986d27611fc7484f2be55ca461ac1a742898f68f83d4b1d98abb4e45598f9df9065cffd0f3e1b41435591fae56bcfc9a9f88193ea6e74a403ea62ac87459a17e20bc9279a782121162dac972c44bb3637b4c44780c8f43ee51e23c50eff69f4d663af5fdc8e9d2d83542c2136f76c337a031289a40c40d61218d48144756cf728b3666a3c6ce35a74583a4ae814caf9ed0dc8360b02c141a887351baf1a498f2c1e342730484d8f316a7a1f5fa0242538c67e52e8f7be2b27b56527be0c043e9ad1f704c822c28d259a11a0899d950ecc24342f72189f226ac725d568fa016303287e44e499dff0bfe46ff372df241761d90a0d35d54523d31d4a1b5ab842299f87027d9bb612812623bb877801c96e72598d47e449a98806da0a8cebda4aa4ee671b19dd1501eca920b49f1a00f9d91759d5d499d66fac46c1d89b93086e267a54338d9421987f51d690cc273fceb1c621a1ff89c73bd27f88eb6dc6c8f1", "spend_index": [ 0, 1, 3616295423, 4294967295 ], "result": [ "edaea6235b2a50a95096eccf977cd9c6fdee4067c395e52623117f856ba78316", "1c4306f65455dea78cc6792f876c3c3dda28a8c4e58cd44cfdbf83ddf15eaeb1", "4f001066595dee1ffb13aed2e36921dde1f9fb7f509c4182d9678ad6a08b4334", "cae1e737e67d7f80941b39a0e178bad2d0748c8823596d765b7f3450b019210e" ] }, { "desc": { "Inputs": 9, "Outputs": 4, "Witness": false, "Version": 228922200, "scriptSigs": true }, "hex_tx": "5813a50d095dd52a8c000000000000000000000000000000000000000000000000000000003f68f1b9fd1301fdd5c373efd2d10c9c119c2c6ba1cb5d7338fe6cb30134c56e74ab2840685015dcda105d2f6741a967b13b4f8b18ae5aa566d9f2b96162ce31d1db10e7eecfd2eafd84af25bffb7185925ee8a844a79759ea400783c32abbbddda7a2db2863c1487237ee612147b4ca963bcf386da21d25504770292640a4d630234c79f002bf74d4d37c84c98ea96e4f02f1a3073617636380a34839e83c28982048d29fd0ec11328e1127baff539546f49372e36602695179361fe5d8fa358fed0336aad6a9f9912762fd13b276bf9bb39e5db98a95ecaaec84c18ac52b1331041742ca0d2390c094583311ac565d6383b80dd356b6e3474c76fb41b00b4be83b8accb7417c97256c13ab7c6316a87895e5b8e23dc7e1d5fb81937f85c0308fea00000000000000000000000000000000000000000000000000000000a349c5c529e3b39bb861b27cb85e78c80efbbda5bd41bc7b73245593b76c3ca8cb3ce09825b04010a48efdba5e682f350a76dc61c74b0000000000000000000000000000000000000000000000000000000077521299d1c9a0c7df8c9ae9b0bcf4f64ca1dbf93f769c755b87d72d182fd71da39dbc7c729b23d97f847aa67b046080c9d127b78b99500e5f5aec94abfe8f8cb31734481d30b24287563b8a4758779c8a5fdfc238c5e13530496861355c3d0e0eee0b6981c7ba365a5996d5c79584afe557b2d8c9acbf2e3a1fea1b18ae3f700b5e224ec7775a327116082f6133aadb47645d91dc994ef56393c7d7cacb54e8836d47a314bc8ad81778b1d16662df20c06f709451a4beade694f4ab59b80401890e4c8f8c07795ecf43c6b8e6024bed8824625cefeb15de1965ca64d685000000000000000000000000000000000000000000000000000000004da36e9800b58147fa27f3cdc50000000000000000000000000000000000000000000000000000000043785f350f5e92b8e86564a85247243c37e596200b86c7a059be1aef0000000000000000000000000000000000000000000000000000000003994ec08bc7f6a101e341758c55e5f3a508b6914268a8d97f73e53019048c5a243deed6de204f5675345609dd38b14831eb4f28212ff3171e47d09a54e31ada8c1575c2858f85b18e4c23e0282f1c9130e0bd3fc2dcd42f8642e7333a2589afdeebe42fd11c734dbc07744045b667672843eee4725871dd2e46ec90e3f238178f295edc4e8e0ffb4b342077b88601ccd133ff558bdf313500000000000000000000000000000000000000000000000000000000575e61e2fd340176fc7b02906571efc17bb6adc866e15706dab6b26b57ffa1b78843b585f9d66313ea5c2e46a74eb5edd59fe7795530ee0d98e1635af12a53ba24b5ae140246b746c14bce965a0878a77ec6e77d23d8b57d3ab5ae94733923fd5d75cb5d071f40e5aba7103a120c4f0cbd6acf326a51cbd45195165320d12ad82e240603613c8a1662a116134bfb89d60b2c30f58f044684636e96ad71c48eb95a0252a33853a0ca17d9e20c795ba7968ae6d89f56a9613f5a127edc77a453c4d078c146df95678a2df8d0d00e0e174754828390d8147b84a990147956a16becc9ae4c113a40f7ce62d33ffb31691b87eb5b47a4f48c367affc66a6c88a23a85813f6df5267ef6c4e4d507fd8f3555d9d03e30df1f36f0e970d58d9597652b7730e6d4ded090832d8033e2009bec58d40e179717414074635a58795afc83f451d6b01800000000000000000000000000000000000000000000000000000000ee8aad2efd140188125d5720261c8bde23eca7bbc6c90fbf666b33d2fef90bbf94aa17063904db0dd71981dcb9116cdbdca1b916155fe14ce3c9959e2af9e8a4348f4921b7a220f13c4ca6e7937e0e2991e560277f9930357d86f4ec7087315014fb90aab1fe45ca17ba23f52e52cb1cc5ccce2f5947d1b89eb5682c968fe4ada1f171839e91612a4730915dae8f907bb4f5ac16e030cb67b01c2d67175768800457967731164de2dba58553e5ce7cd6d700bdab8ad5a72f41bf89e42a82618308257e916191034012c70bf2350b731b4686d6a9a8bbf6224013a2b2e17fda8a55c560c18493555f83922a55e4aa9e847e2fe4de1824825f89094f2f2355b4ce819a8075b46a808aa11edee884ab155df2b5f21cccf8b991896de584f7db50156df95300000000000000000000000000000000000000000000000000000000e9d74bb2228f4e510fba6128202c9cb7bdf967ca6a28926ca367f1fc37f3c9984bb3311f8fb50c22bc4fac0412b090b5d4667d73c81e341b829b73715386b56933dc5938bfd028a699df860e772048285343b590d8a5589e0cf8e1b0a3d70ef7dcd59cefaaec33719cf82ba2ac1874dec67a609f572ed71c6c5cedfc2bb692270fa55a928279aa19d4596283f928c06b2ffafc9139d11d130bc8edc304590718e1c7b847f7f0d91eda897d1843c5dc119b75f7376497dd644e0716aefe4e8c8a0fd760c3e51c79a904d7c15ad458cd7c8b9871fb041072d589f1d6ffdce7d204c0f8003774d65b5b87c62916c911ccc93d5dfa5efa66ec894eda669245785c2f9f26de3139c8efd70dd8fc23afd84195e2a8d9939ff747be802e388639786862881ff9f649c058eaa43d59562a71e991e726134a8cb080de0fc8fd9f07d2b64ede78483f462f15538791f907ed941951cf5c503e64924812be59a67ab83b3b2b71167d005702dd1697fe4b3d8659e704e2c7187b851c2b3ac92288dc905c6154f50bf831c20d09bab034a533ee8e622053da5492d2e9567b5958a3b0e22c2505b187bdcbb7822b51dbf2228a9a093fabd7569fc741e554b6107acca2c9b11f9423f561c76866efc95b5575c3af40c67cb1e0d6a66052c87ed3b1651e757efb03bfcd7949fda19443fbe79268748a5936387bfe77db547dde320ea67bac879a2d67e329a8a2763754efd276f70195969d854f26f198f6ff192195ffef5dfc2d9126a68698ef702a5d5e300e7885823760209178671b16ebe4443b3628cf6610f4c4debfe6a10ce2cf1a62dd8e636a3c7da29f7cd8da80083e835d0cbb796846e8745426583425bb2083bb7ad6078397a13e776dff6e4f3cc8949da9b06a83f5228f2cd2b90798058a2636243d7c353d7d60c7cb3fa6bd5e1909e811e25b83715ff21bef61656300c871d91cb50a3d82be69648785cd094ca70ce8766b37f304afd5fe848df15e60f4f3e116fc2dad8b106dd04d8c84c73fc6c51399b6f8baa876e5d0586ab574afe9c573f9b0082641847fa21aa5f0a5cf8389874db7a0752b2d15418c1060a6fb5a72bfa3800bbbbc96473c99b6b3b63d27892da7a5412e15521ac3e26f84b127d82889e152fe5ef50b2ca13d5a0ce805a0f18361aa823c25b7e7aa4b678d59cad74b68007db7ea25e8224ea07b7db0f72d96607805d0239dea20b7e8ef059275f56c2aa92f6b118f159123f76a", "spend_index": [ 0, 1, 708469068, 4294967295 ], "result": [ "7449c7c0e0957bf2329c95151c03eec76ff335d8df4eea3ce509026112f28cf7", "170aceb5fed624928b1ec575e5456b1988a871de4640540bc21dbcc1d89b4879", "5eb990a684b48e5fc6cc68aaa7689a53c193b23aa4a57aea52e5087797aef82f", "ce5d9a1692d85326a4413a9b10d0019fb33b1bd664eb7cd9edde3907728cd105" ] }, { "desc": { "Inputs": 10, "Outputs": 7, "Witness": false, "Version": 1849375622, "scriptSigs": false }, "hex_tx": "863b3b6e0a1f4e0d7f00000000000000000000000000000000000000000000000000000000cea0a5440066796a3e5d5443f30000000000000000000000000000000000000000000000000000000022779f8400a4ff4c64dfc26ae50000000000000000000000000000000000000000000000000000000017de040100c67c6b7c5c76b2f9000000000000000000000000000000000000000000000000000000003140c06a0087e9bd04201b2092000000000000000000000000000000000000000000000000000000002f4cbded005f9c296bc4afa64f00000000000000000000000000000000000000000000000000000000d32fb30700827eb4860f20b231000000000000000000000000000000000000000000000000000000001996ea7100ac03a6dd337ed31600000000000000000000000000000000000000000000000000000000ec7705cf003fb2d6284bdc38b90000000000000000000000000000000000000000000000000000000017cd1c8500136e3e1a295f06040000000000000000000000000000000000000000000000000000000015f4d5890053381e2b070564ab6e710bdb43c83bf70f7051c2ef7598429146fa2fcb43cec86845c473d5862bfb49ecefdc0cbdf659231669f9aaa562ddacc88743a941e076577a5da974311b3b9687808f9d3812c280e1ede2c6277d3eb3559c6cab90410ef03f2b7abd1ba7cf3da046b8195a0b318fb86f965aa087edbcb2b27b9b187a33b3eebe4647921d1aeb466eba0fdae322d9b23861f6c1d68086377a2a60c92ef33b44063499a1039d02a617f6876435140cccb9c6042d112c6b49b718076b8feae65e665e28ace8ac8941917eb1612a71042d5cb6400f748590fd43424309c8bf3bd45d52f9106406435cfb3e0a2710964cbbfee48b49b25baf0301477bd4244bd6ccce535609ecc6dd12890a63251beb8e092fdd05149322558a2a906b990c5d674c1be436002bb846cbd1a6ab3f8b2f9ee3dccbe0256b676f7cc434cde676ef4aa97850e1ea3fa08f36addc89888fd59500d4c2efe01bf1487723356888486544021057e129432cf3a8b81145baffb2b6b7c59fee655ef0f43269912dedd8595320cf6b0daeb70001dc872343747b50927d61afc5e16407f5fe5e52623b9a22407e0c79fe35ba1ef7cacb457b7e66c838ae3ee3e45a9ccd189b49dc348c9d2ac453fc2ecd4d414848a59ee555ae0461d46aed2078803b7224d380f6254d7e591725db9a5b314562055ef35a7b3c4d791c2d4ee8b60426e4b8b6c413e336f8579e3aa157da4740ff73f935bfad7d9f970f5d88a6f06eee5b6b60bfec3391ebb41ac1f3736123784442a22bd5a15e1d3a61450c3e44e943175c56969346a71cddea0790c8b4e8b51f5e5fc72c6f24dd62ce316e15d51310e1aaed287c4644cd5aff7b8dc20bdcdca63adeddf63ce06b2a213e7f8f867fa5187f50573dadd39b32c8dbd7089b332775873a17d365179c5e5f7aa7f5d4944df978fff7146ef325817dc949933f907ccdc5fd0710fa9337412aa78b9a51e56607b59da97721e128a60c692e021d9659d732eb4f560ddeeafde52301c96f829a9278cf124f0b3492878e49b7c3836bf2fa41e237055c2d1fdbcdd4e4b5e617968e3ae7c48367cd4e6ad75c37b62f6a7a54631aa96ac03bc6264b2157019852dd42785e8c555390e70838e01f87ab86119bde43b60519feb7504c8c1c4b5e643721f80cc712a6efb4df43d64194bb7e6ea8567dcdece0e660c179c8f36ce2e56703f63e16e052c1b7ecb830baf481951510abd5a1494dd6a70118316af13f9b43d8b665546b9fc39c27236396e6cad4677d05b3c7c950da6f3b5c3406e6dc98157c78e1d28f9dc3a8ef12276c173893f0000273acf40e3d89ee11cc018468741154351d436c1da162e9f83577c894fdec48b12c670d12f92ea5f7809ff35bbab7b2370c0ca7524b0f9d01e556d9d0d6f8ca5aa8f044bb82f0362903daf0b56fbc1828d93d18c99f1454f6cd67e8b2e6938a78e0889f67c28bbc8cfa32201e1a3698baedbe3580b75bb0fb0ec87bc284ae0193da658f8a62fc1b695a682279a01e4f3591b0841db404dae69a374cdcb1292cd3f6cf5c30c5ff9ffa13b601d679b856ef86e370171955228c50b5d15e402c078a1b1a04c178caafd7ad885e6779e0c29787860ed55ee6639e8320567329a135b3089ee783b1cfb5252e2bab26a7c3bf40cbe6f7dc856f291d466c14ad7c8dccbea54047dced27aab3cf9369271deb65a3e7fa05a988908de7b93cb9320c2b31a18ed5332722f91be01d3d72db14ceaf8f4f4e8f5fb3501b5522b84f25f025b505fec29617fb575aebe803c8a12e593a9be7165776f717d1e7e5de89a8e79185d1bd691c578e0dfbae04c7d4c7f47267ae773b2de321b9baaebaa23ce5f1f1b76e6de607541cf7dcc00b694aab4ee5ff65d32390b08ed7eefbb9648f4e3c805daada431d6c2ae6bff4ad6920901808648d8a6796e08c0a3db9c2ab0ca99d8ceaa07dd59e2044484d4b4ff9d687e327f8e5f297963325d2917fc58033efb6d1f66339fde905f347a46c908b0a19eb1318b76b2ece20467ec1d32bedceeb7dfaec395bd5b39b34fb7e3d46a69252dbc446754e65c9cd8cbdc1", "spend_index": [ 0, 1, 3358500723, 4294967295 ], "result": [ "a67afbba0065b5896504b0f2e660aed9c45030de3392b04ea3b6eacf74f25c6a", "0c885fbc0ebda0ac9654aa951a9fe010e8b78d95da3d4b98972f0222d5f2b4d6", "00776d3c8512073f11d54616b089e5732369bbd5b4935d9a29f3cc80089871a9", "4e601cc58d1c96b29d4b0306ae89bc29a01a40fa69128aa480bb517952f3af1f" ] }, { "desc": { "Inputs": 7, "Outputs": 2, "Witness": false, "Version": 1798237959, "scriptSigs": true }, "hex_tx": "07ef2e6b075ed1430500000000000000000000000000000000000000000000000000000000ff78f49d00cf1131160c6c8a7f0000000000000000000000000000000000000000000000000000000034a318d6d91848af4d612ecf9cfaa2471fdcb5627bfadbdab545df89daef1f672d2814e46b6d15b5ae5b5e56dbe294424e1d8f2c28894ef417e41ae27f9573d4303689f54a333d04b04131ca9f3825fb365399229a0605e361e694c11cb701c2c71ccf5bec7cea486e09f2b710096f90bf5cfa4ef67fa991397cde17e356649f24be45c377294329e9a0f1539fcf230f5bdb8d9a128f9899d418af7889e475e64bb145b472d60e6a6b7fac0b4dbedf3a977df7948ffec09b41397f4cbb8046f27a4dc6ed090aec2c4ebbfe5876ed54cf3d016440fa9597c7f635a94d7cc7945d4bb8359c6d87000000000000000000000000000000000000000000000000000000001fc9da2dfdae014c120bf9bc218f7be58b7067cd4614596f7d58d1ab928fba5b0a21a3e81d8db1f8c89f8db25a72de162b85c34e7dc66923a2926cf8a538d44e6d2172366e619788448f071f201fae4184f990940ed2c51fe7a31b9dad6524ffa22d176b77a4f7e123e575baabaa35ffd4202ea4ef3644c7dc653c970a7f66c1d33a6a18d1b1a01e70b1649276f06cb5b46b2420605926ae5d7601cdbac978301a2d7909ddd43170786b3264fe45f92b89f9870364364aa2963ac5aca174cb652ed2c10b96817359c05ed283cd841b0865d53fe6d8230738f68de6c4f03fb24275d6007fbdfd591305066d1f310ddbc229cab9f7b2c51b850529f56e50a8762feb20787833399cb3c81eb2c917e016ef6476c59cc82f5be77213acd94a9d6465f5d51af9175ca29fe63b323b3febcdd43c2cf6a2129596a9dc8834326a40ac2476cfa29a7c76a0c5ed3c340ed9b531e54ba5bce4fe020216f45cc96675eb1c2790968441b8929c9430b3c56e42871824f4933d221f26ba67c3088bca40be87b86f95508a0f3861621576213069384d58535d8ce783ccbe22e2a9424a74a1f1cac6b4de29aefc8d7785818be5fc302704e8a63c08f0704a213fe8656aa900000000000000000000000000000000000000000000000000000000a7033100fd9e01401bdaeccd7ff2c040bfdb44d1656d0d54b665b2403e59e4912a8c04d60126407bd04224bb6b2fa327496d639c6d788e75e79a51967a27580eb355602f8c73f4a366aa23a5032c5c5f9777669917707eca2406ee9fea402fd0d5b64bf4218ddcdcfd010a6bb00f13c6ce09a05fdec05602636649f3dc4b6bc2b62eb506b3bfdb1e34060892409961e6dcb6263f085fb45af54113f04972eb8b1150d7ada2b6ce814f3e8d5eb5cfb112ef59813bca080496749a3a9ed0d14110acd032381162e13b7fa5fef0d903a90e23f5eb4cac9256f334bfc3fa2508657ad1b247e8f61aabed24f067e90cb64d369e3bd7c637f854945d58a547aeeae1b08bc3765ea8efa65239c7d5f1b2fca37c25a952de38c97224c8c9dd6073fd5c513f3cc69d5b3502855564ffd4340f8d35c763621b0a6f926b9f0f97eeae5f02343192832de354dfaa9e2d78fa6d87bce125df54d15c2b14c52df5b531b33e9fc793451527b4f4a35df5951f0fbc6abbb994871765f8c494fe6d843394bcd54c0f66f172716b7b54505c84d717f129319fd201d51854c191027df094ab07eb6fb6675423a2701f0d6e75c91ff51400000000000000000000000000000000000000000000000000000000bb3ce8dbfd46018d139bc3a62dfceda3d4b32db06baf6edeb1c6121f9a292486a92c060ee0aa0b8858ca8e87c083f3a425bfde773da3e3b639fe454b5f51cbc0fe03dede14118337872031513415ec11804593f83760a290a90e423bca0b99a127f8e6b632700ec71626b1db14ff277d897c7a9a5778edb073e3a3adc45fa91e09ee4ea17e01bcc4cd081679ed54cecdea2dfa1058ed5c948d1c38c4f92e7cacceeb728692bb93a65d3ec0e4f0608f23ba3190d0873667f31364f24409d0b6ff4f61cd20c4126acdb0e5acfcd7fcc1359a30993da1d7c8fac52448b43736b764c12c1684f62ce020dbc325d70bce63fcfb8a3348f29ef1358e04aa4a5076bfaeadfd8646f786ab872617e8259cdbc61f1ac5ffbde8700e10541884ab7ea980d0ba83f53e2c6d97cec6486a8c2d2d8d19056fbeb987220d8e97f25ea08d5ecf0f1cc4d844a48eec48f6058958585e2f04abcb39155700000000000000000000000000000000000000000000000000000000a628b2b8fd3c018097865fcd8fe6470455940a4d67fead20a5a785401ac7c866a95ef9a3772957fbc9365db696d03ad84e51b63cd418f3a08159dc76c7e2859b815429d50cabba3329bf3eb1ae70d3f610328aa7855c9d04a10e79ac916e5789d816c39af09bab264be69819f83b487870ddc2b7378ce083c6a6f925ddb27d4b19b5c693b8da8262e1e392dba31e586f5af636873a3c776e9d454f4d623bc5d6e7567343fbd8be6ddbea50bd1e6d10bc40228d779174789cd26272dbd4b27233d75b32bd1c7bcca3c56f014b9329d3e1edd7001a793f4fd8d0d1b4e78b413fdfe5cf56e992c2d2f02ac71d261c9c31940041d4585d2b0188fbd77250a13c26f3ec0325f245a7744733958eec2cecfb9d9afed1e2a58e4bec4840030e9f3e0c92aeef1f4938c955b46ad14704c2b6a2741cf0606c5d4d0a887db0d355efd681184c37c9f35fdf95ce70f3d4000000000000000000000000000000000000000000000000000000002b11a978fdae01d84f6fa0f47c77d269733927b97b495afe13bd0736173bc108d5a536457cd4393d740d02c208981e9e34805e1ae9799f7fcc970b994e3f2168ae4076c9ee0cadd49cd01e67e3eaf614708413e8e6747a7259553488f005792d3fbbe2cc9e7a4921a4e88739c0cf0c48b322c14daa8a62f7fe1d767ed98ef950dcbfc8e6d3b2912bacd52256e8ee0eb8feb9654e150cdcc63b37501738fa74b8afde3212f0454e274e0c70bfe05db3e5b66fb0a37898339cf842f4069c2b15310e03c7247f0114098a2abd6b3a7b95f74c0d66e5183ef9dcea6cbc76ab811e85a3927e9f1fba24a3edf1733c299ac3e3751d8bef340be63d2bc99a37de7ae4c93473825a8a0e9ccd34add14342fa49b2a4339d82adad9389cdf32914df4df313ef940392eca3dbb26851cc7f633d4c91c18255892d461f96bf3ad9dc20b87782d124b8e9010183a1d662ea87c6390558e30f327e75cb7c02f09cb8ad1b29603fa67fd176b0dbdd37d89898c15d94151d6001ca7467ef8651438fb8d5b69ce346a4a3a9ccc006c55d69fbd80a0956911a5d353858d5d20e161bd2467fc524a70a0121ffe69d6879c3433163b4b268bc144179eaf2c4483a2ac702ff27ef589383cb35c860617e20afba9d9fde90927fce0a9febcad50562c77535a516f0fc46312e7e44b78c04510449c8775834336be170ac6035634ce9bc3fa426caa1a1e21585d5377244d6c0f5b4bce9554359c231ea2d2a44c6371f0030ab2ddde40264ed65b630bb26ea0fa44e22f83347b12f34ddc757476a15809bca3264973795c1ca85c9efbb4ab971b46f283ccd3b31bbbba467d9293ff542a9c047036f63f7999ade74e15afd120060d814ba66d5dd324b5e9840d9c5aa82f2d92c50aaedde60ecfb197d89f803b43f951642ef440a4ce557c119c8b0b3b31396ec5eb2eab3b68bfcb8d87d514e2fa9d99f55bf73b6de4a2c0ae686ac120ecd351950f301d788e9d05a9be5316fb0347de8f8627aeb14222479d9c0935682cb19433ae087e6fa55586b71fec9de2fb3d7fbee0fca4ba677df4f5a058d881e4883956f7e2c8c9a7ff843153d495ce0508d9e86871a75ac58760c9f6ab2ac11d638798eccb3156d869060c00808e8d589a1ecbcf54c6ce2aa41d927a337b4bdb357bcce9262113256a4209f65cd612f679edcd92024eaae80075d703a22027f77627ce71d58210ce6", "spend_index": [ 0, 1, 2916844456, 4294967295 ], "result": [ "283cb2047c37309e829655648b28267b033c1087d81aead63e6ff2d26caf9e8c", "7010b42b49bdf5cca62e1f8f49362e68f9b88f18f762620cdd8456154b163944", "02459f32cf304406ee4b0de8526b878e6f8d2106be67ef4e34f8093b3d9f958e", "e813f4d71c4648851297b59fbd8703ce205c8c1bfea7665e221d94b32525c2f5" ] }, { "desc": { "Inputs": 8, "Outputs": 8, "Witness": false, "Version": 728859774, "scriptSigs": false }, "hex_tx": "7e84712b085a8b7c720000000000000000000000000000000000000000000000000000000007339cab0076f4ea875264aae700000000000000000000000000000000000000000000000000000000e03461fe006a66435164c792eb000000000000000000000000000000000000000000000000000000004d3a4d3400183a7cce719da3c700000000000000000000000000000000000000000000000000000000162a98f500813c238d4b9b642f000000000000000000000000000000000000000000000000000000000ada854600e9fb24603d09b8ac000000000000000000000000000000000000000000000000000000009e6175f00071d3837caed637bd000000000000000000000000000000000000000000000000000000007a0ffa3c00eb027ff74d8419250000000000000000000000000000000000000000000000000000000043fa453f005837068f0891a5843d7f2e8411c8bef21df66eac8337d06a1f249cc01b956e0603d06de734ae6a2f1e170de9ad5737895c85f747bb07768d1b0f99669a7dc73b91a4d168bae17dfeac3d2f009cbe51a15460f3b26d88138bafa6ee1644c6df181291e5ac1f3a6b11bde316a01bd69588022485667ca6cd2fc73f6d7aff9d08e63b0a77fa3c2e74670d6d2cf83670e0b7edaa56ea961c1e8d3b9088f480725029e5a85e0db3dc972895698621b988a3af0c76ef806ec8335ee019d158a73ea608899a0b435ac8f288288c3a7151383f76285c5b30981516f91cfdb08ebf4fc8a638d0073680ad2a824cae7e99034b4507d17837196949c1b145183ca9f56ec5450a4df6d077e4e1f3f057660d4ac9db405fefafe0fb966ee668ee6489d97a9643d2b973110adae292a3332767c762fa56001dbe1668a48e77136bfc287ace637c12a701bbe119dc30ec7aace3f84f9ecbdf7fb6881f5fdb21c1a24fd364dbc4428e8ddb353fbc80889baee1c631e79a03ccb4897ed3f8043333eb8afc8adc5cccf00e5cd6d46963cd5b0483b3d1f09415f656714f502945f5c4e83a67259f6083947cae09df3f4c7a74a4871e41dd4fc8b8700b74e4d6ad991c2d1ea6cd6eb7d4df570c73ee21e0c75023d041f4c2599aefb7b82eb364a5fe9de8de77c208a34541ce5a90d37245d57dc1886715a0b038e2e0da44233dbb7b193a8967b53d959da49e1b745e556492cad3563637539e2a19507dc88b73fcbd1d3096ad4076af5b1e93ea376a705e061ac6b5f76f9735d3372e21eb9f9365aa4f620f60b3559f34254ba22e6e363ceb086a59dfe328df23b6a407447e265130ae51f864c0798018c8a2f8a3b8aecd0e51480e69f4dd3179ecfb5152071652f14206b1aeac2b9105c857352501592012cdedfda53a1780257ac8a55d5f2d488e5eea6773c451c1c1799d33a2dd05f4d72fc69419145efe46f27e328952b936babdf3f80b1aa64dc34696664aa5d5bc5cb8894571d3376d937a874357564b4af3040defa9522cbb52053e460b8e1bad794705049e3c15e8f260d4d3577ba8d9e26fcf6624516a549c932b2231a4fa4d99d9274af0ce1ec85fceef43b11113cc20a02147a7c06116f133159bf277163ee2d987575a2e342103b4128520229574a41c75ccf4b0e492aa6355074727921c18be00cb4d8c1e3f503ac86f0d9dced8a28b17613ccaecd59ec3e7425cce0eafa1aa76d6adcda848043e03a9d02a00a17ebaaefbc4d1c9c3b5c34c51a25c4c3e640cb1204c8b30b95d2544913a04bc599f4addda2b652886778bdbbf267b5e5d222828b7fda07a577ee08f21df7c38a89f7c5591f6d49793bb0acdc8ee4006106912351b2c5d76e5fca68f5931cff15be0b2a507f5c936445a6c05b0dd78d5f16e35bafaab2c94ecf6a31e53d62bbdac9dc32c7c6bbc4a6f82b931f874a9741c3465dbe65c126acce73ea19e3e22e968b10650166bef64c7598a35c81029234477d439cdc1cc604a8b9be7a672ef766be533e596b7e596ea75ac33178ab366a8542dddcac4692756da61b552fc12886e915985b8a8ec8e09b1c6bf1af372791e9c920507cbe78476299142d5d85e153e7de3b1c681e57e755d8cdeae628303acde8550c4ec867b7c0c49dd4cab2d917c609914569d598260ab23c489e3eafae99e398b857e55c69e9d782e4668367b0200fe8020a62d3208031f9d70dfd0b2d9f317fc9fc0b1e1f645109e024beb4190b24ca8352e496e990dd665525d5e00b40085467ccb24f2ff00af6c6ec8f57ba2b20dad8c85c24e767b2cd82083607a3f3cd4ebbc8a9b92d0d2c0006c14c9c5ecf26b023330067c581295cb232b157263ae71599d4de8b90ca13a5ab850ccc63499f3f7b6b018965f9daacf5b96c4d735cebbb654b83496891c6969c54e69c9e72eaad85b83df205ecf2ea504ba71c042f1b8497fec95ab33ffb6e7a0fbd68ffaf2274e143f5bb3cfcffc0235259dcc869ba3f6432d7dd6108586063e0646b30e1304c68034a24c69e790e529925fc7aae4a5f575ccb65584d121e7eaf14a70039066d6415adcd31cf3774f8431c851a8e22b0b1ff4b196ead0f96063c78dbf54b5e44b9041c33bbab4d01ae6c2e3667d825abe24f1d4085d43f9a5561e2b605f8109979b760907ab9b894c0ccb6e2e26536d3a835a438c9902b7848347f7789b9ffa73a21ce7709bbea337c0776efbd9302d7d789a8005c4aa1906d17bf93a4ec1dd61caf6c8314504eed98a7e7793fdff2299f1ad78d5a29d26c64a5d815a59a798d6ae86249bfebcd63efd1ab92fc305023bc1babe53119d47ad340fec3d89d7aea2cb1ae92b1fec69b2ee06a6c8aa8d5d5e87e84f2dfc8686", "spend_index": [ 0, 1, 1256674190, 4294967295 ], "result": [ "1cbc2c12a17c62451d2cf36548bd5428bc856da30d5fe599b16743a3b289dfd8", "0a1fb9e324a3bb5cb702204e1a69660c8b8c1e13240f4d1c28a52c5adcfe3ba9", "8be86606c28d4cde311a518f44cd47582eae349332b906ed0235a14be33807c2", "7c1b06f3d2068192342c5b643fa15b9d7b7810934c665afe08c442fa66ac8b96" ] }, { "desc": { "Inputs": 5, "Outputs": 9, "Witness": false, "Version": -374849814, "scriptSigs": true }, "hex_tx": "ea3ea8e905240338c6000000000000000000000000000000000000000000000000000000002eabd87700f486a7e201ac6ca600000000000000000000000000000000000000000000000000000000913fb2e9fdb701bf3f99c49e04f63d21a8518a93a4ed96d016189b40cb85d3a5764d2a13a66a38caba68238877a2c7d804bca7979cd40b6fd7849bea3755721b10482855ce2f68436e85cf9a64e3846e69d685ee1e8601ab13e1ff8d72c42bcbaf4023c935c08969b2734e88529540433125e1ff66b31ced3b196cc54b0128170f51dcea554bf15d13de112c6853ce11c379180534afbd747128f6ec49f696f1b2cb6f2384b159f79019a3a9c30a92078110daef12c648fdc75a9efcd04f663e1f42ba2d5c61bbfcfc73b8d111264424346ca055d77ff1e0f6cec83889f5792e78ac7c02566d0d9702185d93394de0cbf7de83f007f65487e8e7f1229e88f75e493790ca05e0304cda49c000ae971d9b34f418a37d7442e84e47348d4c7a6ca83cdbbf429719c4d50c621ad64bda30107a588cc6d82050e9282783bc79cca10fe04505aadbb90f7d071ae3b515e02d94e4e6c19e51df33b2b5f2b940d6df47f0c68d6d595308fad2fad8354a51ceeb8a28606f59d4bb936c94f82ab0add1ae510adb4e4373a17b4f18c2bb77594809137a66107bdae0ca690cb969c4e1f520ce0154c57dee20139b1d12f5ce987be8f5566e17e24354008f55f96da4c43d7b1823f704364bc600000000000000000000000000000000000000000000000000000000243a49d777627f4fc5e826acdd8e81a6c5f1d7d5ca35cc83369f4f1f1f522484315964c12be52fd9b55adb1ba9b8d20546b29c4edb02a1e6cf24dd93e440aa3dc35964e8ed467f2776b3bd26b51125e3c917e84a89c61a0a722352a9acdc6242e712af1ba5a88a3a695c265abe130a9636595e94ae50e30ec8f5f148dff30a3971e6eeb200000000000000000000000000000000000000000000000000000000856c91830037bb2ddf0def03db00000000000000000000000000000000000000000000000000000000c1e25bb4657f10a47dcd64ac85b0037fd99a84d60773e3b9b144061b33f32d5d916c3aa83ca0d22d932d6b06c9eacbc2617370c3e20cf65dfe63451a3ed9f8a72ca6486ab9bb99825d8e1afe7c02098d36fc80e79bd5a9f4bb4561ca5a46478d51da59d81c5539f2b000bbeabf1b09e59f12d005f9071fc88526fc0e9363b11bddbafeaf51e5d948c453d0d14a3feea58f30ca135a3ba3eadfb991d4241c5863ff4ab8cf062a23be20ec8e718a45b3ede10f67c9e31d568782c5a55cb5a38abdf0ca6aa95549563e4774221576fc9949aeb296656b09cc1a00b25b8433702079f51666f796ea9df041377476d18057f16d293114703b604e9ad5fb88bf4443744dea5117601ad991f568d564a183d668c87d4997b5713587ba8473921f86e941e8f1cf3c53a7997c1d0f3a9944cb5dedfa8a563dea7cdae4b886c4daf24b8268ff6771399b747355c8856fce298f7a3078c80f26627780b203b1bb06504de5332d8fc66d9f85b671393eb52d7daedeebdee62c3f7537151d8a0844aaea1013ce7c96c3f39e2e98399efcd11b5408f84bdfc3bab3130fb5a97bbf8f4e720978a7e50e6dc587f6585f01d9e71c8581ae4fdc77d4e49e9f07f612fac5bda8c7d92dbf139e5c6746b3fbd69a5764eab6588e2bd00019e458c57cb9d788afc60d020c46d03574ea012d56587a7b4ea8f94b2059c25e169a14b0c9efb28bf12ba967bc4b36254d0667274264a62b61362f69826327c8cb745842c875c8b9b6f01084a3326f38f10dc155953b1e57ec2206bd468aa408fa0e3a0fa71ef99afef0cf4ef869594cc71eb912a459fe07086f9d138afcc6834444f2509c0803a5cfe88205e9ba266bd75a83b672542b7741cfa7373df23b765c5e16e2a10d6b197c6a0452c4af74191ccf46bafdd0c66e8162719aa9b1a4c56b8cf11678d10fbb0ba3971fbb9cb136c744dd819239957c0c1948634ca0da513de49584b5afb789d8418a1cd5dc92dfe397dedeb11bb92eb4226da232d4ff4cd185d5e429e0b0d351dd28171f959282298ff39726673ec8eb5604005253281915006ea974d8edfea8f128f8ab252ccea01ac3e1cf88740c5a878f764ced73ffa344744ec40f0fdf542821dc79842b1dc5774cc0ac7d901f6577522ab724d9118f636c590f4b4c72341982d46e1dc5ed3ace8e04c186e519a382134fdc98d1cc1b8496c233abe88976e3d748373626b9ead18ec9cdbcce680bce924253fc04eb32374e4f759dda34f4c39ceace35bd417dd3f5c4d07831853d53ad130030e67655ca30de7f46c5ab27e7370b8601cf804bed2b273e0565f086dbb65faac171a24bd34c7ac0ab8449c832c028d50a1639f5d815125ab6c7149c8498fbee4ab67dd7b3caa147700a58096f0520f595aa9f1b407d46f5091ac71a4dbe333eeeeabdedb9d607593332b01bec9e7482811568874145ff42c740956d6ae7e09c96d1de46e0b5542016a909fb46ea77e5c5bf17c1786a7ce9562e6c504106a3daa54d64b1e5513dd2db3087338ecdda2f886ad7cdbfdb795684548a69b4ba4ec83032e446bda170c44a66d8c27f875f4d18261622f82766191fcc6840d9143d8d4fd0ea2b183b2278b8d26638ac0e0b6707fa18db741b7dd779caa001c8177971a9fbde34a2d82dcfd9798f041e037d0b33fbe8642527878a33d97693ffefebbf8b383254bbe19eb91a11b8c05de60adf3a7708bf29d6e82a1310ea6fb9708cb20869cd5c05ef4865d45c919814f4276a0f17da82ae7ce6a63cbf4c37e417c9a77f273bf9b512c4272ade516d36c89b7632fa043981ee2d019dd9b9a2d28cf935235e6cc3a021af1d9cdd40a697d1bf281cf6781c3c1cb5459de2c2a7e8862f802d4080f5ef3820e3bcb75771a3a5746b761ea033a7709dc50d846060ed2b4b88bd345a5cce967fd2c8a7faec14c8ea4e68509fb61843a687745938308fc0ec9cf6e2ed24448a0cf1ed2d5f0266dceb5c48120be5184c04601dab0cbe8b73d790df8384a4f0863b09d2ccdb2cdcbec287739f5406ddabe7de9dee27a0f6ea8c57a5697c9becd9b511040e3dbcb1a8f614a7b750e15f58d25942f0b8a7ad2897f93d5670ba1ee3346ae226dba8df07efaaab4bf77fd995a4c8072c1f89fd37ca1e36a9c503ef73668a1a466b935149dcf79afa4512427f71a8be26c3b054bf11a28c0db7cad86f042447ed8d23038f3e2053aed5e7d90d34efc68b37ca1f6fc8a4f9645ceccb554b3a4c632caf6bb9d1a9b38ebb2054ed731017b4d9af7d8c979c1f2b0380108d2335408ed3e4bf0989888953d71f3b6130ca8a5a5772718abc157ea3e04ba25a8a2161238cb7c21191169c0aa141c9e1ae1fb00e26176460a98d1cc7ebad95a9bd653950a48881a4d297a320827e4400f8c30eaffb7fae3b2b57c021b8c5d5cf560ab3863dfc712ce41aa849b9a24da9d5bda298f4821312ab4e2addf2364cf5d171bfa478224b80a484727e36a5778348c5dc802a127e988ef1c03828f200d991b9fb7c9590f36420c8626d84d36c486f305d84dc1c337ffdd00352b253e1263bb2e4b868446ef6bed02eaae3542daa4af65b48950b57eeb2b17b92031f67a6f69b24d473a28f68dd1077d73b7a23de3c8570f051ec037c5950c03abc86ee5b958e198218ff086485f8444c928f8e5386d02caf99c7cae1ab51f586814eacb85a9024486d489ae76a1b8eee999169963da3945ad8f894477aefef35c8c788448028ab8796e0c0dda90389ecab4f29f56783228bc1e135cc218b31fef04aa8a95b28fb0681a4dd2ef99e7b872b2c9c2d078c88baba73", "spend_index": [ 0, 1, 3216091953, 4294967295 ], "result": [ "51d6788249aeefcbcefa586c698aecb744761d187790a75f86d0b22c09ff17a8", "a7ac21bac86b38f58f751e9823153b7187131e62012c5ccf09518ccfc3963d78", "69d12a2eb89f805fa70741c42ac301d5092124760cde28b0cebeeda59525a8cb", "a588484f0c7e6406bd8873a30f7f23a80e86bd46eec094053e1cec93414496e3" ] }, { "desc": { "Inputs": 6, "Outputs": 4, "Witness": false, "Version": -1556642398, "scriptSigs": false }, "hex_tx": "a28537a30675c9c29800000000000000000000000000000000000000000000000000000000bfd666c7004444d5dbd688d48f00000000000000000000000000000000000000000000000000000000903fd8e3004d2e132f18d5332e000000000000000000000000000000000000000000000000000000002849a5d2009261d646bfea33db00000000000000000000000000000000000000000000000000000000b0fde66c006f46905fc78dc059000000000000000000000000000000000000000000000000000000002b79037500b3154e35f19922b40000000000000000000000000000000000000000000000000000000082d485b5002e521d82045140d648ee39373ac8826ed82def4c4d580bc5b5d8b27360aa81b08b0b5b3a0b12fa33ff0d4e64e4b70da80c62878bd456bcb877a629cd1db0de8c23d543c6e9981aaaec764e86557c6a2bf9e2de20fbbc6e8f6cd5dd87e8d014969cfa7e3a66f83263fc74cf203335d164e35e16eb868835bb08d430071ce08e8d00986a8bd9c73ffa3b47d9424621df29370c12a63500706f1f8603c18aa4f3baff28bb395f64e1a2d094747fb5134d581b2ee2708136b3964464c9c8347c59b3a6feec739e395978bcda6fcffdf4b6acd48bdf2cc6c838a27ecf20dcbd3fc8a81a6f4c10f8d6a31b3eb0b8998ef66d76193d083ef1c166127b0470457fa0f483f1e8a4eecae4c7ffa2ca403bc3754ccfaf7c6b784feef3af94777fa9ded97d85fdff27c5ef4180f305a5d2cbf3d18832ac182a65b0d008619ef460cef8a322196d8fefea42add04b9177f9d7ed2042d6b196525bdd5eacbfcd8d527ce2a7c75f7670b605af6027c3366199153482ce3885e59bcac2285b907988914e7401ea486c42bb5b1836c61a36ccedf662e4bb3c8145ec702be5101bfa48fd7f2705d40a5b15f61f1e69a5fcffd51df8199824c8418ea0103eca39e3daf6818c4f20118f0c267238843c345676e6d066254243666b5418a651af82814b2f4981246c056f7f8b2d78b6b56759bf04524718ffc679bb7b8e24276ebaf0cf1062f5db3665bd100b5257f59081ef49e136f0d8b87fc9e6f076110f8e4fd9e99818bc806f1576a033574b4a40310342c889cf32d34385c802059a890463cbc02a015d622a2d4056814c2ff2c8889388366c0de79eb6295f19fec73485584b9d6571209df890f0de9a8bb71c895e0013f4fc8b290422b17ba62b24332ff6ab81f2b00379c9df37c80152c490efbfc668069d1db20a79f9d64bdbba39625a64b4faaff402f5abf0f5aec586e982a9e3101bd961007495ce197750faf3bb2867269f9fb96388053af3716268e387fb65f0aca88b22130e49ecdb01591b03ac91dd712878a97b15e250e32fddead53a2fd03e689f72521adf58ebd8a15ebfb6808dcf4c27b9a5a4f9a1e0a028f6033c5f3e47e11e123c8f1717abd0f18bce748b2d6ffd17bee05b092723ea5992a1bd03fa1953ec441c7809739bb744d74768ca8fa65db6c05ca4e3dec59d38b7a9dc285214dc941d", "spend_index": [ 0, 1, 1428324591, 4294967295 ], "result": [ "6128d94d21e16b1667b475e5d1cf8fbace201967b93316cbc29018ba9ad7e1f8", "991f8bc21b2fd0ecce39835699e395e2da54601d914bd614b944f4a9c0048948", "edb18e9a94967cd1ff1e7020b301eaedf57a935a5d85e2f4a367d806223060b4", "720069c30122090c70546a46f3f33306fd7e335b4ad6ddca909017c2971b1dc6" ] }, { "desc": { "Inputs": 10, "Outputs": 8, "Witness": false, "Version": -211459921, "scriptSigs": true }, "hex_tx": "af6065f30abc77d8470000000000000000000000000000000000000000000000000000000011e2d273fd66019b1f3f930e765b6da05fe932d2d17a868ce72055ba505d4dd4fccc39a70578d4247dd78d35a9d97b58f396ecdcdd0d7531e8f6699c808778f3ef5c4e1563c0ac1c1566a891faa79a5e806a3094b3f9b8a1ff4e3387c99224e858f46a612c9426e3cf5c8f16b77c8f90ec321419d007959119be97fcc13bfa1ffb59215096f9e2d15c565582302939923764105c0656a06208abc93d7964d5c569300f25ae8ec9252ac39ab27d34d3fb5b6a6e8a2e9ff95665de700f044dd753e265bc9a5763642af033cdf3755729fbbca777f20cbae9cc0e3716370e0c71752344202de90cfd1706b6ef852e3529e7324c978e511d856af731f0dd311011780051f99318108b3c6f1f649fa615c7003632b2f408c0ac56adefb815f0604d96fa9ccacca3430d2de8a747ea002b790acfa0f65327c89587fdbf195141df88d2ee11d303dfd8211a093c358d6edbd8da5614faa095e6ac029f43f51d931be8d97076394e06bc458a0a8250f00640767840d19ec7b4000000000000000000000000000000000000000000000000000000008cf7db67c57e0f1263a92afe95dbba6bbceec4ce7b9c45a7099d125ab36954f11c096d6ec647e97da54eb8f58250ca9efc6b6d051e4895b22272e46881de55fdf21f17ba4e1f6af7f82cf1ffc25461f9d79089bae859d9bc6452d9e2827395b006d1e067e31146ea27f1ae0abf63f03adf2cbd8cdc16e29b80a3126f55b3162c0941b7a7da15124a614721664be4179237c141d4a437afc0ea7c7829a9f180c45a7e43fd1eea7ccfc7df39a7f23962721b8bd9816553c8d2ff41e3af548fd52081515f1da07faf916c80d012e25e96b741be000000000000000000000000000000000000000000000000000000009749e369f3d3f49a059391f2b6064156a8fb478cb02d9b7455214a7ed3b2266564178c116910c0d63b1b6a2e24d25a3f649dc244210b763e2115e2190323e83858df0e87355a5e532a863eb56193d9177e82b04161aefc46a8c6eeefe14ddf8bbec7f5f80dfae3a4f8ff0e91997dae5807c9a1a8e94846bd8e88f268d66f9a7a9b9ea1656156a35aaad8648907a7908b75b7e07027fb761cd35b655b79e09eee0d9ce64ae803a59a7dd51c0e43ddb5e371f3ad30d62616d793b5b1729278f63b5be95cb683b4a96bd88a72ef80df86dafc96603339534f03071091cf8f6344391620dddf45e76a368e9060ee64f127c35c8d8735fe42afdf5862ebce0d9f559c0000000000000000000000000000000000000000000000000000000067c1080f4842480cd397165a7df7778b3423227e2e0f34dad207e5404415136d42828e3daa4bbe78b337d522c29964eec0adae1a0197235edf369c960dfe1da771b1be8879c363d870459be9ef9e29b806b6418be2000000000000000000000000000000000000000000000000000000007e83b03cfd7b01c958574b8b1b7d0eda831bed14027e7b9f8080bb1b82d10133d3afeb736586de324e883462a4e0aa7e7950e97d99800420c2104787970c008c1cd3b8f2ea20605bd22142410d483411f80b1b25c5a83fdc21400f7007bd28643778c517de70362aece62ca15455ef573ecbcecc9318f2d80fe03cb95a489c939337ec2f9006956defdf71aee1bb5beab82615511a6bac509918259bf5c771319718998895ca20481852bd2a2d47701bf2e332fe11669b1ad5667543a4d2bbd6ce4cbbfb15985d3fc410fcc40fa09d8a48a1f18c23b78c22690f12f83d64bb9d3c63b3f566fefa2baba9fe9829339ef461b08f0983ba22ebb1cfea2d3c374e1edae8bfe2c4572f9851010b4b377d1605572611e7d4f01a95def35c9281d62ff267725bc5a5ecba4e814ea1dfa2a9c91ca1bd28222e4edb479885bbae7f7545750da21377d38b18567e438c6b19cf7511913c4713ce0b3e3a0f260e5abad4ad52fa21f05e6257716f73dbec3bab403abe270f2a6fc0d3cc11aacc99abebbed5d16a5a959b9d7b9bf103f8000000000000000000000000000000000000000000000000000000005f047ed0a8b3515e051848eff79b5ac436b6fdc9ce49d79b355ea2605b5c2aa75d69a05cb8f9813e16073917e2337b4ddc81ba597d3e44c47857e1a5d86949c4618ac74a34b92c67e2958ddfcca76990ad5b06b6cc63d9c755842b60a964a702e2fee1fa942625034e14f720f4a5f32b4a5849c71ed0442d7ed76455bf2696706cf2af3b952eb09129316f0e3fdb6d8b2475c3c28d04c5fab15670d97e559a5a68755f73567df8ed51b0b134d2f8d4e8b225ccd42100000000000000000000000000000000000000000000000000000000db5e3ba8fd6f0184e40c4c15b56c4b03440298ebc916c1afddbcd7afd5eccd9dbec4d35d5702096964d1015737af3e1131237925642acb3900dd4e90e45e1554e11231d8714ded299219ef50e9f50e65d99df34cbd648dad1f067116e24eb8f657a49e9cdc3bffc1610355023f24faa112a367cf8d123abd803b79d2f011e406cf38f6b20ccb3107698ad326179bc6564355b0463ebdbb55a935611349c468a32fda87c8f457e2c3df0371cbed5303dfd659c0fc9a4d19ba1c54178a5f63d20ec9c5e01a0e4da9014aca148da4a5e1d399d3ac253424c4f453c573e947a265a4adf92a1d9b96d4f4c22b46544bb0052a5d20d83da6566f3a6bd5ede87bf00565596e3d02e413e830433879fd6988cbc5082851445857da186a451b44f80107d53dc82cc2eead17c478165ebe17d6d12f0318cdf5cebc0596db7d1c342e609cd6e47fca2871a3381d38fac6d27c32af85fc7f6a863a9d98366370ca56180bcbd3f4d8350816a061f4c3f0515d423e7fcfbd0c8c8310d88b2cbacc674aad1d000000000000000000000000000000000000000000000000000000000d1a6eb2000ee4f5a2cc5438f3000000000000000000000000000000000000000000000000000000009fdadccce95aa4d7458f28a041fd4e4a5dbc3cbdc97bc762346628a38daea7f4fd8fc060f7196d510ff0bfadb80f45c10cf33a9175c7382cb05f35f139a38de9a60c2b91ed96c84ba19c1c572ec472419f4ceaff8c6f64dcf0d2f60bc2fd985b9cdef4429284735913ad616fa3fc0ae94dc74e091155d6dcd4052b9c71c9f18fa71bb89050e1d7739cb581b3bbae181fdd5797e42744fcf7ab04893536f57e85cf860cc32c3468293c42fcf2f85c4e0b0b113b5b8e7ca10e6c55082c4ff1ebc37d62c9150f5fe4e173f83aaa5b837180a014e7e05b417a0e19a275114509d7609c612c52edd3629c56f967b1435d3f6f5dd22db269430000000000000000000000000000000000000000000000000000000067f0c87a000548fd6d08a01a56f0c6c32b66c84b3a5b3eb086bbba2a93c64297bb74fec48fe3e51af608cee555c224d9f4f131819f1503ee536720c851ccceed7fe2ccfbac32d6c07fac139366a8f325b434ae9eec25a023d987219e46c7eb13975cb8b0298543a41115b4b448adedad0c868b185664f0410ba6b2bdf27495b4f48fe970386c8a56cadf43897c6f9cb191f9aa26216af54caf15692ec1e6a621ba844b31c8094c8dd9ae6d2aea6bdd7759d0ed0f8d716240e68b18383483f6bac95407fc95912c2c631202689f490ec2ffbd4c8eb9847c34b10f5e218ea9ac7c121d49c807d704f1aaee47235cabfe3ce21dc6d62956c6b944337f5d05b28083a5688fe1a03d2316556488a7d7c22ef7af9a9a5e97947aa45a7cd09fdfc86630e374b51e19f795fa1d0d980d16dd41cc7cf853a024cd1594130a81e4e95edaba49e490cd2c05432f0b7fac41c1dc99296214295a02a0db4dd2b6ce13b32f864b56151304c680e67ac84867034ffbde739a280635bf018eddaf88581c09daf5744ac8ea0a6dfe300aa0c62a0daf596e2854a95af252656a0619777c2e7cb0fa407a2b4e097ca00cef7d454b49aafebc478285b407c8260126f7fc919323ae4b0e014fc14082f5b515fd8d35d40328a0edb6b385e6a6fb3cf900182d351a1ca531528b521ffb34d4384303a8ef5e03632796e8ba5479345b57b3bfe9f7ef03f3c64ea7521c819f91668ad039512e3651b51cd120dd666073f128db33a3a47e66a03f39eaebe93b0069705a4a2af10c907d7aeace015cf20b19988eef8df7f8b780ee61216b84e52234b9e1573f37d0607fa8e9c85e4b03a95b873c611bbcde2b607bbbffbbffa54308297a8033898b7b741dbec07b63bd71875e90cf933fe8a8d62dbccd8461c8d2e13ec493e6f3751c1110400d051c6e0d7fc4afc253512e9b5fab91b957032ec85372fa71eca10dc5c4e2ed7a0ed9b65310dc88648d559a8fed66136b69318e0bc9d5c9ae0b456b2891b76d5fddb89f27c414e3fcccd72fcdbf61dc341b7f29cd39126e001648e350d68b3a6034dc10c43c37f1ba16b77f3b5578b90b79322ee96a72de721e44c02a7cb6ff86f7888469c87d6a04a90b77b422a212b0efe0a17daa58dff7f4e76fef4688a9bf03deb37b8928214a38d7d410c65bece070bebc96ff93671d9777c355e3640187d0c40ec8c90140dcbe2e46778796a6394f8272faed81d304c54bbc9de9a9f7aad973eb067583057cdc18999bb2111de8c9f008d282c26e7e3fff2264f04c066e4138098e70230fdcf47b7c1fed3bd9e593bea4880960cb3d3e89ae00f5b4f2d90e4ae58830da9b6333f3274b314bce2f3143636359e72dec9d81a4c68c07d86f39f2881614137bb65c22341cff4f4fd91fee3c1523af2c716950c8f17657a12188b2587bb9b16fcd232ae6ff25781df9b5a88db9027ecdb7d05cccbce8fddf86a0fbb5acb0d37ca147d5e75648c9f66da2deeb4bc891ff6daedcf5f3cfeb59f07c0903c81c04dc2ef98e4a0131587590db695e8944ba52a189b440bc77f49caa62e4ef258ecf97dee745ef31f3cb905091db896f98c758adafebc5472753cfb9f3de41b07584fe704ae6851ed2890be4b6091175a247397b8f8229144d15da9db16f0c429c7d74cb31e9ebccb6e5ed783d93a70f5f8e5fe027ae1f4361b5f89ec3b5604756935bafa937479dfebcfd66cdd6fb91aed84a76a7781dc1316f2e39879ed975679336172a0372587a289004948de16776e5228236bc6bf737786ded7570dd6b5fc8e030038e0c40eaf9eb94be857c72cb5e2258bbf22ec9f8ac84562ced49783c0a47addd78179e018ee52ea04a4e91c396b9730fe9a9e595dc7ee04ce3e5eed6c85ad367ccf0e0752c7e1b27b810f9d3ab1d4850196ab41258eee0f2e06d39095ca315a0be538f537c2c2a3c61823667ccf22f742f47c9e3273dc0d7fbaa9ec9985a603c523ded78a4bb08538bd30a0c298b838708d6f2f8ce657daa1ed68f75d1f5582f26958cb59a56c0a8b2037f3e568c200020f26ff447e947cb5aa48548a6f64afa7832c860e4bd5b7020b51d6905c8920289d97d67ed1514232c785971ec84b744430bb29a067f75c8f51ebb50f2b704ddc20aa78d1129b50181aafe9e7792c970f4d89f64c91ab37bfd01db691dcd8e86d7cb60df5f628a48a00410a312e11d204d85a3ec4426926ec7a2cf130af3695188fe2ba5a420b85ec441c66db2e0778a2cef4130e3b8aa15edf7952e2d173ddb20291d1e256d1a11d127413ade1f2b46d0c358ff96f53fe87ab86ba777da22603938cae0b3d126e87c0fa3d3e524a3d496825b339cd49fe299edf7fa58c332361ee8f404822789663e60", "spend_index": [ 0, 1, 2180284422, 4294967295 ], "result": [ "83633cbc593700cc311dfb713af1ba7c4ff5d87bdd695e59d184b61a9d7b99b2", "76c01715ecee5d532795b67fbfabf83b1c853b74f59e0eb440b0320a1479943f", "152fb1fd8300a8c37f464be40f512db3227cbc20cf51dcf0a2ef919dba0661ee", "0abaf55540bf9b7dcd307594168e46f95ce3a2602327bf0c88b6322f13d40f2d" ] }, { "desc": { "Inputs": 1, "Outputs": 8, "Witness": false, "Version": 1828189183, "scriptSigs": false }, "hex_tx": "fff3f76c01395fd8f8000000000000000000000000000000000000000000000000000000001519c49000e4868e7708a5c1dd79df866c6dc814a969c33e937c2dc893dd125471ed68ef3fc99be691e0cceb9896dea9ec51881a15287fa69a6119911f05224d9cabf0aabf953100833e933f5e3d468d0878b6b181214fb58c6e4f7c16e129debe75ee67610444e322841fc8e55c408cabc75089da4e14db69bfeae855623664640347b1945e94fd89e6944bdd7f9ca3238bce1e035d710c6dade4b40ee54000354892f80c4b70cbcbf46dbc74c4c736e15ad3a32662750afaa5b75000da31affc41b3365f72fe6d8c3269bf6cad4f31571c8002de37a217c04a7a243f8358a3253b62c8a4d3382e103651b5320df9f3dd92119fde16ad13f9d1477efe02dcf8ab1aba443a0d18120a8b16b613678deda2dcb2c1fccec0c2b996002bc5b1abc8fd8128747bfb2b8102c16201fd13e5b3407ebadf66ee38ba3f0bffacd2bec490ccededfa969c7f7d633943de9b78722aa8cc06e89b5c29d8d91960584661594c32da7e7b44dc9f6bbd540117c38c10478f3999b61055ae1a02c2e16ddaf7fde74e105c489cd9e4a9b7d851f8e2570e8c460aa917e2f8169f3b752bf0985953d7f0f0aac38967b2a3b912c6a86cfc46e224b97a7bc8de043f87630bc6d21529716a8ad2d3df44535b1c14daed7988866043d598cb569f62646a4c40865d22f52f1046ae609786292f16bc239aae63d691519f50c66375887f609829659f0892f5734c32ef3017ab698755908dd4f43460c934b211fabbd4e1f52f6b13844c14a6a121ac29d8f08a44b0d97dc668103b1a2aa882336723b10f8f9a581a9a29827cbb62865f2227fa900263fd39795a84627146594bf8418644468a9116ff8a7fb54cbfb560cd0a1e9c9fcd52d62b1953fb68e93d9a0bdbac303e3b7a6466cba4afc95a915b62c8e1c7fda4f5f695ae89cd50b2e8aac8f0e2243ec468f64d5132fd717bdf72a4850c10894d4d2c1dd600d4a1dc8fed25556abf767532811bf1c14d6d07a5e6d670fab661ab57c4d63ba389afe43b30c82afad7822afbae6d733ad7c3bf7296c8058f177462c7c1aea72645fdad3ae66977a7dfa994e3d35a7452f69b299444e8bdbdc875804ca99b7bbf28a737968a96377e36ada76af430bbb6dff870d4aedbfb816fdc43ee2ff1fa8c7db35848a547654702238b79e7e465c4deb95fac095e20b464cbfeb8ceba429bdce88668e3a61dc827348fa419592bb5c90f9012221fd5b851f6265b95ae18b378bd9e74079b6a72fc53bcefd1e78202ed5ed47e80e9d292714b63004a30dbd3be47b3eaf0a5f1d697318b656916f7442b19e7230fb0f641a3e6392da8f9de871a1b040735d2216185b99d473a651935527e251c1af6dacdc0128900920c3f58dc99aef811a3b9ae186e3c8f81dba6ac699228ba33f5054cf51e39e33d7021fac120bf50a7ebdf607a438c411ce10a658f62d0a4c1a3a6e6a13d596a543a472e3b255312183dab6ffca11948f43074ecad40400ec69aec64c82a406c74e35fce2ad407552a2127be23ca25c90b547e175a0e0f8f5260082e4581b22c1cd9ebbe985fdb3214e300c84bcab86b77858a456d7d1a794689768f0f9c6043ce0589ba2fb3f28850a16e50f52da7f40cc09dc2881e7bc3400c9bbb0fa59debb3bc8f85eabf43f4be8eb19707af9301b2106ede7ddc1441c0c5189ce0fb1d05a313fdb6fd11e17f288ba2be293e73fe459f631dae97d81f61eb9defeb7edd2e744736b0898accfcc7953ddeb3ac2b6edb7efd059e9c2ac5059ff62da45cb550213e3ad7fe65948e46e314420ec8cdd4f9cc1eb66a4f16c282367d31c47cc8e5fa853d46d236dbec364042f273c4a4754a480e6792475f7eecc6acb94d77c11b37fa96af178d8c09edfb044488492f376072eaa8bf137df8d206a204067d0624f538408fb5b8de11978d09c732ab9991cb67306976934b197337eb241d286997fd8379138270472008299d336056bcaf3e93c0591973db850d1711962771838a4f0d692776bdadd9a7b21537d930fea9bcca7c40407f6230668130b612fc823e29dc4264ba98db789dfb76a416b9261aae0f881e5e31979583a03e76657bc8c510ca6b166abf9c73d12cece1fb098c22e9e2db0b8bc39202121dae0fef7bbb43295bc5d2d4288d3f2ae029a09277743434f10ce0215a7a078b3609769cb125c402b78407b8def9c52c5c9f1c3d0037ec0c320c8435db314b5019a4233ef628441f39d36096b9709a969d2283b51d593d8fb53fb4906e4357b6531e10f087a107b2b89fcdf7ee6a3ceff5bacdd96b87770a449d77e70ff01711a6028155ca51b04ed5b9c78e0d9d5edac9fa742a23182b75a7c82f38ce36e7f61ec8adb3c9fdd071fe6a44dc3b50478f3658", "spend_index": [ 0, 1, 2241195222, 4294967295 ], "result": [ "fbd57d70f59cc8564c04cbe05b90fca6510655e46d14cd7e380c1fd337c258d2", "7a4eb4ca724c0a4c0213100d9b7c6f930422e4218d35a940165e4cfb3f130658", "4a9dd17fd4f6f68a122394ae66c695637d7fdb0f49f59edb917806923a25b18e", "97f3848d984da92ad3baeed4f2ab8757e4a1d645dcd3f437a1a80cffa2d32efe" ] }, { "desc": { "Inputs": 2, "Outputs": 4, "Witness": false, "Version": 2138978941, "scriptSigs": true }, "hex_tx": "7d3a7e7f0275a01a4e000000000000000000000000000000000000000000000000000000003416da7800a2727c85eeaa277a000000000000000000000000000000000000000000000000000000008a062e10fda4016027218088115c0a566dfd58ef389ae369e7c46ca01fe4478621ad39094e8e827f759536a9688e2810f1f50b23b0ca743fc677c714be50a31362aa94ebf7573ce52a2a486ce518b257bf400444b1cfc1c1d8621ed3de8981607a6048d45ddc8a5fa5633513b71223b99564bc8e22b52a42bdb4152028b2519d82076b168d305cd4f7a10ca47424a397df0a1ad60e55083650578e94f7c76311fc7f4d1527ab119acf44220cbda555aa2859d69ed0fb7c329992ecd4073e0d36c8920310ac693d1cf43f5c5c19234527e6f3da2f0d6e0c953c090ad2e5210cd90bedecec478d7eae037f5454844ad144e3124c4f148bbd62183b67899e11f981464faa2777f7d0a15addc90d8b9f6bef444f0eaa64a6f0593e4646dc79a3c8edf2a1720eb1d0891d0247a3cceddffb4b4523c7c2b6f8dbe5fd9eb258ca0904ec0a35e13f5ac642efb1b3820ea77b2666bc25ffb3167c56b8b7cb96e5ac415aaabc6d581c54185778662bb2386187e41503ca7e410008b09388bf24c47acb10978ad2b3ed941d1a89bf44f5913617c9b3c50edee7fd5d42beecd02790b058554ecc1c1377be1614d0c0bd7d0a3ee217042e6eed7b479cf45dc8caeb0c8d73c63b343fe76f81a9929752d86dd73335f4304466e436508eede269640785aeb08bd513427767918520da622dc83b3fc74ea99f3d61cd073af15c5a6710760800f11b6361f2a25d1b4ab0125736b9a07051bd961663888dd5cfe3a65a79df650c41b8215c2c4c3387c14501a82116ab6e9f7124380c132dfcac494ccfc8cf987f1d7d8751dee86b7af18ba2493c45a12c11ec2737eca80e96123c9a678b73660b706da76a8dd3b3951888425090dddd1849decadac72dd03dc3b4155256d6379f8146a5d1bb1ab9f20d4216c8aa99314a0833dfce4b04ca8fd74855fddfffa01d3b61ea1c01eb63e4ac9bdea80807cc0473d58fbd5ffbff4bf6705766abc6c2b592a4291f84bee8b6659ca92d6652eb8dc625d67198031277a02ad2375d259a1b89c552b9ea8d1dcfe813154a7fffcd7678e4de2b6d4b5302ce3baf756a8692850bb000c987578cec72f7ab8ddb4c9ebaf9ae3dc7c97e84f38e901cf2da028bcca10239bfe568b2c625c3fa4f1b9e3d40bee5a1aabadf9bfc0ff8583eac4a95a81555b1569633744d6c0b09dbd87b9e914293e32a5a6abb57fd24b659c8b9ed62259d489f9115c45fd77e9882ec861c206506b61b7767b2d96baec3b5b68e74d5db478d06d94a5dba60f927f0c4732061f40cb1f8fb15101907687ec0ebf92c1e939f9a57983d036940c1849cbc6db36b3c979cc55cfcae1a7cfc061fba2d86b8606de74298fdbf4fab9d5e521d393ef953803df37ef3f556704055a56dbac8196c83e146a88b9916dcc089656c8fff94f79f30428d008a7a51f6507aced962fe3d3b19fa15b6c8f742e53cd1b4245b6895fad892837077ab9182fba16250fe9602ff83bf1a72f84ea38751b217c8d7f0f45ff0d4561deb9d8468f8a0f08d3547e61e90b7ea92e8f7eeb6456990bc594d013e5096cfe29252f0efef8db29f32f763a30e93cc07f7916cf142d1b1b4c30885f5df6edb2918729b307cc0081bd06f8882fc69fbbde3927fe6e1712fe7f9dc3d3ce845c2232075cea309c7d50d758086bab845ea1d6cd6b985ed7ce426de20275c72e49e64d760da34f38a9858a3896fff020ef7144b3aa2e4e924505a86cda8c9b69a9e43cae6c33e8b21d2a275679f3de01eee64435e060317ea05821daa31d335fa8729305110b2", "spend_index": [ 0, 1, 1305917170, 4294967295 ], "result": [ "fc195d4db6372da39b2c2b11a1b9c848b9940ea4d1c656832ffcc6b8dc1f4103", "3776d9678ef3b5ded3bbd787a089e370f7cc2cea3b5e1d4c2ce522d954142a61", "7bc475e72431de33427d3bfd6dfdeb6a23113cc7357003f6f0140bec3ba76142", "5e7572ecca53b57b4ba9bc5891d9d3ebf6d80b7b37c60c3f834953bd5e2d326e" ] }, { "desc": { "Inputs": 6, "Outputs": 6, "Witness": false, "Version": -294915705, "scriptSigs": false }, "hex_tx": "87f16bee063b22436400000000000000000000000000000000000000000000000000000000d4a5120400b186c1459b435bb000000000000000000000000000000000000000000000000000000000f766765c00d2f1a611e2a8f5b60000000000000000000000000000000000000000000000000000000039f3b98600d9b00db56c4553c700000000000000000000000000000000000000000000000000000000cebf0e8c00e022321210fada07000000000000000000000000000000000000000000000000000000005d6594bb0040e8dfbdbcdb2f86000000000000000000000000000000000000000000000000000000000af613a3003f6db8ee060be5a9a7e0ee5d57c87486d17ae1ef277ae1ecfb56007e6613f7a589dec0784d04bd12b55b0e807ee2ba79724856c847d1aa26fabddde471a1e31abc2fbf0590353d9e7561e2da2eeaa68514f6e3a289c5aee9806c61680184a1589f75bd2cb596077ab1aa6b03110ae8fa8b8a5fe0fe68caf2c74305c23271b7c221421ba1a8b62a5a3d0865af4b32c2c26956583bb826f65aac3968eb2d4044cff0e32db16506201f0db4a73fd5663c0d8ae9bd8760a64e36427e8b06f3b89278d7f980a982d5291df5ed05e59e6da75f0a51c3caf8834d49327aec670e0ac8bfb3df257f260519cfb4fdadc108cc3db9319420d2685bfabe605a0ccea020d2865d9af14f4e3da06a45023450ead96ba0bf665a5935dd02d6dc5ae778136fd996fcdbd5ec8423b931c4a00f9333863338dd7a4c7d4f432a81f2cb4aef11a2dcfd4f38d1a2fd5c5699a0e2911a378ed992335647c62c1742f781baa9d62f75f1d34061438a6b537038a2eb96ac1994ef21e6ca294558cfed77b43e84d0737b962b6265bdd5264e34e388863087141ee73c37bbdad44a306d6d01202c33684c9846c0ab8672c2ae0dc215fccd47088561c8f5a297ee801a2932ad8f87439ae6dfcc4fb1ec02a895fc38757f2ae2437030cd8d3cf44654ab53a8aae980ba8a2c7f816b4e0ab7b07b9d9d6f1a1cc61c7474e491d4a39e50931456dc194c48cadcd4baa145e2f115497098c40846fe099d852fb62dfff3ae491d6edded0974968418054abcc9205fe70a858a7a0e98f55fecca60aeeae68b9f725ecf643c7362873a56bdcac43cb4fc0785f84719d47bf12ce2bb5576632def2c881f10dba013cad3a3559eed014eecbe9a312bd7d7dcf6e7312de36a3ad310a72a24f12c5ae9e2ea43c8f4a5f7ada4dddebf352c3ce865cab0478783b45be54b36fee788b84e9d13cf229a2ddafdef61b8538636ff0f1e4b9fa2a236ff74608be595941aced141ad1700b30ec1ee709d8692d224ebc67d3fef441ef4e9a8419598086ee01c632f503a068a0ebaff69a50b6bbfc32b72f954cd02348e5f6e67f3cbc7017963238f82292bef830cbc763c1bfc6c8acc3ba5871759c6b2010922bb50cf793f54d0c3c5b59637381fcc03902b29c227881147b9c3f6357c863580058bd483b8a74e1c1c4f53f6ce8e614290cf499d4b74bf68d48c6cc8eec4b2d714a9e9e828207b70fe9830b25a4c40c91715b683ffbb0fdf3c5856cfaec220cbf400ecd80551c69c9b001481b27f54bb2fcd75355bc2046830507c625419eb677dd06cd06b591ed7a388b12b9af78e3f78897aca4b6e7a646a650ffc4a4bb866d758d3fa9da20520e8aa15ea370ad0ceb9e973097467aa22b3d94dddad3d516d873460906f8953e58011b5a08dc5f26bd428d11eab34a871d9249946d58446826f2ffb9fbb93fb020983073c785ea260aa15df12d07fe549d3a7ba96088767eb4c276617b768d86b323d4957c842777560b4533a548f3561643f2b1b7dc1e23ecfdc4152af084d57977571dbdaf3c777b559f65e9e60e794c57314bdf8c8d9a1f75055c40c52ae0fc5d6b9f4355e968d0186b3f9570b69a686f0b7b80c14e7dd188cc59325a9cc35026022c8b9918fa2fff5fd09eae04e4b4a5945e032ccdb72c5fa3e60edc932973dd21fbf48f333f881829d1c1e2752b7f61d4fb063e9735609819e7f373704c629d1fc2ab5fa0323211c6ca6db1fdd2f4fc82084ccc3ba373625b760ede4d89189844aa1639ee46f1e4b97e1f7a4ad73b7", "spend_index": [ 0, 1, 1110732603, 4294967295 ], "result": [ "a76937970d2a6cbb89815985e1c250fe926653d190acf2c89948710cdb0c665a", "67c0a507a7ab1bdedcd53ed21fea39e218fc0c20881e25df91224c0c86cf5a51", "28825f9efc56ee11571b204d728ce9c584bea95267e832a673dd2bcfe8323d49", "065c5a476e658952244105c9a461c8bebadfdc82bfaa8f2149488efd88176e6e" ] }, { "desc": { "Inputs": 9, "Outputs": 5, "Witness": false, "Version": 272222305, "scriptSigs": true }, "hex_tx": "61c8391009518e09c300000000000000000000000000000000000000000000000000000000453a077a00f5322949e2eda1b3000000000000000000000000000000000000000000000000000000003c8bf33dfac0cf7f4a6b5c1d40b03812966620314f8a6225837a06feb6216fa82036c0ba8d70489215b4616e8aa341aaf83c3662a3a958b76c3f9ae7819a5a22b8fe0d9bd2d2c330c1a7f7fe4b860db1a60a6ac8d4cbf177a87532ef0263570c377183344bdcae19ada6594e012c5731651560342ded3b48b96acdb0c6be50f58169bed868c13c27229dc7a0945fcd7ae1ee00c4d1ab417cba72fbc589b8eb4bc22c020a424488da43cc41eac899d62e01cea5cb30da6c0ae2ba47ad77a60c4bfeba8b5370a0bdccde64835d7918f0d70747d5d2a06309b128e92fb81f4a21af39514a8e37cd11072542d8b3bcb0d20390aefa426d6f3c0b8eb70e012c14e3196442d03c24a58300000000000000000000000000000000000000000000000000000000381b152ffd340117dc059b024bcbeeaab8fdc630ab9c87882eee6f7fc1c8fb78fc2c723119fe5eb3fb7a042add14a3e7014471cd103b9b64b7daf954db237c874f728a74093b08f3dcbc0771238f610bd5a2c1e10561abbb310b0d84d69bc53e95d18e834192a1a855745fcd97ac55ae35c1547d67624fd82ce69d6c8dfe3be57937d97dab84a69509634e32806618585ed7c722350757ce2ba0d8c8d4e20b5de264aacdf368ce4bf0dba4b018c5cd824e44b920978cf36de74aededa0c969175523f7a15257b83a7bf1b51cfe8e5b15a13ea6e8d0de34556e6c3b3f086f589082bf86800f7d2be765d47a6f6ad36b02d04b8b2d2b7ce73e979a2434e3f9855f1d9806b42cd58cc6ab4836ae630885d8a9b69b6dd652b61fe39af0cef3deb8b834376c5350aa2c4014d397f1b21dcf0c3ac025d2e566de0564be350b1c7b62f53b8c1900000000000000000000000000000000000000000000000000000000108c7fe70039110cd93375fc270000000000000000000000000000000000000000000000000000000096c1158fe70940a6a817da0da129ec2b31f8597f593a774f10e9793178dd889a1eb6ea459cc5ba66452c6c360d1b1957be78d17aa782f85b55488b10a4e26cbd0b973589f5fd713f18f2ace2e53b9d5540db88794998a6bc8b0060b85569e0582181fb04fbcd3ebdd5518e4a82101d1158577b57c176131fcab97c5b30941a9f042515cfcb12397c4a12962d655c51757bd3ee7da31cb50716f7e1c2bdbc4e88866149f118085ebb0bf79dc8653464a5c944d994e937f5f06b3888838d67d255b5f77efc1ff73956477d9fd16a2d37736d1b0aacf3c3f4881093fb41d5417b8e2a1f70e64cadde534077e273a5dc435bf61da07800000000000000000000000000000000000000000000000000000000de3a04c3fd1c01d0095f5b3571d99a651bc79ccfc06463aad8e701d70bab6a4ea89cfd3b0a72e02c9e4902c866a9cf6683074d7ef1be4ca9e8838375c3d1776695d02b73acad2f20b4579a4547d0e05f52931411b8b5ac6a00f63d4c9454d12209dc80b25252ec0e2b50034a1822b4b5581166236aca296afbd76ea4644bd17b0a80fb7d101de07067878ede3d179e8039af76cbd89a39274da70b4f02acd1d5762ed99f1f075d7ba53891fe2b81d8e256797f7ec6da5ed472fc02512c5e00987dc3a8241d50b648d0e8ece70fc70f4c04ea6fa039fc7988645ed9072c253a9025207a593a59f462a2e42f2ddee41620d11dc31310e0224c005c19b444ecc78fbe8e256f489352f0e81dd7af6a52cba9560157cf8339e7781829efcceb6f9bb06506aec38fcf18b4cc5ab2000000000000000000000000000000000000000000000000000000002d11889b5761d5011ffef2b4bf421afe3820812f8bb46b0a4caa46255025edc12dbb403834369e4a6a563130a636917fc9255a8f66aeac3ad5a1cb699126dfd8c2e54f0b3dd0ecc43ba66be98e23804f1f46c9874ca7624eb0293ab1c0e20b296c3fd8d10000000000000000000000000000000000000000000000000000000032187b311012248dbd1e7325bd0f5f9ac534e217374b070cd132c88a86000000000000000000000000000000000000000000000000000000006ccfb6db00aac41921057c645006896fa637c88be739c1364acfc641c44095a047f212d9edd51ff417f0cb95e6e5b4bf175cf5bf7f471d8049f19b7472ff0e2fb9ee0212cd22b68b5cd845e5a657604ce44a54f1c9257f55365874ab996feee51d5eb1cbf64e49fcc7a59a2c6ba06f96070090f318c7fc1f8739cad50a557adc405e66136a1fa086fd01a84b11bf783310f791f51288ffb063b14dbfa9a491aa8ab72c36e61e552f468d831aff3a639dac505b07eb9e37ed8e783c7f53f4380b61d3c5d3f931537bd29da2ca65498d719a149b89dbeb6748a42908c15b1535b8d53338c8b098268b7d87cd72b348cbb2e5962575a2443d0c9f3af9aca6b1922c4e89d8629a31676b8e9eb56a1af1f80ab64096c327d8f3b1be930e03fde7b887bebecd8c1ba7b43058502edc1dc41d298338decc8919c254435a8ed69dd1d4dd0aaf042e63fff946d38ed0a5a01e1bdd135e2a9c83d9b1269a10ca5cb4c65f8df4c686e681d27eee6056640ab273e8b5501980287a20e6a68588bfc5362044d2dce957e6b0c77bf7b063fad2678ea20bd10d8191fb81f02d844f696a60e203478b07d7ca753d66b2f81f40b3afd6740a46280725c8ac171dc361857d6e53b3348a4c122d72206f8c045ab87f937ab78654e9f448a39013c808ac58e1fb6b3be406bc53b40d30d7ff0d79a544ee5be60b67213394cc8bb9d086792e03da60208f0647e11706423142306a65a7f2d7f0cf08a402cba8d6ba34caf114ab20cdcf22350424d849a9514ac6ddb96a737be9c01acc919409ad32c74bf2b97d23c68e70917a63d8fa28b87e38f66570281ba2cad85c95477a700a6f6e070ebf0c2b90efd14ac153ecb8d885699a53a98bfa5babf3ce2fffbb744b476590c291643fcd5d8d0a8f2f40c8fdf3bea971cefe5229c5fa5eb00535b57965ef4c0f4a300e8a2f4dbd1d5b128dfd6df48e480f250f68a80b4473cb65dd8001d014f3856592562673ac8877b3d470032122404df93a6d562460cfb33f1919949cb4802987cdb4f1843302b1045602f0b1321082671c854f5b7caf3381f6707dd34809080f01cf999eb62f01efd0157101f62a9a6879d25dd557a3dfbfa7b11af27fc61a4cfb164c3f554db0c421910f9dc06054675ce7615f0b99f5da60fe82d391279854d3566b220f303f49541eeea5b67c997f72f1bb67a42d4e6334c8de11cb2f791a817e05fdb08d812743a7402bce9197e29ebfd9e999de913ca8769bc0e674612c0d567def8c1402f35fab9c6c81edcc03a8f7d975e0e7ab2627e83313e9ce4f9b12d56bafc2b8ce1397d0ad4643e7eec4db82673643e64c5cb833c19c13c0b74c96a4544e1d1cf33fe97f4a374980f4ff2116d582a784c8ebe01e31a31e1192eb78d6140670f9e4480588682e09edcc2ed7f2705305e058bc5d70694b94d3c3a6628abf900cb9a5c7964859535c49cad5fd5d875f8816340b392ae24577128ab5d1c9de7a8425", "spend_index": [ 0, 1, 2869676934, 4294967295 ], "result": [ "ee6b346a4e975ff06aa71b2d00045a53a5e11c31f6e7b3f82f21484bb5cf8566", "b9057ab45662d92efae0349b7f66fd857fbdeb10cc4ddc98b2f2e51a461fb30c", "94528b90a2039bc506108d367bbf257a5c06e72fc58fbff1cea4a5ef33e4698b", "7240f3929afc6c1a7094bcaee7f4d084539b6d454edc2368730a7708d4a7e6db" ] }, { "desc": { "Inputs": 2, "Outputs": 6, "Witness": false, "Version": -1826872246, "scriptSigs": false }, "hex_tx": "4a241c9302d12365ec00000000000000000000000000000000000000000000000000000000108ebb5200e960a377c5c83a81000000000000000000000000000000000000000000000000000000005a87644600bdf1d4cc060f618f5e1d2e4c43c8fcb5ec9822975995457d6f02f0e9b6922319ce2d3bca0325ce352e7726c00509268931c90b66d7c6daf1d8f664a7087ed8a8597a42df0984e9780618666ad36a9aa691c87c85a5714f3e0364d41eead90b63c1ee77626b3a84a4a7e66e02f68ed431f1a954549064889fb35ca43bd5afb682c4492dfc44c86ef03e4a5aa3eb22e346030de38487ac0095317f36db93c2293157e8d56968ba9761adbac0d411110c30674c4b14ef284cba11187691a72a1ef66c8cb1b58133e458dbe3517be8260cadb1f9b2c4104b6b42626a1322db0cc82b61385816f84cc544277fc53a7cbdbb09d7f65ff6d77159203bcedb0adef81e10c3354091fd7020ebe20bf853bddaf795596ab0c02e70af157d1559013681a7f54d0294877fbcfabe137138be3ef74dd35bdf7af6572d41b4b4b5027a60132b438cb37cb63aa7d2f1ecb6617ebea1cc7b9e7bfa500c647f04d8307a88c4e0537d68e5c6a0fe9980e3d60ba1b84e25043580e9f991d25236edf7cdbe9d57741f3ac9ea35f3583e33e51cd8f479cdc53903491fd3eb390c7decd2e42c11c566e632ffc3180bc7f441243d27c9d083a842c85ff88ae29119d379d894c0480eb9cc793fcc200f9ccb6ab3771be7cf2a54004c46b22be8095cd6b9f4476762581aff09c128298006ebf3ff3cb6a281554dfdb52f8e6ef4b0a1bda1c77b2ccd185e8ca098ffc40cbbbbc41b3a2e5fd3d07d9b3567a008d5c8046ea4213801f1c8f57e1c23ddd04d490f9f38493d1ad2727039676e22359d55633ed1719e5dbbf3fd51b47011b48fef1693f2c10094bf52f87f705c1442f2537daf0ce67a3b1246c5126214ee0bd216e218ae22f94c0fc61b7a21675bc8fa8a38743e483d0faa8261d629c847448d7cd53ebf30c474a83bf7ada56f9b55d6c2d511a7e0c16457bb66ea518379ac91bda11c765ea0e355539d43baec4092855fd8a0f484f50a64087dea748a75a696670b776cb2481f65e2e392b0a35527199f68bea64e78c04306a0451b32a5e59c2a4082050af27e99f447836051265bdc57370f9ec7852f213accfdfefddaab52e8965c94e1fa95658d7a029edb97196c94ef594adbc8b6b1431533aa4b8aa7753d1e5a8088ab64a53c6dada3835279811eb0fa4913b31ed418c8bb5be24e8b315546f8b82c90990f360a4eb000c8b45a5d72bd1d91381c018e12e5101b5fd7f1a13fbb45b003d474406edc7ce34b9a2d593bf7caacc4b52d438ee3d8f00a418accdc2c7344e51688894201410385a7a3948fe15f9ea44423e7c3042928cd367a690afab83af5cd2b890c0d69a2b6118da7af34199b4cc06bd4905715748779b4d7be96467479368b4aff7121308b960388193533612c021c65ea62f2ca0d74ee11cb2680ba25a21eef49adfacaf098ec17a4d5be2c2b451743c5a140b22e28fe96a22903dfcc6a63f1f37be56f8f8880a60aac3ed947a9f4541a830e9023c8769655597205a607c4166c283585036e614ca444cb9878d15a1ae3894da69ebf609d7b2094becac5441150fdf6eddcd24ea6cf4d00002ce72daaa305b8649f55dfa370148976582c3a589a5fe9d7fdb23580172720a23d316cb81a83d83d5b440720a3b6981f774dba3c11dfbdccb31d160f72cd8839b3a67a08bbf4ac144a9c6fb1a7f01a6d4177e50788a0b9a5395882e741ed0c65f717f566b02f9e4c3997f46b0a52c3cbc9809aeec5d55ebac828a21142901f5d9ea10040fb9aab0083fa88a7456c9ea748c698f21d92", "spend_index": [ 0, 1, 575568086, 4294967295 ], "result": [ "5dd5906f251a5a753ba3ef3749f2c31171f4441a800ef9997179d439a81d5410", "2769f08ead076d90d001028dcad018c11d21d71b70a618cba5dd00787c008507", "4611f46892da7ef37639e6242550dc7722072b3a20eb1f63ce190d92e92978c5", "6bd1b98061e20e755f3f82400a850792f9636c4f67984d5657b58bdabcaaf606" ] }, { "desc": { "Inputs": 1, "Outputs": 7, "Witness": false, "Version": 1596452751, "scriptSigs": true }, "hex_tx": "8fef275f01fe49fdbb000000000000000000000000000000000000000000000000000000003fb453858a65a0959c27b6da7959f75e51d9a20de73c5d5313df615a82bbdd393e1d4be462e6d3f4ac48be4ef5dea637e06fa95aecf8a570547b6fba0ac4756647233c688ff095fd038dbe503e59210b38605f8405b51a469c2afd2766ca8e8437f9eccec71b586eabf524dd35d0acab8378d09d55044730e9572b803429f304f1d21f3a45938c2fdd2806f01f5708219546fa07dc9bc0903817ed4ac886ed3fff82070238dd889d3f39b7855ea48ac42844ca8cf7aaf21fdc2462255a5f3eaa9991c7676f9a606403cca61af4da1f47bdc29ef4b07d664a74bc76a5136f351418a64db6b83340d7fa2c1e9f62b92917295bfb1e5932e7a07e397e374424f62b546ec1a0d2c319aede4e7073c02a8e5fa72feb556bada1d8f3fc6b3a391ce7ad957c92eed821576e428ea72c9d18a3f6bf1e0983910ddb1525e0a9cd3690c78919849487e94c9c203136da237f548a2824fbcf3872f9a885dcf5dcbaa4f979e8054bf9c8440ecc67f709f11801c8b77f53d2bec233401aea58edc418bb52fbeeeb73de750afd6d6991d98ed5526a27ce76e6024173af3b55e9e67c0b7c7328c8a9098af189a472b09894c4a9f43792ff5c6ed92e98152eb79b9d86ba613c7e187201868998e95d92b6bd9f335f68dfc6c84fe654507be9e20e01b262b4c3099c33130e59192181a5dfe82b8d76ac53d0870905e807056c77d753cb0dfc2887973345a676bf0c245e2ccbce2d21f665d461424ee04e7fa3cc97b7bbfb65aa5a03b843cfb14ea058c7abe066ffb9262efbf3460029a59fae824a0421af6642c8276a9ed14c0622944877f3c22b0d7197cad24487fc9fa3c81cb9868224c4141226714bac6b21298fdecdb58d759e7e4af629de124514536827ef1bd153e552e6176da597705e6e9234194e8a28f87be47ec9b4ce9bc07566a7186009a8d0d7d8c2cd475ebbf10814f6e51d2a6a4d1766d977b644275fbd2302505e5ba0bc1228a39c778671c0d4c5bacb822bf1074bfb680182691149dff7187689f92d84f494192302a279cfc369d8e15551558f71ae1afe737a8285bb629c9d91917406bbab845c2869537a9c3c0a550d1ddea96366c817d6130c5e450fbc0352063e9720f80ae4fdf2f1ceedae79d16b3458b75a72bd69ef08d0a110e510d54ae0e52ae44f1ddd510a74ad04f901883615d3bdafbc76d917a10fcdd96bd205fa6b18175ead4db6149b436957f388991defe8a8bd0aa6813d684babd9c6868c180fdc20ba6c7c12d17ae590380a355c7b7e5b8c0bf385c45281ea80e5306c41443eaeeda6bae67432cb606ae1da4aacde09daf6db8f5c034aa9e3fe17b770bf439eb743e7ff68864114e0ca33ab6de41b67119b5ea9c26feeab700eb190d9e94bbbc09eaeb060c89549b3618158a9440d8f51e94f09d0fd542f713b12b2aff73373c48f4348a12944cc486f151d678da06b732ee4da6adae212640075fa692e295b95a042cc4a7643913c08b3872489f0a07b3a008ff943e599501f60d6a60843eef1a7323ca96610bcc77f03f4a36ac0d3e625c515c8803e603362fd76e6d6aead7816636a9dbb15d3684f995a0f9be4b070811f9d7edd8c31f11567e7c9adf35d918a005eb6baf9081590497c1f6f9e882271d1e374d21df74a07c0f136971964f69ce019699a3071efe791ae7aad8cdca4a86709916ec854b57ac31c8b93fe6a824b9793a5d8e4151c07331c8eca48c6fe4b09b56bc42f1fedf9e9def8a0f734d832d6e2cd9b78f049c06d9f26310e536aba69d16efc7aeabc5136414ecda08c0dd8f4725e692243df16e17ddc2acd76c138a02c798ef539c2b048bbfa98692f20659bd1a8bc17f59067ac729c0358af46153b674597a0a2c2f8523f4c21e42198c838a8ef94664c5a4bd691f4af43f7afb570017cf78ec311c148457b780515dc70e9aed0bdc978fd90b74bd75b327a96e0c8bb69871e17e6617b38b3de51b044250b6e4d910fc810cd36d82ec14a9e176946150dd691a40f8f8e52574a9fa78d226bc6a0dbfe4b94f7ed9d3619f4fa8379863e273b569b14dcb4714332de37402f9f0ee5d97a441f9ce5200025286bc6b37ea58ce5dc679f695de3c6ba067eab629365332a28ae02fde53679125b5d93c7f760455cab4582a492374f5555594169b11e6af3799d780f0eda7e88f51949208a6abddd1fa80e3f35636852e68c7bc0b09faa53286a57ab82ce770fdd443e6859f4036da74169d701cb04b37361422635fe1b3b5a7ab26f79d996cdccde795bf000", "spend_index": [ 0, 1, 2439581743, 4294967295 ], "result": [ "0561d3777d16886c59dc321139a81652a2a26d0d3aacc2c8a4395abc2ed72106", "26743f36d47a4672e1a8ea8830b07602e6b1c678a197671cf8a48c73add9ea5f", "f196979a9156393464a226205342856f82fcc62abbc261ab8c2946f01acbbbb5", "41776e4b5ef0612e56e84a77efa8df83a3554d84f4014c4c5df3e1560562a5bb" ] }, { "desc": { "Inputs": 2, "Outputs": 1, "Witness": false, "Version": -992228038, "scriptSigs": false }, "hex_tx": "3acddbc402bc0caa1000000000000000000000000000000000000000000000000000000000037880d9002373515e48d037ba00000000000000000000000000000000000000000000000000000000fb034aa200a3c107b4017f2ac44961d7e119c8a65a431d1ce4aea903feac3ba4a98980c1867d9db4b80697309cac4d2f756348ffcb8484d8a5eff8c82a5f1a9cab33558e98ef446b0358ca6c6bfdad11a07834e3109b9609d318295ea58cdb80ed4c0e40cd6e994fc58703fbcf603cf966136a3b9ea86531381adacb45f0ad0999346663d732a9313125a821c094cb1a55dfe031c91332853f0ba4ebd62b20ff6e968f7dcb69a128ebb28ca1739c8e799c3a4cada5c9ea33b0c49d6fc3413a82305f8f59b30a6b97b6c11c69e30075abca1248ec560f13fd7b9a66304fd75e", "spend_index": [ 0, 1, 666533160, 4294967295 ], "result": [ "1974f6d3689556f16961d392d2a2bf6665774a95d3991a3c207c2169926ca6b3", "496674f8a4c0b3b346643d324779120d5be39e88cc3a5d7be38c4616c4653644", "02c31a6cf436367f5ded051aed47d0965cdbbfb8e14fcec9833f7f0c44e9d035", "988c1e9159cddabc70e14486dcacfe2ea64cef3aa4d81c2c246ff6600cccf5a6" ] }, { "desc": { "Inputs": 2, "Outputs": 8, "Witness": false, "Version": -664652085, "scriptSigs": true }, "hex_tx": "cb3662d8027bcbf7f60000000000000000000000000000000000000000000000000000000095016521fd770136bc66af182202911250cee6c5b1038e5b4b853d5efc59c1700253f3585183d380c54f08b805994b8887917f0af61d64decbc672140c8aecbdabe3930ed585851b5590c33497e90c337852b0fad85246907f3a9768cb3b6537630fee802f9dcd4c7fb24001c4108d5c9124c36a8a9ec5ae26396244454237e9e8148a22ea0190054f39da11b8ac77fc13bc0bc6e2097caddd89973a6cc6867b3dfa2bb765337402621db7d6efb80ec92aef6f5f411ff67e5329567a0a2aa1edcea25552eedf2bf26c8cefddfd7ab778beeb540de8423f7cebc89af8d20b148c7657e0ef7993d88a70a6b091695f156d9c097df181de8e01ff636bbf7a8b1e2ea29b5832a6f5af3ef6c80e7e178d23a0b0e51e4a689617b95441c4bd767ac5330717813b1d10413626ed1b77a489aa363573d34fd54f07d1857b98bbe6ca549a5bf55fa412995ea7e8ca13b8aee7082d42f03a073f11eeec959189483c6b2a072f388e0bc126b9fdebf142a67be0b3475514b5fae1e271331d2d5865ef9ed150771547258e1d00000000000000000000000000000000000000000000000000000000b454ae62fd0701e6da317e90912ab6cc63214153758de06c9cdf5d46e3643e61f7dc6d0026123dc1bcd10e37ee3ef44c5f025d4ae537b8e3ab685089cc233d897fb089b2986692e35f22d84591af1a7b3fcc7cb5848f5037c99ae16c07fc99549820dfa158da97773b86fd38061f8324de927217bb7d28000b43303be10aced03637cecb33565cfe11f69b27f247e80e3d3aa1afce145bcb53e5e592c72dbffdd2600bb7f7b27852e6e436bda1224f152ff63e038b72f1fd71f5e53c9f7ab22974ae453505dd48a3c88b526e229417006b12c3796cb5184fb4c1bb0c189ddfc55ca77196bb9a11f00eac4599324cec962100d99a035917a29ea61bbfca5dfbd84a903334c104d2e0b9209085cd7a4b90c7db08e3ec36a15f65a215c8d14435e90a9c908b64ec88b815ed0aa7b2c2d592193acefc7b3e02c8c9908c3718ad2d35d139e1c997ff2f121cc636b1da9e4903fe47de4cede8ec6c08a5e23129562acc8868eecf8642c142fc2b5cf9cbc792a17d58387bf945df6cd136059c191ee1f3f8d8e4aa919c84217e558e9514ac7541997be3e1608ab76700ddf83e9d0abd78af7fa47c167f8ed8f840de5afee83fe0275697e8dc42f2449e07bbaf7f62f560912f05fa91849de6688445c1d07b66019367ad7d5b83d58187c8c93b404bb3024d8e98084cea773e8791e756c87e31323e72908e67e69788368e6cbfda79e3fbc66155deea140059acd53e626f1ff91d9f311fa7656c4a789b0ff413c55b6be5c53032f4ca9ed128e0d58d1b6c55dcdb59f7b90a4e1c4607510d6209a8bf995953138906ab3c2d967a280e4c2811ff57ba4fa0f67035e2bf9024106b1ed612f2009224439b1b2842ffde61deea4b9814bd8a5ff977529a5668afc59eb2763a93e064579cb05ac385181f374bf2d7c18f1c7af3df634251d1e5e3b953d124389982de3245d86a4e9c1946936dd3b55c917bf38a1c8395b056114d065008c8919645852c1e3b8822b3e7f338885b10dc74ab947f53a2f6b380c0b69f4d051dd026db658bc2f022f41ccc25e1da8eb30315033512836dda46c4674e46378d3674ffe8d0746a5a82fc7dc283e636a7d0931e71a59068b45d209bd70640775672388db9f5650b7a71ae0edf65fdd05ac1958fd0327868d569c23d35d400e2fcb784fe12314bd3b1f5338f7d93a26034f60d36208c71e7dd7928da1f0895caa301988e9f86ec972d1e7a12c3bd4b6609f14f704681523b01a25552c4bc77b217c0a7ae0a71f5dd8ce13c46515414c48379c89a114a65357c3dce83608347ef99b062080226368353b2273d3c7f94fa5f5c5cd0df9fd80b05a34f411e949da1850e0a453565fb0890ec10c165a8abf1cdf4606ae66fdebac10174f0ce40cf32f237b145db90b6fd915ad12e4b85077450f59d63f0ee9cb9ee48c777f8357766a70dbb68d2ad2b7ba33cd85c6e3be0a90d561813b82dc114b8d08a04ed742f11715accd1382eea179f73f51de77345a132711d425d6b5bbec08b1d6ff6df487132c7fe9be2c05abfd7f9059584533c503f3ff989e1ffd2bb622af3016f319c18abaf0ac8963163ff3dfaa1b52b50c1d06ee489c99e43aabdde819f6032cd57a0e2979c6a487b57b93a062d19829f55c38a3657b564aedc969184b65ca0b038be1aa54c931b3daf73c421c2ab4a7ec7fa65a1f7141fe97e8876bb1082822ae63d6985d58de4f1454880817c1e2a61eeded0933faa2336cde273b30da047ebc7b34fb802824947b0c1c7c0b133affe55154f88ff9071ceec83f479c1fdba0a4cf30521870191a4118b5d002c4ccfea5f91744b66d8e00ba1c11b208c720ffb77ef03ed229cdefba3facb3cb5ee939c9b1d2a7a0f20c85df17597d69d133466f234276e9fd6d3569ba2a4b2d4fa9d937181567dd2cb352c696a66bf6622f86f4d4a418820f1034f829506b687f62d3b22f225356a873e1caefa8c141d533b28dcc1b41b1aa5304214127e7a95b02d82d0ec6dc7e0b77dac914b59fd29e5ee9ab659067d43ec1972a3ed0f25b7ef70bd6f5e8520f91cf39ffdc2f0cb02a4385a4cedba018500ba734712b6d62356e6495f049c189222ad5063b8028ee2104e6ae32b3519d23a265ac7cb6efdb277763ff9e1dbee1f8789b77cbec15f186a2e55ef28980ee68950c864ee5a9bedabb0e9d38276617d9298c42ef7c62a9b3153db10b0971026fd7ef55570f75d5cfc66ae26d15d3f2b85533da7defff5cf5c892a9d693bc87243c2b385b25eb15f18bd1cab3307ae314bf572467b54957810f6a37b2fc55508e265c9c09d4f129b941a1221df796ff99dbc8a9d1ab46926388a1730c8f701c6c0057a51304796a57a49afe3c95515f126554997d55e1c4102fc068d48a12126e392d9f66a1e1aad2e9a6bb00dda31a787d8875b65d20fde8d5fe2e0618be0207cd6cddf6e18bcac2b9c92debf0c0a05d1f617c8f09569e462c5f5a5f2d4d59ae6bcc229bd8106b12e0694224992f946b944820fc2f2dd747cd20cbe21a68f6b0b79af7ff47a4481a150858bf8e0255393f20e4f06749e2ac0c2f255ea32a5349d4f055c631cea35f8e5fc1c3dd709659cb965c6536cc9d7d6d7b0bb0b215b26f7d530ef742e0d8562eb331db50308d99208b9d5dde4558dc0859cfddbf2be1f6f508b451ddaae6762dafe0c04fcdb7e68badf27540dcb175a1e3f6a6e3851261de8a357482b80af1850d923a16494a290c129c60f9ec0ffd19ea8ea0f97b6af", "spend_index": [ 0, 1, 828453430, 4294967295 ], "result": [ "14223bb95cb5089ace31b5dd2fa54e633b9dd60cbe9622794ac6c7578255aeab", "797f7aee1d48be9a28fc4f9316e689bb1ef5d309d0ad51a7f44e598fe96fe9d7", "d9377c0a4b98b538853c775bd335bd2dfa620252880e9eb757f13553e32e6d0e", "745147cc47733cf8bc8a5a562cbb61e3175f36e679dc61f198f0b6fe3bf3bc6b" ] }, { "desc": { "Inputs": 6, "Outputs": 1, "Witness": false, "Version": -1931027793, "scriptSigs": false }, "hex_tx": "afdae68c0620c4e058000000000000000000000000000000000000000000000000000000004f8d2d1e00650104588feead99000000000000000000000000000000000000000000000000000000001ac764b2005f8ef43b135c885b000000000000000000000000000000000000000000000000000000009f440d9a00541c069521d13cd000000000000000000000000000000000000000000000000000000000f6618135006f84fa6b678234430000000000000000000000000000000000000000000000000000000080dd391f00e4d2bd306fba136f00000000000000000000000000000000000000000000000000000000768c6d4d00257affc6013b885e35b58f727dc8b179bb70124ab89e49025858610b85f42f7ee3371540dfcf56395b5cc643d6d11a3ab736b7e4b57a4787665a7a3260fb0b213ada90e0eae735919c031f4774cb907b55ecf41c0fa8e4b6ee17b6a27988ee342d9359a138c0dd6d30f02c5810b1478ac0003f54a635a76028d2e542555072ea3eb1e8e0daed2aac38e4d2202ae2568f2b6ff839df9d1bff6df340d29f5c2f26919478b59cb14efa6fa2379238384974fc913b5471ec00eb97a4213d66d26286dbfa092dac2c2cab41d3a242f3a58374a3b38d4622716840a6d0", "spend_index": [ 0, 1, 3362444138, 4294967295 ], "result": [ "67ab9ace43b9095f407f06235f14dd2f0de435cc176d84ccf7753f09d526a916", "c8941602c1acf44bc263663f5d24ccdb050d58a0fc6a5a52d3c65e91b7a55768", "a072439c88ad5d89e8f8ab06b07850788e54ecac24ea2875f025b71ac699db88", "bbdb0d1a66f26cf1b26885c4a2163f7c4aaa4f9377413a94e5797bf45dd2a5b4" ] }, { "desc": { "Inputs": 9, "Outputs": 4, "Witness": false, "Version": -874883095, "scriptSigs": true }, "hex_tx": "e957dacb098545a2a20000000000000000000000000000000000000000000000000000000075fd30694825ebcd8f1e2e8342da01866f2f98334bcd4bcf63bd59af5d4c5e97ae1ee3f745a4d091cf2b4c2028be3d4afade8169a1cbe16f518784a42942cc2716c621f880c89f479fcab98aa39daf8c84e79ba7e200000000000000000000000000000000000000000000000000000000e6b2d11bc0ff4a5aa6810da2dbc4958b61a3f34de17d7bfe136ee243fd1136ea24d03b7fce5d98bce0a82405d8febe95aa7ec484ba72dcd918637687f646e38707a800968d8a96f7b4f6900041b1052a3ece6012706f1efa746fb5d1f8bb870d73eb0ebed1c54e980ddf5479244f7663002c94a83954006e6530e086e14014a1e53b3b8f93213b8a4c5343f337247ddbf471043d976c0fe27ce5fa25a5f3f7a4d1b8b679b179e3bd8075e711a7dd3c0953a673b6c7b14ee99f3dba804cda975bd187714b7f6b44972d68ec8ad400000000000000000000000000000000000000000000000000000000063af4f1009623c5357dae487500000000000000000000000000000000000000000000000000000000c2820587fd9d012809830ed0ee43648113c614a60ec62defa4627c78c4e0f74d2c5fec35e45ede7cd9122c86c2594c32cab8f78a6a2698bbb98f89bda48cc43cad7bf76116296b1f821f3fa60bb9ad18ed76c20d72ad8b62ae4afce66c6613807c1871c5db1c8487b80cc274ac7976a43fcda0c047ed385c853860dc9c8568d490303cbbf66f863ea1e1a621453539388561df7993139eed6a9a0c1d6fa4703aea5a522149d50b7fbe4e4b47bd763a19b1b70b24ba1cdaefadb6aad561ec5de926d8c17c8aeb3796ca3c93e2237025ddbfaacf1813ae29f75608913a183542977fca8f8cd280345cc61abe67a4c5b5e3a9a633330346bd9c6738f6a5e4f8e4f254863676745104a3076e2a3753fcc267ec596a77cbfe303f11f3881f753db96227bf782e8a31960c866b97e92d4a44fcc3af9ab8986ec6598a28ae9db0c222825ed28726ec00a091b536085737904bd01da260453ff9ccbc79a166eb21c4c00a6c0a2f4ab70cd5354abbc89b64adeb1995e2e39246855bbf335c4005b529d65a983f95452c88c299ec05296c53269204990eb481c5040eb1567ff8c132ec54b26ead680b59ad557be911759300000000000000000000000000000000000000000000000000000000c6fb0db0836334fdcb4c67336f070dcc70d24d625c5097c9b99e707776b7c1832b6682909c5daad5b83670510a6bde4d0b86ce0c96b74efdc6226b1a1f83c165afe56dea14455129b8c7fe5bc8de45ec4d77b8b38eee153f2a83fec943f58512c4432b76795b8885fe86cad5bc1bd65b518ae0e699b6c909efed50c6da3352647ef7791e8dbddd0192c01ef12881995e00000000000000000000000000000000000000000000000000000000435021bd00439c012c2bc78a9e00000000000000000000000000000000000000000000000000000000e9f9cabe003d9de2afdbc8746c0000000000000000000000000000000000000000000000000000000024fdd004fd9c01c3fb32ee1feaf1fdc4682dd4ef32de4a67869a89885783b0afa845136886b5f30aaf0241aa02a4815cfe2f7f2cce227a3bb5eb84d79789af7849d47f6230acbe4455231c2ff7ee5a30dc6d169a041a2aa1c3b753296f3b5cc82523a650afdd714404af6db979ef892dd4fbaba72354f30f686873491170ad12740e8b9547420fc5ba34444dbda398115c1fdd5c9284d98ded2d59a4220a2e52a8c954f1d17f150316f80c9d987175c080f8a8edc9a33bbc82413cd9cd8c6eff80875ef196bf0585e9306c348fc140016a99c66506e59109ebfb1a8e0120b3f557efc9915ca78244353d891fbc7e853a28486346834d0f750113bc34bf2c6b4c26e794df2df14778ca1a42ebf35033b8ab0747bf7d1a046dabe6cdc33061092d8aa9c10f6e5c207a84143606523a754405b362a2b3c514291066fc8f6849ca7d5ab9710d6cb5567a54f3f9b574a5f35da31930c5bd1a3b85d76b8cfde87c24357328110ba6c8531926639d65b386ef12b5b9c4acce40049a9f67ebe63a109a24a825354156a5ed403025b2109f6812f1b014eaba101ea6023940e39617279db6d1d762c38a626ca477fe4300000000000000000000000000000000000000000000000000000000d4f9b9e4005e92b09e040dfbac33a2ea2755c8262493bd17e8ba8591a83afa080308cda50b3ae9b5ce8601fb832476635cb38c22f0ced832dfce9179cccb2c47d243c2f0c55091dc7740a25366000618ac960e792cb1aeacb175ba9d3131659e9982f0a4faec22124975c92815cd010e061a04e2714c709dc3cb0555df751d5bf612c36ea45fce6043af9f5792b779c3bff965247d524e64e250d7b456f2767b021ce4949e015cb493e2c611301e8105c927ef3a9ae15b08032212b352d27d8e5a0497c211e5bb7ae996d8069b4fcc999a9c87a25ffad12cb1605658c7e10e2c577c5fc82a506744b0e97ba5e6ba06fb899fa58f761e046136c15715cdcb85c4033a05b326590ba85fb4e6374d425fa0c83069369ec7e4e79ca8a5199a6a5021e3b5b19681e9356e364d5ac65c37b15ca11ae3a69ffc0458a9cec356a29e27fa161d0b4ca746121cb4d8a7fc36c80ad0169fa58a034dd58bbd79683f225137d953e8906c17f8c40f8e61df754871d18e29950621dd33ba886677f8ff42b780f3b1b8e9b762f3d1af1256bc6f5a41cfe78b2b8bb9ec0e7f97b48ae7e645186a101d72f995ada4ac2cb3766a81c4be4ce6143d731bc8615a082a911e3d41523abd1367b455c86a6798c7a0d285c47259cddcd96c9c72e2e1d3858fed2d7d494d2ae56d42d963a767c74b133004b6289a35466609721dfb8c7104d989525af345649b980aa64c2dd2e5b22dff9d75b86ba49c7ee81b2a872ef4ba2ec76a4da4fc73e2448feb0b9f4b2aed0abd7b7d3ab0985b1052f1f1c4354ca63034050a2c440a369f39ec8366fd65edb0aab19907d18f34d573886cbe99e9ffb104136a663dd3b5475f23f1e76ee4f9e28f4b487a6367d336d88b6aba9d2439508a0747863c0f5fbf3d074ac863b7df9fa7cf663b89ad51c2faa53de17fe38f5305dc1097cf1c23cbb33a5e6511a6ffe751415043d4210ce46a79dd6e00cddfcdc785bbddab5c903256c71d5765ff455c8bfe511f0b649a3f8071014f02f03d2c6e14762a1dd45c3d9544a4c9981352038cb08b13bb708fe8a28b4345b4bdb4add8c5efb4953a155484961c6dee57a4e389bec716e8c22e772e48f0545a0d9d3230043d2c3f5e5ea9f70c0a0dde26a2fdba059fd80c276860160ec6afdac9ce9b397c0d25c4ae2cc48a508bc28ebef0abb8e6cb3651211f7c", "spend_index": [ 0, 1, 162187532, 4294967295 ], "result": [ "0b14c77350be266662c94ab6e5f76050b4a0469ea1015aab3cf625bd35068cf8", "db8732b5313cd230d6009e4ff51699d60a04e4353e591e3cbc3171af44ca5c5e", "66da7e700214af7983f5b53dbae29faabd2189a67dba51601ca7f11e9d34d5fe", "3070c3e90d0b5390886a34cb53e241c5a2319460a649a34e529dc26a15d4e1cc" ] }, { "desc": { "Inputs": 1, "Outputs": 6, "Witness": false, "Version": -958545809, "scriptSigs": false }, "hex_tx": "6fc0ddc601e38aa54c00000000000000000000000000000000000000000000000000000000873f54f9000d0bbad606fec9a289a0acc269c877da865916769ae8cc62ce89f4ea26e28f9f40bf05b52a829561155aae42e922a1dd18f540c85745c59e58ff76fb3301d098a7ad8634c2aa050cc83beb144bbb01170a4c1bf1ca1ce186433f67826a965ebb65a60358ac6855446dbf18393d22d8b87775031f98103793650ea36e99e9989c3f53490849378abb56fe00bc4330883644377541fc89c42661a8362a6f1693111491319afe1042c8c0b4f72434c2c778f4fb54cecf3ff89e775e817254e95fc04be0c436dc7e25ffd0f004851aba8796c6bf77e54aef1793264784af7739c846243d520b907967e6b3a79a582fecd923914b066718a8232658e7374b45c38473952343e45ba311a05412db5c745f5da4726313d07c0c5a24f773ce47a9d67957c0679f3a42a094d9478ff9ab0a87cce41e65b4af111478e6a7c613508fe6acca9cc4db0685849380a7e83a9796bc7f22eaaad7cb1c21aaac860eb4b653ad4d71b27d6f092059d9899dafe6589dfe571c24819d82e92afe96596900fe5dc48dd6c2d441416347f400e15d1b799727274350a510829755ba0cf1f675bc88e0a3b20a6201b38421bc293a4026bee02778c83f3b19c341f5d93eb71e69e4ebff461c884413a22f30b27c85a981f740e528dafe7a0dc9a5b4fc025bd01916c122946110cf049825032e8e7e758db978b2f66d5e24deaa245ffc2ebacc91f881b7a6843e43ca4b9a41caceb531b948fc74e92f9d457e06915476b1b15f03b7c53ed8f126e9304ee119b7a818ec9d0030d1a37490f7e69c8adc1b39c5c05899c08c28bb6b76c1dafa14a0b7f3fee2accbcbd01e50ab1c3d1eee738a866bf5a79ece5a4c962fd32f3aa20709fd7b45f0beb643ac3ba33480c1d8bc7c6bec514a6d8ec41fc8d88a5e0199abbb814edd7e706530a5a55c260034e081bdee78ebc1a8ce732c3b3ba02d0f5e38b0bbf6cae18794976581bacfc3b9d7d537757a36ab1fa5f4ccc8892160e736d69016ffae3dd8e6cfe5da67316c42ca4bd899d1f5304a830939b68c512c1d8f0a1cc341b538313136077d9205ed88615cc2a7a5c7d2d106e80d77c3f32e73534ef6dadcf5d9e0b87e5842b6fabe4358710ea71942a3489ee69a77027f7b5c053b4254fb6cb7aab584eaf515d469f1e58b707fec1c9f335ce7f04505c5ece43fd8bf944ce0c4b1cc510528c826d016caccfc30cbc87ca721a25cd9e8514b192fc03dac8baa93e61185b61b7d0b3e6adb979716251ee883553076b0653fe2658f9bcfba7c765ce79249a60e44a5aaaf4228f6eaafbf6e5d4a1626bd0e07ec7fab15a7c30bf4cbd1976a8e56baa6918204af3f0766f58041d00819faab5eefef348bb1c1e486429d7ba37c2da29bd6aa21e574242c544eb26ed5ea4c0e8d48e05cdce9f2ead031b2ae8cd46896beb9441b60c332512f5f1ad0bdb71aa52eb7ba6e69e91effd34be469cc4a51a1729e7197750e019616d26bec795e6f66c8572716eb8d8443d7039d7b5a37b53ff73090531e943e95e708b1106b09346f6e17c9b1a1dd8c34c943794299e38723a38119b9b9dc67da4f1bbf8d273251932d8d1fc78a4afcb2e45d59c92fb16c8735f6f370c25edf6e43ae0b72d24ce7b027e5d09778569dfd2e542a9de12d495ee952e4ff98f082c36be41a464425cbd8b14e49a0c23e978d5bb4bf901fd8b82160599cfe2d09bb10c5adcc59c55cfee9502308f4cd1985c615b2a288c5c97e416293e160b328a43cdce05e1d6c1555084761a439a2bd7cd686a5231fd3", "spend_index": [ 0, 1, 3791416821, 4294967295 ], "result": [ "2e5006ac1922ac0c1ba24205e9adad753b39e7b10ada6a0a73caad4626a1535d", "e3d7d29935fa2dbd398b89c234b3138091ce1c28a384970d745226e973bad9f1", "c75c2b038cdc9f9af15f6b8a92bafc2369db3c1794354c40860ed783e20bb81e", "bfe8372f7fdf65775f70a5ad3576192001c460aca3f57eb560facc45ada13f0a" ] }, { "desc": { "Inputs": 3, "Outputs": 3, "Witness": false, "Version": 28001504, "scriptSigs": true }, "hex_tx": "e044ab010340fa7ac1000000000000000000000000000000000000000000000000000000007cfa2e5917675ccc65ec2e4f6a5805c9ce83cea2bace928f8d70e25aaca507b0aea1dcfa00000000000000000000000000000000000000000000000000000000e10b5859fdb001877400ea9b1efa85855559c057c74c71e0e5c3959b36aed3f7203cb8bb86d73691348b0963223e8f780cf6347dbb73d0272be706d7a5e4c443e764c6d3a7cf6b477e06d95e49512340bb87a579721db5b7274fae15ee19545dd479a386a87d4a7c7e1d3a488e572e18f30cdf93bf2355945b299140675b3dff9f0ba3cd2ef22cfb2a4eb7d3d80980473310efc821bfe8fa56112ca4ce7994dcb269d4e41c39c118c2e555f89a120dfc2f8e47b7822fa709595f63e48a2e2b4b58bbc1d526f3f42237ee4f4a068c351b3b3e0d05024ca5c7b75a0e2e8cc5fb55177b8ea9a166109ac000515f30a59412be6f33e963d96899d3363ca50ea14ca78ffd6f29d2c78ef195fda6313a3deda1b592a2ce0e0ee4dadb1208f9f99e14078e484578d6fa88d91bcedfacc53b695d175c613b10ef42c5b279249c741b92c525200d52801c50afac12ec1b502f80e14765479af03ec65071cba119b68ba26f65284ae935414cab6667a0b643a44edea4b41bf9f0698e55cbaa9db64bf9b5c1cff02f485c1af6dd7ef0a16d8ca3ee1b1dc4118ffe250bdb113c834c3dddd1800bd55ff81956ea4054eeeed296af81add5f00801f9fdbabc8d29b958e947a6000000000000000000000000000000000000000000000000000000006362e53cfd6b01d40085bb5cb824f485eff1864e3d4749b50a38308fb6e2eee2b8595834b4bd89a33adab0dce1d55a1dad7453e60d4367435478a27d4ec517c6a8f578fb71bb2d6f504ac9d1db3a508cbe07324af806480af1218795faf985b97213f4e24f13acf39790c2a059e4a6e0ded11fd80906e71632cd6fc14708b4d3ec5d9e7e246d80f8c16cb37184c3f5ee897d2313cd103dc8446bac19d46f7835bc84749275f550d6d2b26e0298223898a342d86fd0f2e1025f97f847a11643cf74bd402f9fdfd73955305ffd3e98a60f703700190b676fe2b165b2666135266da41fb878eb02ab4740703594b80e2cd4745deb573b8c24982253709e713c77f1aaf00656623e62855b46449019d2590ef572a22615dcf438450a5321a008f1c82387db66fb4fe7f425811bad034df990724f37afbfdb610e6fabecbfcee59a124c0eccd8887832b739e3312eeb5ef1891ea02a7cc0609feed848548f48573ed5ed4c80e35844feb0f03e795469033fdcbcae946a312603a9d820f3b114ce1bc810c835828e295c467a41651a88e631884f46cfc19231eeb980d8010b9d9990c688280ec250da2cf6b4c80ef26ecccd58d68f38657131641694ac3811a5032dd3eba2867c4b25d837f60941d7bc691b1964e8dfebff94ea0ade2649d53c18a65767a6503b12772d1d7584a6bcd9a25bca845235d12393ba6f147861e79f2d145fd3691d315210d445be9f970d927c1937eb71031d61de998c910c4ab8f02f5489fb50e7f6276261c9da4ff7faaa226acbd24acc021f149d2daaefd15868136187a5eaa35876cac95c239f9ad5badc9d6bc8651d4c17338a92cb88328eb391c887ddbe7b57b7999bfc66f8b88867ac15a618e3f8be4e4dbd10d96872c627cdfe645fc78a38bc0fb087a34266cf5990a764221b1b4ca2ab92d37266cacb0091f8802ccdff63ca4787edfa0ff24df50e2255dc79619bfa756215b3fdb1539730a28c56baae728ebf0b6efe5063f37f2b36fffd185dbd5606657c7f96c2b75e6c8d7014e2cc4c514a4fce5adf7ff4f60f1ba90d9dbd3693cd6b3e86f125bd2aff4ddca60ab72f6afc7392d30ede4470092e83e92ad0cc938e98f8e49bf332eddf4cc50cc84cd0817a24ef5189c0da12a9e572a49a0ceabb6ee7c953a477cb089d597f54a5a873ff6e1e49d6dba7099fdcdaa82054d64cd4f8ef7c282775bafc31cfd435e669d102e7aa1ca7769fdc63e68e51039541eee399f20cf3f5e3a863d3e962a124031dd08a8d8d0043c35903537e03ce98d041dbfda7e679e07e4726f70ce6ceb957b15de5c88a9516ed39598098a21978eed2dcde79b10ae8378b951af7ec9ce672f56a12b2718ce991b2d88694daebab4ba9ed00215d67556d0e3c88164cf8619c812611022f0195843eed22", "spend_index": [ 0, 1, 3820598746, 4294967295 ], "result": [ "a052c1319b824ac2c74620fe9e34b98e7704ff278e29e9d23b412106f23c4cc3", "df732fdf2991619c2c1c8e5e0cc03dfe12f224259a5fc5578689571566280ca7", "925ff3fc61a3204a96a40efc87b5c6830a0f1a1791204d12cfca674d0e1f4498", "4f8f73c50d9fac235513880b77dbeb50cd5a37b9488a6d11828d0fdc49bb63c6" ] }, { "desc": { "Inputs": 2, "Outputs": 2, "Witness": false, "Version": 365301493, "scriptSigs": false }, "hex_tx": "f50ec615021d38a93e00000000000000000000000000000000000000000000000000000000f31203eb002037e7ffd9301c6800000000000000000000000000000000000000000000000000000000d3fcbbaa00fb8133f202fa8882e48115c743c8e2d189ebda48f2358eae7232b1cbb268237cb7e56a298523d9d195f916c0ab03156cbaa63861ef45f5e66e1e40125f65e3889722e69b82a4c7c3cdfdc28259beb010c63b43356472e08b36e4872bb15b0a180a47a75d3b17f066b4d0126923f69a28f7daecfc60c523605a4dcbd9bbfe25543744004643f121fa5b1089d4898a920b776d1cfdb466102ed3426eb1202b857420a9dc350a3b2b359dc6e10e0e572fc7492dc2ab4d243e67d7067adc190f8e91158cc691365b374d80801ed126b03f2cd25fd2fc82f63c373c6772503264c8d76efd7523cb2b950a8de0f9be4f3334e335c4aa724a94c273ca23e899633417ba9433f6cb9f33d82fd55e6e5c24c21897821cbe79c7e191a9bd72a108c4f6bc23277e1f3a7ba7a0be9614c6175e64334100785b59386b8e5629d459f72972d8c4b218f3b3eb0786f8f71f8f0a1ec9cac6beb70a778419d03d03909801ad795869a7826b39f682917de9b2791d49951e67f8993956e43ab9bec8e8469ab1de37fc57f3a21ca084a45bd55bb3a9cbe102d47d920ce5cdd4446c801160a41be9601936412d03fe24a54ebf8570", "spend_index": [ 0, 1, 701516357, 4294967295 ], "result": [ "d132f573cccb094cff83da9ef8e921e025c5c1c882c0566feab1b4823cf79563", "c9bb3447a0d33de729b44d1e6a712e68af64b6c9238d1d824999ead42baf9f67", "16d589f35d842209bcaed71275bda304a5e486bc962c96b0ad933a169f623ac1", "0b703dfabbc5645f1840cb2c647a7f991d768e7640fbcf87d1277c580c60ef81" ] }, "Inserted without comma at end to make diffs cleaner..." ] ================================================ FILE: bip-0119/vectors/tx_invalid.json ================================================ [ ["The following are deserialized transactions which are invalid."], ["They are in the form"], ["[[[prevout hash, prevout index, prevout scriptPubKey, amount?], [input 2], ...],"], ["serializedTransaction, verifyFlags, [{\"if_unset\": [\"flag A\", ...], \"then_unset\": [\"flag X\", ...]}]?]"], ["Use BADTX for verifyFlags if it is expected to fail CheckTransaction()"], ["Objects that are only a single string (like this one) are ignored"], ["CheckTemplateVerify (CTV) Tests"], ["Modified Segwit OP_CTV Spend Failed if Amount Mutated"], [[["10bf165531fbdfac386f018d92d72dce3ad73af1f183f6fac2c7a2a1050aa51b", 0, "0x00 0x20 0x9e650578b4f13cde08d16211f3635239e22ba3e108ba7f5fa4bd6c12f8c8219a", 155000]], "020000000001011ba50a05a1a2c7c2faf683f1f13ad73ace2dd7928d016f38acdffb315516bf100000000000000000000ae90300000000000017a9142b697af70a75926b158a2ea0aab8054eb18490ac87d00700000000000017a9143177919dae74db1c4cd3e6e69861091c6aee9eb287b80b00000000000017a91417d751e7c17c8264e90e4831fed9c47804b2bbc887a00f00000000000017a914a46167b1fbca936b56dda9710a0c16a53fd32fe687881300000000000017a914b4a5ddbdda32760d1c61dd131007fd7e67d650e187701700000000000017a91480909aab0729614b1162d86563cbfb0c71d5bc9e87581b00000000000017a914997c99e26f67463a1f9770003f90603360408bed87401f00000000000017a9149fef27cd2e724889aa522ac6b5eb35de7582727487282300000000000017a914c7c616d8323c7046de863e2301ec0c7884626e9687102700000000000017a914b590ca292351b64cbf725bad01c3ba6da808ab0b870122200a2891d90df11c7714549c76b80b29c86d544110d958a6dabcfcd5cda1612427b300000000", "DEFAULT_CHECK_TEMPLATE_VERIFY_HASH,WITNESS,P2SH"], ["Modified Segwit OP_CTV Spend Failed if # inputs Mutated"], [[["7438c73c9a554540dce173b485e888683e9ae5beae3ae94142e77ae2cc024e3c", 0, "0x00 0x20 0xc19287614d027e87b85ace418cb0fc2d89241392370f0f7cf2ebb06b861c85f0", 155000], ["24040d2cd61f2ecb67e9fe5634c1d90e59b6b16028ff03003cf20f398ce27e44", 0, "1", 155000]], "020000000001023c4e02cce27ae74241e93aaebee59a3e6888e885b473e1dc4045559a3cc73874000000000000000000447ee28c390ff23c0003ff2860b1b6590ed9c13456fee967cb2e1fd62c0d04240000000000000000000ae90300000000000017a91406651b0a47731127630ccc27d07fb9afc041846987d00700000000000017a914c758d7ce652d5ed562253ed00e9afc34ea1f76bf87b80b00000000000017a914fe8740b477b23838679c7eaa6e452e66c58a72bc87a00f00000000000017a914cc07d98fc32e2ff65f62076f2824d63bd5a1628787881300000000000017a914acfb84e8356788c7a8312194d1833e5d5677d58e87701700000000000017a91409aad9fbb6609e4486fa5b04afbbde40659388f787581b00000000000017a914ffd3dc8f12ebb700dd45a6a58914347533b6728587401f00000000000017a914781456255e72a09dfab2211dc151165c62ab7af987282300000000000017a914ee01dfa11feb2bc68b22d6909052647c8c001ec787102700000000000017a9145dd4e76cb2cef90e09f181c55fdc42717f3d948787012220cf100c0bb5dc85c104d87c31e7b57a4a7791cc2091dc87ddaac40c91edda7f6bb30000000000", "DEFAULT_CHECK_TEMPLATE_VERIFY_HASH,WITNESS,P2SH"], ["Wrong Size CTV Argument is Discouraged"], [[["13e313be0d1eab290bcf2b58f4ad76c3f4fd46b2ac4273c607cdc7f5a4170794", 0, "0x00 0x20 0xaeba7cb39e708a34dd186698a80cc34e70bb92921a01f853ac691bb572b52d62", 155000]], "02000000000101940717a4f5c7cd07c67342acb246fdf4c376adf4582bcf0b29ab1e0dbe13e3130000000000000000000ae90300000000000017a914f0ccedba146f6390e5961b2a0a39cfba046c312987d00700000000000017a91458d4792223eebb552801d6690b5985513fbddaca87b80b00000000000017a914774b6fe872b65890c610ec6edda928703fe8503e87a00f00000000000017a9148ad37662e56b5f2e472e4bdc205f0dcde8708fd787881300000000000017a9149e8680d850f172186f4e16cee442f0d0121fd46e87701700000000000017a9141394792d48889f70878ce2ee3b151de33d4b774987581b00000000000017a9142444dbb85cf5dfa3e94d2a970a4d4bb795495df687401f00000000000017a914b0437ba6b526e697e695d4f8a53482d26547b64f87282300000000000017a91408ceb5466bc28db2122f954ca59d4a4a08fc133b87102700000000000017a91486f51c990634abc769d6d9d01608ff99f93b050387010251b300000000", "DEFAULT_CHECK_TEMPLATE_VERIFY_HASH,WITNESS,P2SH,DISCOURAGE_UPGRADABLE_NOPS", [ { "if_unset":["DEFAULT_CHECK_TEMPLATE_VERIFY_HASH"], "then_unset":["DISCOURAGE_UPGRADABLE_NOPS"] } ]], ["Empty Stack is Rejected for CTV"], [[["e658e5b94eba5931faf2379a61a75a05b153648690527d35f7143bed462a6ebc", 0, "0x00 0x20 0x6c9cc4747e7d287ac1abf8c65152a78d369213583e306b7d3163e12c561abaa2", 155000]], "02000000000101bc6e2a46ed3b14f7357d5290866453b1055aa7619a37f2fa3159ba4eb9e558e60000000000000000000ae90300000000000017a914b038d0ca030a6d6bc4a06bda13ae1413ce96f37e87d00700000000000017a914fa5716162fb8f5f3cafdce1c1f5533e182c83f4d87b80b00000000000017a91417d10dea89621354333f4dfcbdafe18ec6a794da87a00f00000000000017a9142abb09f63aaecdfbe0e92fedc0afedf19194360187881300000000000017a914aab8b0219014272348de62cbc195e20151b7735787701700000000000017a914a507b83449359c82a195fc9bab99fa1b7c8289eb87581b00000000000017a91401ea6e7336fb9d5e5f36994eecade840ba938d0687401f00000000000017a914e5a474adbd25d66bb70c9b0b6a27f3eebf70b3f587282300000000000017a914d4ae33b227632cf0434f054782558baf9aa6e42d87102700000000000017a9147e4cca8f6c63cb7a56dd3c6edd2acbd031813de9870106b3746375685100000000", "DEFAULT_CHECK_TEMPLATE_VERIFY_HASH,WITNESS,P2SH", [{"if_unset": ["DEFAULT_CHECK_TEMPLATE_VERIFY_HASH"], "then_unset": ["DISCOURAGE_UPGRADABLE_NOPS"]}]], ["Wrong Size Stack Argument is Discouraged for CTV"], [[["e658e5b94eba5931faf2379a61a75a05b153648690527d35f7143bed462a6ebc", 0, "0x00 0x20 0x6c9cc4747e7d287ac1abf8c65152a78d369213583e306b7d3163e12c561abaa2", 155000]], "02000000000101bc6e2a46ed3b14f7357d5290866453b1055aa7619a37f2fa3159ba4eb9e558e60000000000000000000ae90300000000000017a914b038d0ca030a6d6bc4a06bda13ae1413ce96f37e87d00700000000000017a914fa5716162fb8f5f3cafdce1c1f5533e182c83f4d87b80b00000000000017a91417d10dea89621354333f4dfcbdafe18ec6a794da87a00f00000000000017a9142abb09f63aaecdfbe0e92fedc0afedf19194360187881300000000000017a914aab8b0219014272348de62cbc195e20151b7735787701700000000000017a914a507b83449359c82a195fc9bab99fa1b7c8289eb87581b00000000000017a91401ea6e7336fb9d5e5f36994eecade840ba938d0687401f00000000000017a914e5a474adbd25d66bb70c9b0b6a27f3eebf70b3f587282300000000000017a914d4ae33b227632cf0434f054782558baf9aa6e42d87102700000000000017a9147e4cca8f6c63cb7a56dd3c6edd2acbd031813de98702015106b3746375685100000000", "DEFAULT_CHECK_TEMPLATE_VERIFY_HASH,WITNESS,P2SH,DISCOURAGE_UPGRADABLE_NOPS", [{"if_unset": ["DEFAULT_CHECK_TEMPLATE_VERIFY_HASH"], "then_unset": ["DISCOURAGE_UPGRADABLE_NOPS"]}]], ["Wrong TX Hash passed via the stack fails CTV"], [[["1303ae3fc607b6eb3a4da63d3d7f4722b595db87890943618e11c3905662cae4", 0, "0x00 0x20 0x6c9cc4747e7d287ac1abf8c65152a78d369213583e306b7d3163e12c561abaa2", 155000]], "02000000000101e4ca625690c3118e6143098987db95b522477f3d3da64d3aebb607c63fae03130000000000000000000ae90300000000000017a9145850541d205b7b1feb1bc10112f9d739fa9a7dc287d00700000000000017a914d76b85e77e20777d5ec9d7d9998ae0c062d4669087b80b00000000000017a914c79f4a39b0580e4ec90e1b4989fc6124e4135cc187a00f00000000000017a91469635f1f4c06d66591282a02303b1435ee888d9487881300000000000017a91410d3b9b2aaffae25b6098169e2dc69928849215387701700000000000017a91456e4a3e5a3a49b9a66240288e79a8a5e8e31d05587581b00000000000017a9143936403d1a70b32c1e0e6920f9cd99cbc8a8345787401f00000000000017a9146ec4fa5a4e329f9d92ea29b65fa48c6ec1470ffa87282300000000000017a914f66743d56210c98bce8a44742b2ecfa9b7f48fdb87102700000000000017a914555c65f1c355993b46003311931eb08cf457209b870220a2638b51a692e6a8b39e87c431edde4fc1ada3dedaf9665875ac8353af44c50706b3746375685100000000", "DEFAULT_CHECK_TEMPLATE_VERIFY_HASH,WITNESS,P2SH", [{"if_unset": ["DEFAULT_CHECK_TEMPLATE_VERIFY_HASH"], "then_unset": ["DISCOURAGE_UPGRADABLE_NOPS"]}]], ["Embedded CTV Impossible with Bare P2SH due to hash cycle"], [[["6a869fd9a0395f35e412ad3eb7fffa61a59263b1ad16aeb5fcc30e032bc3a8bf", 0, "OP_HASH160 0x14 0x40aec8967698985eb369afd3ad3dc571110e6a10 OP_EQUAL", 155000]], "0200000001bfa8c32b030ec3fcb5ae16adb16392a561faffb73ead12e4355f39a0d99f866a000000002322203b8d241649e612058fd2f1b4decbe9141284f0e4dd297d95b0da01a5d8791e4bb3000000000ae90300000000000017a914b04d55bbfedf606a08795fb0c2655bb3212f2bde87d00700000000000017a914d079c2cfad655234e68159422727eefa78811b4787b80b00000000000017a9145ea3edd87eb790af8051da692f4d59e5be6ffd4b87a00f00000000000017a914e17e2c4f4fcae1ef0d5ef96c740565426009ca2187881300000000000017a9144769d9f3b6fdf14f1223d9e7f11be7873bcbcde387701700000000000017a914064529bab7b89253159c9043ef128f37f78add7a87581b00000000000017a9147bae64476db031d744b442ddee9af3e60ef1e4ea87401f00000000000017a914dd2d96d0ba673c0b9d5950223c334f19f2b6f4a487282300000000000017a9148abaaa7b977855f96afacea4c79e3caf5e7482c487102700000000000017a9140dab14b1ee04aea522639ee27d29a5f6a57758c18700000000", "DEFAULT_CHECK_TEMPLATE_VERIFY_HASH,P2SH", [{"if_unset": ["DEFAULT_CHECK_TEMPLATE_VERIFY_HASH"], "then_unset": ["DISCOURAGE_UPGRADABLE_NOPS"]}]], ["CTV at pos 2 with >1 Input Fails if too few inputs"], [[["eeda9ea077b04abec103ffbba6bcf41cd67cdfdabe5ccc6ed766b9cd4ed4808a", 0, "0x20 0x3e123dbe62352fa40471c195aebd3cdec43cca8728520c8a2d5737009fa05b0b OP_CHECKTEMPLATEVERIFY", 155000]], "02000000018a80d44ecdb966d76ecc5cbedadf7cd61cf4bca6bbff03c1be4ab077a09edaee0000000000000000000ae80300000000000017a9144dd991d2f69eed133bb9d16e298703c830e1fb2387d00700000000000017a9147a50ac55b0af704dfffc797c507db803488ad44787b80b00000000000017a914caab97b53be0b75526e011bc49b0101365f611b887a00f00000000000017a91448c947e1b16103782a7dcba1dd5896936fbc7d2587881300000000000017a914ff075d852727e7e32ff5e11b13d254cb553fb73287701700000000000017a914761069764474d5ef5d0e068e88e4ebe2edd2336087581b00000000000017a914cd76c979ed6421f5d39380b5eb3d0dc7f56e864b87401f00000000000017a91417e7563571166469e14275be7ef00d91927eee0387282300000000000017a9140f9ddd36a76392fec584f05b34d33282fbd4921287102700000000000017a91417603536acce13cf7496387f8169a7f832f08f4c8700000000", "DEFAULT_CHECK_TEMPLATE_VERIFY_HASH", [{"if_unset": ["DEFAULT_CHECK_TEMPLATE_VERIFY_HASH"], "then_unset": ["DISCOURAGE_UPGRADABLE_NOPS"]}]], ["CTV at pos 2 with >1 Input Fails if inputs in wrong order"], [[["eeda9ea077b04abec103ffbba6bcf41cd67cdfdabe5ccc6ed766b9cd4ed4808a", 0, "0x20 0x3e123dbe62352fa40471c195aebd3cdec43cca8728520c8a2d5737009fa05b0b OP_CHECKTEMPLATEVERIFY", 155000], ["b6d623f1e5eaaaa83a21739f60ac173818ce6b9e13ca18ddda74e9dbe6124c0b", 0, "1", 155000]], "02000000028a80d44ecdb966d76ecc5cbedadf7cd61cf4bca6bbff03c1be4ab077a09edaee0000000000000000000b4c12e6dbe974dadd18ca139e6bce183817ac609f73213aa8aaeae5f123d6b60000000000000000000ae80300000000000017a9144dd991d2f69eed133bb9d16e298703c830e1fb2387d00700000000000017a9147a50ac55b0af704dfffc797c507db803488ad44787b80b00000000000017a914caab97b53be0b75526e011bc49b0101365f611b887a00f00000000000017a91448c947e1b16103782a7dcba1dd5896936fbc7d2587881300000000000017a914ff075d852727e7e32ff5e11b13d254cb553fb73287701700000000000017a914761069764474d5ef5d0e068e88e4ebe2edd2336087581b00000000000017a914cd76c979ed6421f5d39380b5eb3d0dc7f56e864b87401f00000000000017a91417e7563571166469e14275be7ef00d91927eee0387282300000000000017a9140f9ddd36a76392fec584f05b34d33282fbd4921287102700000000000017a91417603536acce13cf7496387f8169a7f832f08f4c8700000000", "DEFAULT_CHECK_TEMPLATE_VERIFY_HASH", [{"if_unset": ["DEFAULT_CHECK_TEMPLATE_VERIFY_HASH"], "then_unset": ["DISCOURAGE_UPGRADABLE_NOPS"]}]], ["CTV at pos 2 with >1 Input Fails if scriptSig of other input modified"], [[["eeda9ea077b04abec103ffbba6bcf41cd67cdfdabe5ccc6ed766b9cd4ed4808a", 0, "0x20 0x3e123dbe62352fa40471c195aebd3cdec43cca8728520c8a2d5737009fa05b0b OP_CHECKTEMPLATEVERIFY", 155000], ["b6d623f1e5eaaaa83a21739f60ac173818ce6b9e13ca18ddda74e9dbe6124c0b", 0, "1", 155000]], "02000000020b4c12e6dbe974dadd18ca139e6bce183817ac609f73213aa8aaeae5f123d6b6000000000151000000008a80d44ecdb966d76ecc5cbedadf7cd61cf4bca6bbff03c1be4ab077a09edaee0000000000000000000ae80300000000000017a9144dd991d2f69eed133bb9d16e298703c830e1fb2387d00700000000000017a9147a50ac55b0af704dfffc797c507db803488ad44787b80b00000000000017a914caab97b53be0b75526e011bc49b0101365f611b887a00f00000000000017a91448c947e1b16103782a7dcba1dd5896936fbc7d2587881300000000000017a914ff075d852727e7e32ff5e11b13d254cb553fb73287701700000000000017a914761069764474d5ef5d0e068e88e4ebe2edd2336087581b00000000000017a914cd76c979ed6421f5d39380b5eb3d0dc7f56e864b87401f00000000000017a91417e7563571166469e14275be7ef00d91927eee0387282300000000000017a9140f9ddd36a76392fec584f05b34d33282fbd4921287102700000000000017a91417603536acce13cf7496387f8169a7f832f08f4c8700000000", "DEFAULT_CHECK_TEMPLATE_VERIFY_HASH", [{"if_unset": ["DEFAULT_CHECK_TEMPLATE_VERIFY_HASH"], "then_unset": ["DISCOURAGE_UPGRADABLE_NOPS"]}]], ["CTV at pos 1 with specific scriptsigs fails with incorrect scriptSig"], [[["a2522fa96033c5736f3142ff616426cd03a3d0f077f609e22c5a33a96e04e597", 0, "0x20 0x4870387ef3dc7b392294140a323ec7b38dc138710f0931ce27f386a57128ea63 OP_CHECKTEMPLATEVERIFY", 155000], ["b6d623f1e5eaaaa83a21739f60ac173818ce6b9e13ca18ddda74e9dbe6124c0b", 0, "1", 155000]], "020000000297e5046ea9335a2ce209f677f0d0a303cd266461ff42316f73c53360a92f52a2000000000151000000000b4c12e6dbe974dadd18ca139e6bce183817ac609f73213aa8aaeae5f123d6b6000000000151000000000ae80300000000000017a9143f163a8747557345ce2e6fe00c1894f2f281795e87d00700000000000017a9144cf13dfda93a7413b7e646611735656e5457657087b80b00000000000017a914868998b49df649c37a88d48c9d4a5b37290e507287a00f00000000000017a914034f9914a77571a6396482e9881745c92c3037c687881300000000000017a914a8238003e1732e2baf4334a8546d72be99af9bae87701700000000000017a91491dbac5d67d5941115a03fc7eaec09f31a5b4dfc87581b00000000000017a914e0c0f19fec3b2993b9c116c798b5429d4515596687401f00000000000017a914d6b40d98d94530f1a1eb57614680813c81a95ccd87282300000000000017a914fb0bfb072bb79611a4323981828108a3cf54b0a687102700000000000017a9149e2d11f06ba667e981b802af10be8dabd08eafff8700000000", "DEFAULT_CHECK_TEMPLATE_VERIFY_HASH", [{"if_unset": ["DEFAULT_CHECK_TEMPLATE_VERIFY_HASH"], "then_unset": ["DISCOURAGE_UPGRADABLE_NOPS"]}]], ["Make diffs cleaner by leaving a comment here without comma at the end"] ] ================================================ FILE: bip-0119/vectors/tx_valid.json ================================================ [ ["The following are deserialized transactions which are valid."], ["They are in the form"], ["[[[prevout hash, prevout index, prevout scriptPubKey, amount?], [input 2], ...],"], ["serializedTransaction, excluded verifyFlags, always included verifyFlags?, skip excluded one by one?]"], ["Objects that are only a single string (like this one) are ignored"], ["Check that CTV is Processed with a Taproot Spend"], [[["f90521604b56c392ffa17a01bcae5914b8cf7728cc6cec00d90838818cc5465f", 0, "1 0x20 0x24f5fe807bcee7774dc515f0b7ee8d6ae39eefd1b590264c52ff867e22c49419", 155000]], "020000000001015f46c58c813808d900ec6ccc2877cfb81459aebc017aa1ff92c3564b602105f90000000000000000000ae80300000000000017a914ce0036ae7d49f06967dd92cc1ffff4a878c457f987d00700000000000017a91406e00c3b362e65e03507a2858d7b6499b668669887b80b00000000000017a9142ee42c65592c59b69bfefbd03781140c67e5232487a00f00000000000017a9146b3df16a1e6651d582ca6598900cb4f2d6c9dfb887881300000000000017a914877d55932d4f38b476d4db27e4efbe159ff0a07187701700000000000017a91441e9dc892e861d252d513d594ba833cd6bc8917087581b00000000000017a914b93075800c693dcc78b0553bf9d1cf879d76a02487401f00000000000017a914e9f0ea3a2cae0ad01114e2ec3502ef08bbc50af487282300000000000017a9149a645b5293bdf8be72cb9d1460bce7d64445cfad87102700000000000017a91451e5d6b2ee24ae128234c92245df3624620ea7d3870222209eb65498bfcd4eb90e61c2c5e323a9c16c8bfd8d53ba649915bcdb572099c12fb321c0b7e0105780185688d998a8f8438aa07637a5799755688ec80175cb26c0406e0200000000", "NONE", "DEFAULT_CHECK_TEMPLATE_VERIFY_HASH"], ["Check that CTV upgradability works (taproot)"], [[["f90521604b56c392ffa17a01bcae5914b8cf7728cc6cec00d90838818cc5465f", 0, "1 0x20 0x24f5fe807bcee7774dc515f0b7ee8d6ae39eefd1b590264c52ff867e22c49419", 155000]], "020000000001015f46c58c813808d900ec6ccc2877cfb81459aebc017aa1ff92c3564b602105f90000000000000000000ae80300000000000017a914ce0036ae7d49f06967dd92cc1ffff4a878c457f987d00700000000000017a91406e00c3b362e65e03507a2858d7b6499b668669887b80b00000000000017a9142ee42c65592c59b69bfefbd03781140c67e5232487a00f00000000000017a9146b3df16a1e6651d582ca6598900cb4f2d6c9dfb887881300000000000017a914877d55932d4f38b476d4db27e4efbe159ff0a07187701700000000000017a91441e9dc892e861d252d513d594ba833cd6bc8917087581b00000000000017a914b93075800c693dcc78b0553bf9d1cf879d76a02487401f00000000000017a914e9f0ea3a2cae0ad01114e2ec3502ef08bbc50af487282300000000000017a9149a645b5293bdf8be72cb9d1460bce7d64445cfad87102700000000000017a91451e5d6b2ee24ae128234c92245df3624620ea7d3870222209eb65498bfcd4eb90e61c2c5e323a9c16c8bfd8d53ba649915bcdb572099c12fb321c0b7e0105780185688d998a8f8438aa07637a5799755688ec80175cb26c0406e0200000000", "DISCOURAGE_UPGRADABLE_NOPS", "NONE", true], ["Segwit v0 CTV Spend"], [[["c16621d89637274011a8fb02ac487d283367f33d36de8c1ec8e323e55cb149cb", 0, "0x00 0x20 0xf47ad51491d952cb1fad0d3f208dde482561d2170ebbbbc08e2e0292eeb4ec3d", 155000]], "02000000000101cb49b15ce523e3c81e8cde363df36733287d48ac02fba81140273796d82166c10000000000000000000ae80300000000000017a91496e75de842d245fe846f1866f535d3d549af1eee87d00700000000000017a91443078220afb62f1dd0f13b58103c2cdea3ec31eb87b80b00000000000017a914c2aabf119c1825b1de66bc34e0792e37c198b5a987a00f00000000000017a9146e9e99a0b342e90e9360e26aa1a2b12ac7d1701e87881300000000000017a9149fc2952de5c6268759a4addd6f1336585de5a6b687701700000000000017a914f0bb53b2734e0f4027b25084630f4c7cb793f0d087581b00000000000017a914151a578ea0bbe3a24bf8335c4ee162643be28b4787401f00000000000017a9148f7ffde60fa425fa919ab9de3c7731fa4268151787282300000000000017a91454c45d77bccc359d07a2b17b4abfc78e8c3237b787102700000000000017a914e43197dbd28424b86c7c8823180e2b15192a96d1870122207427029cbb0a48361ba1b83e4fff21918618477be3d217d83b2ff846815305f6b300000000", "NONE", "DEFAULT_CHECK_TEMPLATE_VERIFY_HASH"], ["Check that CTV upgradability works (Segwit v0)"], [[["c16621d89637274011a8fb02ac487d283367f33d36de8c1ec8e323e55cb149cb", 0, "0x00 0x20 0xf47ad51491d952cb1fad0d3f208dde482561d2170ebbbbc08e2e0292eeb4ec3d", 155000]], "02000000000101cb49b15ce523e3c81e8cde363df36733287d48ac02fba81140273796d82166c10000000000000000000ae80300000000000017a91496e75de842d245fe846f1866f535d3d549af1eee87d00700000000000017a91443078220afb62f1dd0f13b58103c2cdea3ec31eb87b80b00000000000017a914c2aabf119c1825b1de66bc34e0792e37c198b5a987a00f00000000000017a9146e9e99a0b342e90e9360e26aa1a2b12ac7d1701e87881300000000000017a9149fc2952de5c6268759a4addd6f1336585de5a6b687701700000000000017a914f0bb53b2734e0f4027b25084630f4c7cb793f0d087581b00000000000017a914151a578ea0bbe3a24bf8335c4ee162643be28b4787401f00000000000017a9148f7ffde60fa425fa919ab9de3c7731fa4268151787282300000000000017a91454c45d77bccc359d07a2b17b4abfc78e8c3237b787102700000000000017a914e43197dbd28424b86c7c8823180e2b15192a96d1870122207427029cbb0a48361ba1b83e4fff21918618477be3d217d83b2ff846815305f6b300000000", "DISCOURAGE_UPGRADABLE_NOPS", "NONE", true], ["CTV reserves different sized args for future upgrades"], [[["e8e9805801b7fb44814531de0dd498b955651b9c25a85a043d73f18970622647", 0, "0x00 0x20 0x65f15821061635e6807f06701bf0a12d8e89dcff88df5968bd0822c9dbb52f1c", 155000]], "020000000001014726627089f1733d045aa8259c1b6555b998d40dde31458144fbb7015880e9e80000000000000000000ae90300000000000017a91496e75de842d245fe846f1866f535d3d549af1eee87d00700000000000017a91443078220afb62f1dd0f13b58103c2cdea3ec31eb87b80b00000000000017a914c2aabf119c1825b1de66bc34e0792e37c198b5a987a00f00000000000017a9146e9e99a0b342e90e9360e26aa1a2b12ac7d1701e87881300000000000017a9149fc2952de5c6268759a4addd6f1336585de5a6b687701700000000000017a914f0bb53b2734e0f4027b25084630f4c7cb793f0d087581b00000000000017a914151a578ea0bbe3a24bf8335c4ee162643be28b4787401f00000000000017a9148f7ffde60fa425fa919ab9de3c7731fa4268151787282300000000000017a91454c45d77bccc359d07a2b17b4abfc78e8c3237b787102700000000000017a914e43197dbd28424b86c7c8823180e2b15192a96d18702015101b300000000", "DISCOURAGE_UPGRADABLE_NOPS"], ["CheckTemplateVerify Argument from Witness Stack"], [[["e8e9805801b7fb44814531de0dd498b955651b9c25a85a043d73f18970622647", 0, "0x00 0x20 0x65f15821061635e6807f06701bf0a12d8e89dcff88df5968bd0822c9dbb52f1c", 155000]], "020000000001014726627089f1733d045aa8259c1b6555b998d40dde31458144fbb7015880e9e80000000000000000000ae90300000000000017a91496e75de842d245fe846f1866f535d3d549af1eee87d00700000000000017a91443078220afb62f1dd0f13b58103c2cdea3ec31eb87b80b00000000000017a914c2aabf119c1825b1de66bc34e0792e37c198b5a987a00f00000000000017a9146e9e99a0b342e90e9360e26aa1a2b12ac7d1701e87881300000000000017a9149fc2952de5c6268759a4addd6f1336585de5a6b687701700000000000017a914f0bb53b2734e0f4027b25084630f4c7cb793f0d087581b00000000000017a914151a578ea0bbe3a24bf8335c4ee162643be28b4787401f00000000000017a9148f7ffde60fa425fa919ab9de3c7731fa4268151787282300000000000017a91454c45d77bccc359d07a2b17b4abfc78e8c3237b787102700000000000017a914e43197dbd28424b86c7c8823180e2b15192a96d18702204d5783a61241bdef19c3480e094cc933c91d2bde995c8c50407099184b501f4301b300000000", "NONE", "DEFAULT_CHECK_TEMPLATE_VERIFY_HASH"], ["CheckTemplateVerify Argument from Witness Stack"], [[["e8e9805801b7fb44814531de0dd498b955651b9c25a85a043d73f18970622647", 0, "0x00 0x20 0x65f15821061635e6807f06701bf0a12d8e89dcff88df5968bd0822c9dbb52f1c", 155000]], "020000000001014726627089f1733d045aa8259c1b6555b998d40dde31458144fbb7015880e9e80000000000000000000ae90300000000000017a91496e75de842d245fe846f1866f535d3d549af1eee87d00700000000000017a91443078220afb62f1dd0f13b58103c2cdea3ec31eb87b80b00000000000017a914c2aabf119c1825b1de66bc34e0792e37c198b5a987a00f00000000000017a9146e9e99a0b342e90e9360e26aa1a2b12ac7d1701e87881300000000000017a9149fc2952de5c6268759a4addd6f1336585de5a6b687701700000000000017a914f0bb53b2734e0f4027b25084630f4c7cb793f0d087581b00000000000017a914151a578ea0bbe3a24bf8335c4ee162643be28b4787401f00000000000017a9148f7ffde60fa425fa919ab9de3c7731fa4268151787282300000000000017a91454c45d77bccc359d07a2b17b4abfc78e8c3237b787102700000000000017a914e43197dbd28424b86c7c8823180e2b15192a96d18702204d5783a61241bdef19c3480e094cc933c91d2bde995c8c50407099184b501f4301b300000000", "DISCOURAGE_UPGRADABLE_NOPS", "NONE", true], ["BEGIN CTV congestion control tree level with 4 levels:"], ["CTV congestion control tree level 0"], [[["d0246d069143263bca9a2b176fcf64bd8e4975c7670ed33659b4b8f88d3e7446", 0, "0x20 0x10618b50aa1120e9e940bbea8b6d081019e38fbb9b956b0ab4f61631d05727ca OP_CHECKTEMPLATEVERIFY", 16600]], "020000000146743e8df8b8b45936d30e67c775498ebd64cf6f172b9aca3b264391066d24d000000000000000000002781e0000000000002220bceb923d731eddf09705690d6ee697d1b3d57279ad96910cfb66a8d43a638800b3781e00000000000022201210e50077518896fd1661bffc2c1e88ad6e204ec4e8755407b42a97347c1e1bb300000000", "DISCOURAGE_UPGRADABLE_NOPS", "NONE", true], ["CTV congestion control tree level 1"], [[["b69f866d47ebb75eeecfbc3b9b641f926f11035b64ff27a5a5e88b9c065bddf5", 0, "0x20 0xbceb923d731eddf09705690d6ee697d1b3d57279ad96910cfb66a8d43a638800 OP_CHECKTEMPLATEVERIFY", 7800]], "0200000001f5dd5b069c8be8a5a527ff645b03116f921f649b3bbccfee5eb7eb476d869fb600000000000000000002480d00000000000022204c683607ca7950380df10647b223f656cd73d1f7ad67b30caf60d78337f913b2b3480d0000000000002220805bddd8b95a3cf3729b62703de37a1533b11634de76aa4a18605b640f1f3208b300000000", "DISCOURAGE_UPGRADABLE_NOPS", "NONE", true], ["CTV congestion control tree level 2"], [[["7d331a33880504fa94478c9687f3f41322ec76f81edad8e72491cbb81eea4754", 0, "0x20 0x4c683607ca7950380df10647b223f656cd73d1f7ad67b30caf60d78337f913b2 OP_CHECKTEMPLATEVERIFY", 3400]], "02000000015447ea1eb8cb9124e7d8da1ef876ec2213f4f387968c4794fa040588331a337d00000000000000000002b004000000000000222084ac6e0fdbe91b09d1bf68158643ad68e0b3e64373738fb35711de0835011079b3b0040000000000002220241af26179a8e861cca473244723978127c16531f71fbcc33563c4f099651f8fb300000000", "DISCOURAGE_UPGRADABLE_NOPS", "NONE", true], ["CTV congestion control tree level 3"], [[["e630b2357e02d1611a0615ce3964c408823ce3269974bd94e57ddea96900da70", 0, "0x20 0x84ac6e0fdbe91b09d1bf68158643ad68e0b3e64373738fb35711de0835011079 OP_CHECKTEMPLATEVERIFY", 1200]], "020000000170da0069a9de7de594bd749926e33c8208c46439ce15061a61d1027e35b230e60000000000000000000264000000000000001600141ca3bdf6bd2b1fc27420316a0d13f81fcdb85cb0640000000000000016001489d611c79700d6b4ae73d853ed49b86621d5802100000000", "DISCOURAGE_UPGRADABLE_NOPS", "NONE", true], ["END"], ["BEGIN CTV congestion control tree level with 4 levels:"], ["CTV congestion control tree level 0"], [[["d0246d069143263bca9a2b176fcf64bd8e4975c7670ed33659b4b8f88d3e7446", 0, "0x20 0x10618b50aa1120e9e940bbea8b6d081019e38fbb9b956b0ab4f61631d05727ca OP_CHECKTEMPLATEVERIFY", 16600]], "020000000146743e8df8b8b45936d30e67c775498ebd64cf6f172b9aca3b264391066d24d000000000000000000002781e0000000000002220bceb923d731eddf09705690d6ee697d1b3d57279ad96910cfb66a8d43a638800b3781e00000000000022201210e50077518896fd1661bffc2c1e88ad6e204ec4e8755407b42a97347c1e1bb300000000", "NONE", "DEFAULT_CHECK_TEMPLATE_VERIFY_HASH"], ["CTV congestion control tree level 1"], [[["b69f866d47ebb75eeecfbc3b9b641f926f11035b64ff27a5a5e88b9c065bddf5", 0, "0x20 0xbceb923d731eddf09705690d6ee697d1b3d57279ad96910cfb66a8d43a638800 OP_CHECKTEMPLATEVERIFY", 7800]], "0200000001f5dd5b069c8be8a5a527ff645b03116f921f649b3bbccfee5eb7eb476d869fb600000000000000000002480d00000000000022204c683607ca7950380df10647b223f656cd73d1f7ad67b30caf60d78337f913b2b3480d0000000000002220805bddd8b95a3cf3729b62703de37a1533b11634de76aa4a18605b640f1f3208b300000000", "NONE", "DEFAULT_CHECK_TEMPLATE_VERIFY_HASH"], ["CTV congestion control tree level 2"], [[["7d331a33880504fa94478c9687f3f41322ec76f81edad8e72491cbb81eea4754", 0, "0x20 0x4c683607ca7950380df10647b223f656cd73d1f7ad67b30caf60d78337f913b2 OP_CHECKTEMPLATEVERIFY", 3400]], "02000000015447ea1eb8cb9124e7d8da1ef876ec2213f4f387968c4794fa040588331a337d00000000000000000002b004000000000000222084ac6e0fdbe91b09d1bf68158643ad68e0b3e64373738fb35711de0835011079b3b0040000000000002220241af26179a8e861cca473244723978127c16531f71fbcc33563c4f099651f8fb300000000", "NONE", "DEFAULT_CHECK_TEMPLATE_VERIFY_HASH"], ["CTV congestion control tree level 3"], [[["e630b2357e02d1611a0615ce3964c408823ce3269974bd94e57ddea96900da70", 0, "0x20 0x84ac6e0fdbe91b09d1bf68158643ad68e0b3e64373738fb35711de0835011079 OP_CHECKTEMPLATEVERIFY", 1200]], "020000000170da0069a9de7de594bd749926e33c8208c46439ce15061a61d1027e35b230e60000000000000000000264000000000000001600141ca3bdf6bd2b1fc27420316a0d13f81fcdb85cb0640000000000000016001489d611c79700d6b4ae73d853ed49b86621d5802100000000", "NONE", "DEFAULT_CHECK_TEMPLATE_VERIFY_HASH"], ["END"], ["Test CTV with a specific scriptsig"], [[["32858fe9a6348d4ee5fcfce78f6dbca0b54dff169ff4cc41439adca4e5d30746", 0, "1", 155000], ["357722dce671e5aa52abd617002baa8d5d970cef43feca3bf2d4c8b1e5d53d11", 0, "0x20 0x08a5903863a0562c0b5608521a8a77ca02e669eb01f3981eede6bf6f2f38c2c2 OP_CHECKTEMPLATEVERIFY", 155000]], "0200000002113dd5e5b1c8d4f23bcafe43ef0c975d8daa2b0017d6ab52aae571e6dc227735000000000151000000004607d3e5a4dc9a4341ccf49f16ff4db5a0bc6d8fe7fcfce54e8d34a6e98f8532000000000100000000000ae80300000000000017a9146422bb825e07ab99ab915223ac67f195a4fb761987d00700000000000017a914cc9fa001f8c9ff9dfdecf0ec1356d37c808aec2d87b80b00000000000017a914092f42f35fd05eaf816a090ad8f1adec8394132d87a00f00000000000017a9147cfd2a76093289ebabf860d3071b92756dbde1b787881300000000000017a914c3d81e1a59c256bff75c535878e1701943a9e48987701700000000000017a914029ddf1319c05ff38cd974ba99fdcf1cb4b88b9687581b00000000000017a9148c95279a9fd452ad7b1cb7a35fd08e7ff55946af87401f00000000000017a9149216fef0f965b2f1890a420aa725cb86ba47a9c087282300000000000017a9141424c24d8cd907a36310db639ec7d194c62d620087102700000000000017a9145b278b155e6dd103b4bf5ba78e4a95c16926c9bd8700000000", "DISCOURAGE_UPGRADABLE_NOPS,CLEANSTACK", "NONE", true], [[["32858fe9a6348d4ee5fcfce78f6dbca0b54dff169ff4cc41439adca4e5d30746", 0, "1", 155000], ["357722dce671e5aa52abd617002baa8d5d970cef43feca3bf2d4c8b1e5d53d11", 0, "0x20 0x08a5903863a0562c0b5608521a8a77ca02e669eb01f3981eede6bf6f2f38c2c2 OP_CHECKTEMPLATEVERIFY", 155000]], "0200000002113dd5e5b1c8d4f23bcafe43ef0c975d8daa2b0017d6ab52aae571e6dc227735000000000151000000004607d3e5a4dc9a4341ccf49f16ff4db5a0bc6d8fe7fcfce54e8d34a6e98f8532000000000100000000000ae80300000000000017a9146422bb825e07ab99ab915223ac67f195a4fb761987d00700000000000017a914cc9fa001f8c9ff9dfdecf0ec1356d37c808aec2d87b80b00000000000017a914092f42f35fd05eaf816a090ad8f1adec8394132d87a00f00000000000017a9147cfd2a76093289ebabf860d3071b92756dbde1b787881300000000000017a914c3d81e1a59c256bff75c535878e1701943a9e48987701700000000000017a914029ddf1319c05ff38cd974ba99fdcf1cb4b88b9687581b00000000000017a9148c95279a9fd452ad7b1cb7a35fd08e7ff55946af87401f00000000000017a9149216fef0f965b2f1890a420aa725cb86ba47a9c087282300000000000017a9141424c24d8cd907a36310db639ec7d194c62d620087102700000000000017a9145b278b155e6dd103b4bf5ba78e4a95c16926c9bd8700000000", "CLEANSTACK", "DEFAULT_CHECK_TEMPLATE_VERIFY_HASH"], ["Test CTV with a specific scriptsig at different index"], [[["e2f2baee9c59389b34e39742ce05debf64aaa7a00fbdab88614f4d3c133186d5", 0, "1", 155000], ["c88e4b769a9211d2bca7516dbeacf250585dc825e41e34a65607a444b97fb782", 0, "0x20 0xcc06acb181a8e9893c53c92fcfcb56fc004a360964af02cfd15b9f3321385f86 OP_CHECKTEMPLATEVERIFY", 155000]], "0200000002d58631133c4d4f6188abbd0fa0a7aa64bfde05ce4297e3349b38599ceebaf2e20000000001510000000082b77fb944a40756a6341ee425c85d5850f2acbe6d51a7bcd211929a764b8ec8000000000100000000000ae80300000000000017a914d63e77972529f4db5b32efaa4e06f66ae0b5dc0987d00700000000000017a91488b6705f8c9568c52b55ed712c257f84f64a49f587b80b00000000000017a9142be57e9a179f8d9ff8f33a788d4b54512ea9e36087a00f00000000000017a91429261b4f65796f618908de9f51669014e2e2e04f87881300000000000017a914e3a1e1d24cbba3ca9369248082988bad3ceafcfb87701700000000000017a91403801b0a9591f3b5a00a5ea60fb34dc12b4a691187581b00000000000017a91465248bc2c732db2d88db0b0d677c1514b101025b87401f00000000000017a91420021e3dc4e80c7192c1a3cd04026d22d0f8d38287282300000000000017a914df27596dbff2028791bd7692846e65d16d8fed0d87102700000000000017a9142ed128e911cab04d3277d3635f79d5e3d7e6f4c48700000000", "DISCOURAGE_UPGRADABLE_NOPS,CLEANSTACK", "NONE", true], [[["e2f2baee9c59389b34e39742ce05debf64aaa7a00fbdab88614f4d3c133186d5", 0, "1", 155000], ["c88e4b769a9211d2bca7516dbeacf250585dc825e41e34a65607a444b97fb782", 0, "0x20 0xcc06acb181a8e9893c53c92fcfcb56fc004a360964af02cfd15b9f3321385f86 OP_CHECKTEMPLATEVERIFY", 155000]], "0200000002d58631133c4d4f6188abbd0fa0a7aa64bfde05ce4297e3349b38599ceebaf2e20000000001510000000082b77fb944a40756a6341ee425c85d5850f2acbe6d51a7bcd211929a764b8ec8000000000100000000000ae80300000000000017a914d63e77972529f4db5b32efaa4e06f66ae0b5dc0987d00700000000000017a91488b6705f8c9568c52b55ed712c257f84f64a49f587b80b00000000000017a9142be57e9a179f8d9ff8f33a788d4b54512ea9e36087a00f00000000000017a91429261b4f65796f618908de9f51669014e2e2e04f87881300000000000017a914e3a1e1d24cbba3ca9369248082988bad3ceafcfb87701700000000000017a91403801b0a9591f3b5a00a5ea60fb34dc12b4a691187581b00000000000017a91465248bc2c732db2d88db0b0d677c1514b101025b87401f00000000000017a91420021e3dc4e80c7192c1a3cd04026d22d0f8d38287282300000000000017a914df27596dbff2028791bd7692846e65d16d8fed0d87102700000000000017a9142ed128e911cab04d3277d3635f79d5e3d7e6f4c48700000000", "CLEANSTACK", "DEFAULT_CHECK_TEMPLATE_VERIFY_HASH"], ["Make diffs cleaner by leaving a comment here without comma at the end"] ] ================================================ FILE: bip-0119.mediawiki ================================================
  BIP: 119
  Layer: Consensus (soft fork)
  Title: CHECKTEMPLATEVERIFY
  Authors: Jeremy Rubin 
  Status: Draft
  Type: Specification
  Assigned: 2020-01-06
  License: BSD-3-Clause
==Abstract== This BIP proposes a new opcode, OP_CHECKTEMPLATEVERIFY, to be activated as a change to the semantics of OP_NOP4. ==Summary== OP_CHECKTEMPLATEVERIFY uses opcode OP_NOP4 (0xb3) as a soft fork upgrade. OP_CHECKTEMPLATEVERIFY does the following: * There is at least one element on the stack, fail otherwise * The element on the stack is 32 bytes long, NOP otherwise * The DefaultCheckTemplateVerifyHash of the transaction at the current input index is equal to the element on the stack, fail otherwise The DefaultCheckTemplateVerifyHash commits to the serialized version, locktime, scriptSigs hash (if any non-null scriptSigs), number of inputs, sequences hash, number of outputs, outputs hash, and currently executing input index. The recommended standardness rules additionally: * Reject non-32 byte as SCRIPT_ERR_DISCOURAGE_UPGRADABLE_NOPS. ==Motivation== This BIP introduces a transaction template, a simple spending restriction that pattern matches a transaction against a hashed transaction specification. OP_CHECKTEMPLATEVERIFY reduces many of the trust, interactivity, and storage requirements inherent with the use of pre-signing in applications. For more details on applications, please see the references. ==Detailed Specification== The below code is the main logic for verifying CHECKTEMPLATEVERIFY, described in pythonic pseudocode. The canonical specification for the semantics of OP_CHECKTEMPLATEVERIFY as implemented in C++ in the context of Bitcoin Core can be seen in the reference implementation. The execution of the opcode is as follows: def execute_bip_119(self): # Before soft-fork activation / failed activation # continue to treat as NOP4 if not self.flags.script_verify_default_check_template_verify_hash: # Potentially set for node-local policy to discourage premature use if self.flags.script_verify_discourage_upgradable_nops: return self.errors_with(errors.script_err_discourage_upgradable_nops) return self.return_as_nop() # CTV always requires at least one stack argument if len(self.stack) < 1: return self.errors_with(errors.script_err_invalid_stack_operation) # CTV only verifies the hash against a 32 byte argument if len(self.stack[-1]) == 32: # Ensure the precomputed data required for anti-DoS is available, # or cache it on first use if self.context.precomputed_ctv_data == None: self.context.precomputed_ctv_data = self.context.tx.get_default_check_template_precomputed_data() # If the hashes do not match, return error if stack[-1] != self.context.tx.get_default_check_template_hash(self.context.nIn, self.context.precomputed_ctv_data): return self.errors_with(errors.script_err_template_mismatch) return self.return_as_nop() # future upgrade can add semantics for this opcode with different length args # so discourage use when applicable if self.flags.script_verify_discourage_upgradable_nops: return self.errors_with(errors.script_err_discourage_upgradable_nops) else: return self.return_as_nop() The computation of this hash can be implemented as specified below (where self is the transaction type). Care must be taken that in any validation context, the precomputed data must be initialized to prevent Denial-of-Service attacks. Any implementation *must* cache these parts of the hash computation to avoid quadratic hashing DoS. All variable length computations must be precomputed including hashes of the scriptsigs, sequences, and outputs. See the section "Denial of Service and Validation Costs" below. This is not a performance optimization. def ser_compact_size(l): r = b"" if l < 253: # Serialize as unsigned char r = struct.pack("B", l) elif l < 0x10000: # Serialize as unsigned char 253 followed by unsigned 2 byte integer (little endian) r = struct.pack(" A PayToBareDefaultCheckTemplateVerifyHash output matches the following template: # Extra-fast test for pay-to-basic-standard-template CScripts: def is_pay_to_bare_default_check_template_verify_hash(self): return len(self) == 34 and self[0] == 0x20 and self[-1] == OP_CHECKTEMPLATEVERIFY ==Deployment== Activation logic is elided from this BIP and is more appropriately discussed elsewhere. Until BIP-119 reaches ACTIVE state and the SCRIPT_VERIFY_DEFAULT_CHECK_TEMPLATE_VERIFY_HASH flag is enforced, node implementations should (are recommended to) execute a NOP4 as SCRIPT_ERR_DISCOURAGE_UPGRADABLE_NOPS (to deny entry to the mempool) for policy and must evaluate as a NOP for consensus (during block validation). In order to facilitate using CHECKTEMPLATEVERIFY, the common case of a PayToBareDefaultCheckTemplateVerifyHash with no scriptSig data may (is recommended to) be made standard to permit relaying. Future bare scripts may be standardized later as policy changes at the preference of the implementer. ==Reference Implementation== A reference implementation and tests are available here in the PR to Bitcoin Core https://github.com/bitcoin/bitcoin/pull/21702. It is not ideal to link to a PR, as it may be rebased and changed, but it is the best place to find the current implementation and review comments of others. A recent commit hash in that PR including tests and vectors can be found here https://github.com/jeremyrubin/bitcoin/commit/3109df5616796282786706738994a5b97b8a5a38. Once the PR is merged, this BIP should be updated to point to the specific code released. Test vectors are available in [/bip-0119/vectors the bip-0119/vectors directory] for checking compatibility with the reference implementation and BIP. ==Rationale== OP_CHECKTEMPLATEVERIFY's design is a small code change and simple to analyze. It is compatible with future upgrades if new template types are required for more complex but demonstrably safe use cases. Below we'll discuss the rules one-by-one: ====The DefaultCheckTemplateVerifyHash of the transaction at the current input index matches the top of the stack==== The set of data committed to is a superset of data which can impact the TXID of the transaction, other than the inputs. This ensures that for a given known input, the TXIDs can also be known ahead of time. Otherwise, CHECKTEMPLATEVERIFY would not be usable for Batched Channel Creation constructions as the redemption TXID could be malleated and pre-signed transactions invalidated, unless the channels are built using an LN-Symmetry-like protocol. Note that there may be other types of pre-signed contracts that may or may not be able to use LN-Symmetry-like constructs, therefore making TXIDs predictable makes CTV more composable with arbitrary sub-protocols. =====Committing to the version and locktime===== Were these values not committed, it would be possible to delay the spending of an output arbitrarily as well as possible to change the TXID. Committing these values, rather than restricting them to specific values, is more flexible as it permits users of CHECKTEMPLATEVERIFY to set the version and locktime as they please. =====Committing to the ScriptSigs Hash===== The scriptsig in a segwit transaction must be exactly empty, unless it is a P2SH segwit transaction in which case it must be only the exact redeemscript. P2SH is incompatible (unless the P2SH hash is broken) with CHECKTEMPLATEVERIFY because the template hash must commit to the ScriptSig, which must contain the redeemscript, which is a hash cycle. To prevent malleability when not using a segwit input, we also commit to the scriptsig. This makes it possible to use a 2 input CHECKTEMPLATEVERIFY with a legacy pre-signed spend, as long as the exact scriptsig for the legacy output is committed. This is more robust than simply disallowing any scriptSig to be set with CHECKTEMPLATEVERIFY. If no scriptSigs are set in the transaction, there is no purpose in hashing the data or including it in the DefaultCheckTemplateVerifyHash, so we elide it. It is expected to be common that no scriptSigs will be set as segwit mandates that the scriptSig must be empty (to avoid malleability). We commit to the hash rather than the values themselves as this is already precomputed for each transaction to optimize SIGHASH_ALL signatures. Committing to the hash additionally makes it simpler to construct DefaultCheckTemplateVerifyHash safely and unambiguously from script. =====Committing to the number of inputs===== If we allow more than one input to be spent in the transaction then it would be possible for two outputs to request payment to the same set of outputs, resulting in half the intended payments being discarded, the "half-spend" problem. Furthermore, the restriction on which inputs can be co-spent is critical for payments-channel constructs where a stable TXID is a requirement (updates would need to be signed on all combinations of inputs). However, there are legitimate use cases for allowing multiple inputs. For example: Script paths: Path A: <+24 hours> OP_CHECKSEQUENCEVERIFY OP_CHECKTEMPLATEVERIFY Path B: OP_CHECKTEMPLATEVERIFY In this case, there are 24 hours for the output to, with the addition of a second output, pay Bob 2 BTC. If 24 hours lapses, then Alice may redeem her 1 BTC from the contract. Both input UTXOs may have the exact same Path B, or only one. The issue with these constructs is that there are N! orders that the inputs can be ordered in and it's not generally possible to restrict the ordering. CHECKTEMPLATEVERIFY allows for users to guarantee the exact number of inputs being spent. In general, using CHECKTEMPLATEVERIFY with more than one input is difficult and exposes subtle issues, so multiple inputs should not be used except in specific applications. In principle, committing to the Sequences Hash (below) implicitly commits to the number of inputs, making this field strictly redundant. However, separately committing to this number makes it easier to construct DefaultCheckTemplateVerifyHash from script. We treat the number of inputs as a `uint32_t` because Bitcoin's consensus decoding logic limits vectors to `MAX_SIZE=33554432` and that is larger than `uint16_t` and smaller than `uint32_t`. 32 bits is also friendly for manipulation using Bitcoin's current math opcodes, should `OP_CAT` be added. Note that the max inputs in a block is further restricted by the block size to around 25,000, which would fit into a `uint16_t`, but that is an unnecessary abstraction leak. =====Committing to the Sequences Hash===== If we don't commit to the sequences, then the TXID can be malleated. This also allows us to enforce a relative sequence lock without an OP_CSV. It is insufficient to just pair CHECKTEMPLATEVERIFY with OP_CSV because OP_CSV enforces a minimum nSequence value, not a literal value. We commit to the hash rather than the values themselves as this is already precomputed for each transaction to optimize SIGHASH_ALL signatures. Committing to the hash additionally makes it simpler to construct DefaultCheckTemplateVerifyHash safely and unambiguously from script. =====Committing to the Number of Outputs===== In principle, committing to the Outputs Hash (below) implicitly commits to the number of outputs, making this field strictly redundant. However, separately committing to this number makes it easier to construct DefaultCheckTemplateVerifyHash from script. We treat the number of outputs as a `uint32_t` because a `COutpoint` index is a `uint32_t`. Further, Bitcoin's consensus decoding logic limits vectors to `MAX_SIZE=33554432` and that is larger than `uint16_t` and smaller than `uint32_t`. 32 bits is also friendly for manipulation using Bitcoin's current math opcodes, should `OP_CAT` be added. =====Committing to the outputs hash===== This ensures that spending the UTXO is guaranteed to create the exact outputs requested. We commit to the hash rather than the values themselves as this is already precomputed for each transaction to optimize SIGHASH_ALL signatures. Committing to the hash additionally makes it simpler to construct DefaultCheckTemplateVerifyHash safely and unambiguously from script. =====Committing to the current input's index===== Committing to the currently executing input's index is not strictly needed for anti-malleability, however it does restrict the input orderings eliminating a source of malleability for protocol designers. However, committing to the index eliminates key-reuse vulnerability to the half-spend problem. As CHECKTEMPLATEVERIFY scripts commit to being spent at particular index, reused instances of these scripts cannot be spent at the same index, which implies that they cannot be spent in the same transaction. This makes it safer to design wallet vault contracts without half-spend vulnerabilities. Committing to the current index doesn't prevent one from expressing a CHECKTEMPLATEVERIFY which can be spent at multiple indices. In current script, the CHECKTEMPLATEVERIFY operation can be wrapped in an OP_IF for each index (or Tapscript branches in the future). If OP_CAT or OP_SHA256STREAM are added to Bitcoin, the index may simply be passed in by the witness before hashing. =====Committing to Values by Hash===== Committing to values by hash makes it easier and more efficient to construct a DefaultCheckTemplateVerifyHash from script. Fields which are not intended to be set may be committed to by hash without incurring O(n) overhead to re-hash. Furthermore, if OP_SHA256STREAM is added in the future, it may be possible to write a script which allows adding a single output to a list of outputs without incurring O(n) overhead by committing to a hash midstate in the script. =====Using SHA256===== SHA256 is a 32 byte hash which meets Bitcoin's security standards and is available already inside of Bitcoin Script for programmatic creation of template programs. RIPEMD160, a 20 byte hash, might also be a viable hash in some contexts and has some benefits. For fee efficiency, RIPEMD160 saves 12 bytes. However, RIPEMD160 was not chosen for BIP-119 because it introduces risks around the verification of programs created by third parties to be subject to a [birthday-attack https://bitcoin.stackexchange.com/questions/54841/birthday-attack-on-p2sh] on transaction preimages. =====Using Non-Tagged Hashes===== The Taproot/Schnorr BIPs use Tagged Hashes (`SHA256(SHA256(tag)||SHA256(tag)||msg)`) to prevent taproot leaves, branches, tweaks, and signatures from overlapping in a way that might introduce a security [vulnerability https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2018-June/016091.html]. OP_CHECKTEMPLATEVERIFY is not subject to this sort of vulnerability as the hashes are effectively tagged externally, that is, by OP_CHECKTEMPLATEVERIFY itself and therefore cannot be confused for another hash. It would be a conservative design decision to make it a tagged hash even if there was no obvious benefit and no cost. However, in the future, if OP_CAT were to be introduced to Bitcoin, it would make programs which dynamically build OP_CHECKTEMPLATEVERIFY hashes less space-efficient. Therefore, bare untagged hashes are used in BIP-119. =====The Ordering of Fields===== Strictly speaking, the ordering of fields is insignificant. However, with a carefully selected order, the efficiency of future scripts (e.g., those using a OP_CAT or OP_SHA256STREAM) may be improved (as described in the Future Upgrades section). In particular, the order is selected in order of least likely to change to most. #nVersion #nLockTime #scriptSig hash (maybe!) #input count #sequences hash #output count #outputs hash #input index Several fields are infrequently modified. nVersion should change infrequently. nLockTime should generally be fixed to 0 (in the case of a payment tree, only the *first* lock time is needed to prevent fee-sniping the root). scriptSig hash should generally not be set at all. Since there are many possible sequences hash for a given input count, the input count comes before the sequences hash. Since there are many possible outputs hashes for a given out count, the output count comes before the outputs hash. Since we're generally using a single input to many output design, we're more likely to modify the outputs hash than the inputs hash. We usually have just a single input on a CHECKTEMPLATEVERIFY script, which would suggest that it does not make sense for input index to be the last field. However, given the desirability of being able to express a "don't care" index easily (e.g., for decentralized kickstarter-type transactions), this value is placed last. ===Design Tradeoffs and Risks=== CHECKTEMPLATEVERIFY's design limits script authors to relatively precise template matching. The structure of CHECKTEMPLATEVERIFY template is such that most of the transaction details must be known exactly at the time of construction, with the exception of the inputs. CHECKTEMPLATEVERIFY can be nested -- that is, a transaction that is created by spending an output with a ` OP_CHECKTEMPLATEVERIFY` restriction may create outputs with ` OP_CHECKTEMPLATEVERIFY` restrictions. This expansion is inherently finite, as re-creating an output with a script containing the hash `` from a transaction spending an output with the hash `` creates a hash cycle. This can also be thought of as each template hash `` having a "path height" of the longest chain of possible unbroken `OP_CHECKTEMPLATEVERIFY` verifying transactions, and the path height is strictly decreasing. Furthermore, templates are restricted to be spendable as a known number of inputs only and at a specific input index, preventing unintentional introduction of the 'half spend' problem. Templates, as restricted as they are, bear some risks. ====Denial of Service and Validation Costs==== CTV is designed to be able to be validated very cheaply without introducing DoS, either by checking a precomputed hash or computing a hash of fixed length arguments (some of which may be cached from more expensive computations). In particular, CTV requires that clients cache the computation of a hash over all the scriptSigs, sequences, and outputs. Before CTV, the hash of the scriptSigs was not required. CTV also requires that the presence of any non-empty scriptSig be hashed, but this can be handled as a part of the scriptSigs hash. As such, evaluating a CTV hash during consensus is always O(1) computation when the caches are available. These caches usually must be available due to similar issues in CHECKSIG behavior. Computing the caches is O(T) (the size of the transaction). An example of a script that could experience a DoS issue without caching is: CTV CTV CTV... CTV Such a script would cause the interpreter to compute hashes (supposing N CTV's) over O(N*T) data. If the scriptSigs non-nullity is not cached, then the O(T) transaction could be scanned over O(N) times as well (although cheaper than hashing, still a DoS). As such, CTV caches hashes and computations over all variable length fields in a transaction. For CTV, the Denial-of-Service exposure and validation costs are relatively clear. Implementers must be careful to correctly code CTV to make use of existing caches and cache the (new for CTV) computations over scriptSigs. Other more flexible proposals may have a more difficult time solving DoS issues as more complex template computations may be less cacheable and expose issues around quadratic hashing, it is a tradeoff CTV makes in favor of cheap and secure validation at the expense of flexibility. For example, if CTV allowed the hashing only select outputs by a bitmask, caching of all combinations of outputs would not be possible and would cause a quadratic hashing DoS vulnerability. ====Permanently Unspendable Outputs==== The preimage argument passed to CHECKTEMPLATEVERIFY may be unknown or otherwise unsatisfiable. However, requiring knowledge that an address is spendable from is incompatible with sender's ability to spend to any address (especially, OP_RETURN). If a sender needs to know the template can be spent from before sending, they may request a signature of a provably non-transaction challenge string from the leaves of the CHECKTEMPLATEVERIFY tree. ====Forwarding Addresses==== Key-reuse with CHECKTEMPLATEVERIFY may be used as a form of "forwarding address contract". A forwarding address is an address which can automatically execute in a predefined way. For example, an exchange's hot wallet might use an address which can automatically be moved to a cold storage address after a relative timeout. The issue is that reusing addresses in this way can lead to loss of funds. Suppose one creates a template address which forwards 1 BTC to cold storage. Creating an output to this address with less than 1 BTC will be frozen permanently. Paying more than 1 BTC will lead to the funds in excess of 1BTC to be paid as a large miner fee. CHECKTEMPLATEVERIFY could commit to the exact amount of bitcoin provided by the inputs/amount of fee paid, but as this is a user error and not a malleability issue this is not done. Future soft-forks could introduce opcodes which allow conditionalizing which template or script branches may be used based on inspecting the amount of funds available in a transaction As a general best practice, it is incumbent on Bitcoin users to not reuse any address unless you are certain that the address is acceptable for the payment attempted. This limitation and risk is not unique to CHECKTEMPLATEVERIFY. For example, atomic swap scripts are single use once the hash is revealed. Future Taproot scripts may contain many logical branches that would be unsafe for being spent to multiple times (e.g., a Hash Time Lock branch should be instantiated with unique hashes each time it is used). Keys which have signed a SIGHASH_ANYPREVOUT transaction can similarly become reuse-unsafe. Because CHECKTEMPLATEVERIFY commits to the input index currently being spent, reused-keys are guaranteed to execute in separate transactions which reduces the risk of "half-spend" type issues. ====NOP-Default and Recommended Standardness Rules==== If the argument length is not exactly 32, CHECKTEMPLATEVERIFY treats it as a NOP during consensus validation. Implementations are recommended to fail in such circumstances during non-consensus relaying and mempool validation. In particular, making an invalid-length argument a failure aids future soft-forks upgrades to be able to rely on the tighter standard restrictions to safely loosen the restrictions for standardness while tightening them for consensus with the upgrade's rules. The standardness rules may lead an unscrupulous script developer to accidentally rely on the stricter standardness rules to be enforced during consensus. Should that developer submit a transaction directly to the network relying on standardness rejection, a standardness-invalid but consensus-valid transaction may be caused, leading to a potential loss of funds. ====Feature Redundancy==== There are other opcodes that, if implemented, could make the CHECKTEMPLATEVERIFY's functionality redundant. However, given CHECKTEMPLATEVERIFY's simple semantics and low on chain cost it's likely that it would continue to be favored even if redundant with other capabilities. Or, in the case of opcodes such as OP_VAULT, OP_CHECKCONTRACTVERIFY, and OP_TXHASH, OP_CHECKTEMPLATEVERIFY is a part of their currently proposed implementations. More powerful opcodes, like OP_COV proposed in MES16 or OP_TXHASH, would also bring some benefits in terms of improving the ability to pay fees endogenously rather than relying on exogenous child-pays-for-parent or other fee paying mechanisms such as transaction sponsors. However, these features come at substantially increased complexity and room for behaviors unintended by the application developer. Alternatively, SIGHASH_ANYPREVOUTANYSCRIPT can be used to implement something similar to templates, via a scriptPubKey like: OP_CHECKSIG SIGHASH_ANYPREVOUTANYSCRIPT capabilities above are similar to what CHECKTEMPLATEVERIFY offers. The key functional difference between SIGHASH_ANYPREVOUTANYSCRIPT and OP_CHECKTEMPLATEVERIFY is that OP_CHECKTEMPLATEVERIFY restricts the number of additional inputs and precludes dynamically determined change outputs while SIGHASH_ANYPREVOUTANYSCRIPT can be combined with SIGHASH_SINGLE or SIGHASH_ANYONECANPAY. For the additional inputs, OP_CHECKTEMPLATEVERIFY also commits to the scriptsig and sequence, which allows for specifying specific P2SH scripts (or segwit v0 P2SH) which have some use cases. Furthermore, CHECKTEMPLATEVERIFY has benefits in terms of script size (depending on choice of PK, SIGHASH_ANYPREVOUTANYSCRIPT may use about 2x-3x the bytes) and verification speed, as OP_CHECKTEMPLATEVERIFY requires only hash computation rather than signature operations. This can be significant when constructing large payment trees or programmatic compilations. CHECKTEMPLATEVERIFY also has a feature-wise benefit in that it provides a robust pathway for future template upgrades, as proposed in OP_TXHASH. OP_CHECKSIGFROMSTACKVERIFY along with OP_CAT may also be used to emulate CHECKTEMPLATEVERIFY. However such constructions are more complicated to implement in application scripts than CHECKTEMPLATEVERIFY, and encumber additional verification overhead absent from CHECKTEMPLATEVERIFY. Given the simplicity of this approach to implement and analyze, and the benefits realizable by user applications, CHECKTEMPLATEVERIFY's single template based approach is proposed in lieu of a generalized system for specifying transactions in script. ====Future Upgrades==== This section describes updates to OP_CHECKTEMPLATEVERIFY that are possible in the future as well as synergies with other possible upgrades. =====CHECKTEMPLATEVERIFY Versions===== OP_CHECKTEMPLATEVERIFY currently only verifies properties of 32 byte arguments. In the future, meaning could be ascribed to other length arguments. For example, a 33-byte argument could just the last byte as a control program. In that case, DefaultCheckTemplateVerifyHash could be computed when the flag byte is set to CTVHASH_ALL. Other programs could be added similar to a SIGHASH_TYPE. For example, CTVHASH_GROUP could read data from the Taproot Annex for compatibility with SIGHASH_GROUP type proposals and allow dynamic malleability of which indexes get hashed for bundling. The work done for the OP_TXHASH pre-BIP details one approach to upgrading the OP_CHECKTEMPLATEVERIFY semantics. =====OP_CHECKSIGFROMSTACKVERIFY===== Were both OP_CHECKTEMPLATEVERIFY and OP_CHECKSIGFROMSTACKVERIFY to be added to Bitcoin, it would be possible to implement a variant of LN-Symmetry's floating transactions using the following script: witness(S+n): program(S): OP_CHECKTEMPLATEVERIFY OP_CHECKSIGFROMSTACKVERIFY OP_CHECKLOCKTIMEVERIFY Compared to SIGHASH_ANYPREVOUTANYSCRIPT, because OP_CHECKTEMPLATEVERIFY does not allow something similar to SIGHASH_ANYONECANPAY or SIGHASH_SINGLE, protocol implementers might sign transactions with Ephemeral Anchors or additional Inputs for paying fees or an alternative such as transaction sponsors might be considered. Note that this use of OP_CHECKSIGFROMSTACKVERIFY and OP_CHECKTEMPLATEVERIFY, without the ` OP_CHECKLOCKTIMEVERIFY` ratchet, enables a form of self-reproducing automata address with a one-time-trusted-setup, albeit with limited utility given the specifics of OP_CHECKTEMPLATEVERIFY's DefaultCheckTemplateVerifyHash. In comparison, SIGHASH_ANYPREVOUT enables a more powerful self-reproducing automata (colloquially called SpookChains), that uses a variety of combinations of SIGHASH flags to be able to restrict state transitions based on amount. =====OP_AMOUNTVERIFY===== An opcode which verifies the exact amount that is being spent in the transaction, the amount paid as fees, or made available in a given output could be used to make safer OP_CHECKTEMPLATEVERIFY addresses. For instance, if the OP_CHECKTEMPLATEVERIFY program P expects exactly S satoshis, sending S-1 satoshis would result in a frozen UTXO and sending S+n satoshis would result in n satoshis being paid to fee. A range check could restrict the program to only apply for expected values and default to a keypath otherwise, e.g.: IF OP_AMOUNTVERIFY OP_GREATER CHECKSIG ELSE OP_CHECKTEMPLATEVERIFY =====OP_CAT/OP_SHA256STREAM===== OP_CHECKTEMPLATEVERIFY is (as described in the Ordering of Fields section) efficient for specifying transactions dynamically from script should Bitcoin get enhanced data manipulation opcodes. As an example, the following code checks an input index argument and concatenates it to the template and checks the template matches the transaction. OP_SIZE 4 OP_EQUALVERIFY OP_SWAP OP_CAT OP_SHA256 OP_CHECKTEMPLATEVERIFY Note that were OP_CAT to be introduced with a size limit, e.g. 520 bytes, one would be limited to use it to introspect transactions with 12 inputs and 12 outputs (depending on script type). == Backwards Compatibility == OP_CHECKTEMPLATEVERIFY replaces a OP_NOP4 with stricter verification semantics. Therefore, scripts which previously were valid will cease to be valid with this change. Stricter verification semantics for an OP_NOP are a soft fork, so existing software will be fully functional without upgrade except for mining and block validation. Similar soft forks for OP_CHECKSEQUENCEVERIFY and OP_CHECKLOCKTIMEVERIFY (see BIP-0065 and BIP-0112) have similarly changed OP_NOP semantics without introducing compatibility issues. In contrast to previous forks, OP_CHECKTEMPLATEVERIFY's reference implementation does not allow transactions with spending scripts using it to be accepted to the mempool or relayed under standard policy until the new rule is active. Other implementations are recommended to follow this rule as well, but not required. Older wallet software will be able to accept spends from OP_CHECKTEMPLATEVERIFY outputs, but will require an upgrade in order to treat PayToBareDefaultCheckTemplateVerifyHash chains with a confirmed ancestor as being "trusted" (i.e., eligible for spending before the transaction is confirmed). Backports of OP_CHECKTEMPLATEVERIFY can be trivially prepared (see the reference implementation) for older node versions that can be patched but not upgraded to a newer major release. == Script Compatibility == OP_CHECKTEMPLATEVERIFY is made available in all script versions. Application developers should note that P2SH and P2SH Segwit, which reveal the program in the scriptSig, may not use ` CTV` like fragments in their program as the scriptSig commitment creates a hash cycle. == References == *[https://utxos.org utxos.org informational site] *[https://covenants.info covenant informational site] *[https://learn.sapio-lang.org Sapio Bitcoin smart contract language] *[https://rubin.io/advent21 27 Blog Posts on building smart contracts with Sapio and CTV, including examples described here.] *[https://www.youtube.com/watch?v=YxsjdIl0034&t=2451 Scaling Bitcoin Presentation] *[https://bitcoinops.org/en/newsletters/2019/05/29/ Optech Newsletter Covering OP_CHECKOUTPUTSHASHVERIFY] *[https://rubin.io/public/pdfs/multi-txn-contracts.pdf Structuring Multi Transaction Contracts in Bitcoin] *[https://github.com/jeremyrubin/lazuli Lazuli Notes (ECDSA based N-of-N Signatures for Certified Post-Dated UTXOs)] *[https://web.archive.org/web/20220203124718/https://fc16.ifca.ai/bitcoin/papers/MES16.pdf Bitcoin Covenants] *[https://bitcointalk.org/index.php?topic=278122.0 CoinCovenants using SCIP signatures, an amusingly bad idea.] *[https://fc17.ifca.ai/bitcoin/papers/bitcoin17-final28.pdf Enhancing Bitcoin Transactions with Covenants] *[https://github.com/jamesob/simple-ctv-vault Simple CTV Vaults] *[https://github.com/kanzure/python-vaults Python Vaults] *[https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2022-January/019808.html CTV Dramatically Improves DLCs] *[https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2022-April/020225.html Calculus of Covenants] *[https://rubin.io/bitcoin/2021/12/10/advent-13/ Payment Pools with CTV] *[https://rubin.io/bitcoin/2021/12/11/advent-14/ Channels with CTV] *[https://rubin.io/bitcoin/2021/12/09/advent-12/ Congestion Control with CTV] *[https://rubin.io/bitcoin/2021/12/07/advent-10/ Building Vaults on Bitcoin] *[https://arkdev.info/ (Ark Labs) Ark Documentation] *[https://docs.second.tech/protocol/intro/ (Second) Ark Documentation] *[https://rubin.io/bitcoin/2022/09/14/drivechain-apo/ SpookChains] *[https://github.com/bitcoin/bips/pull/1500 OP_TXHASH] ===Note on Similar Alternatives=== An earlier version of CHECKTEMPLATEVERIFY, CHECKOUTPUTSHASHVERIFY, is withdrawn in favor of CHECKTEMPLATEVERIFY. CHECKOUTPUTSHASHVERIFY did not commit to the version or lock time and was thus insecure. CHECKTEMPLATEVERIFY could also be implemented as an extension to Taproot, and was proposed this way earlier. However, particular applications may want to use OP_CHECKTEMPLATEVERIFY in bare legacy scripts to maximize efficiency. CHECKTEMPLATEVERIFY has also been previously referred to as OP_SECURETHEBAG, which is mentioned here to aid in searching and referencing discussion on this BIP. ==Copyright== This document is licensed under the 3-clause BSD license. ================================================ FILE: bip-0120.mediawiki ================================================
  BIP: 120
  Layer: Applications
  Title: Proof of Payment
  Authors: Kalle Rosenbaum 
  Status: Closed
  Type: Specification
  Assigned: 2015-07-28
== Abstract == This BIP describes a system called Proof of Payment, PoP. It is used to prove that a wallet has the credentials that were used to sign a previously generated transaction. Or simply put, it lets you prove that you have made a payment. == Motivation == There are several scenarios in which it would be useful to prove that you have paid for something. For example: * A pre-paid hotel room where your PoP functions as a key to the door. * An online video rental service where you pay for a video and watch it on any device. * An ad-sign where you pay in advance for e.g. 2 weeks exclusivity. During this period you can upload new content to the sign whenever you like using PoP. * Log in to a pay site using a PoP. * A parking lot you pay for monthly and the car authenticates itself using PoP. * A lottery where all participants pay to the same address, and the winner is selected among the transactions to that address. You exchange the prize for a PoP for the winning transaction. With Proof of Payment, these use cases can be achieved without any personal information (user name, password, e-mail address, etc) being involved. == Rationale == Desirable properties: # A PoP should be generated on demand. # It should only be usable once to avoid issues due to theft. # It should be able to create a PoP for any payment, regardless of script type (P2SH, P2PKH, etc.). # It should prove that you have enough credentials to unlock all the inputs of the proven transaction. # It should be easy to implement by wallets and servers to ease adoption. Current methods of proving a payment: * In BIP0070, the PaymentRequest together with the transactions fulfilling the request makes some sort of proof. However, it does not meet 1, 2 or 4 and it obviously only meets 3 if the payment is made through BIP0070. Also, there's no standard way to request/provide the proof. If standardized it would probably meet 5. * Signing messages, chosen by the server, with the private keys used to sign the transaction. This could meet 1 and 2 but probably not 3. This is not standardized either. 4 Could be met if designed so. If an input script type is P2SH, any satisfying script should do, just as if it was a payment. For M-of-N multisig scripts, that would mean that any set of M keys should be sufficient, not necessarily the same set of M keys that signed the transaction. This is important because strictly demanding the same set of M keys would defeat the purpose of a multisig address. == Specification == === Data structure === A proof of payment for a transaction T, here called PoP(T), is used to prove that one has ownership of the credentials needed to unlock all the inputs of T. It has the exact same structure as a bitcoin transaction with the same inputs as T and in the same order as in T, but with each sequence number set to 0. There is exactly one output, here called the pop output, with value 0. The pop output must have the following format: OP_RETURN {| ! Field !! Size [B] !! Description |- | <version> || 2 || Version, little endian, currently 0x01 0x00 |- | <txid> || 32 || The transaction to prove |- | <nonce> || 6 || Random data |} The lock_time of the PoP must be set to 499999999 to prevent the PoP from being included in a block, should it appear on the bitcoin p2p network. This is also the reason for setting the sequence numbers to 0, since sequence number of ffffffff would make lock_time ineffective. This specification demands that all input sequence numbers are 0, not just one of them, which would be sufficient to make lock_time effective. This is for simplicity reasons. An illustration of the PoP data structure and its original payment is shown below.
  T
 +------------------------------------------------+
 |inputs                | outputs                 |
 |       Value,Sequence | Value,Script            |
 +------------------------------------------------+
 |input0 1,ffffffff     | 0,pay to A              |
 |input1 3,ffffffff     | 2,OP_RETURN  |
 |input2 4,ffffffff     | 1,pay to B              |
 |                      | 4,pay to C              |
 +------------------------------------------------+

  PoP(T)
 +-------------------------------------------------------------+
 | inputs               | outputs                              |
 |       Value,Sequence | Value,Script                         |
 +-------------------------------------------------------------+
 |input0 1,00000000     | 0,OP_RETURN    |
 |input1 3,00000000     |                                      |
 |input2 4,00000000     |                                      |
 +-------------------------------------------------------------+
 | lock_time=499999999                                         |
 +-------------------------------------------------------------+
The PoP is signed using the same signing process that is used for bitcoin transactions. The purpose of the nonce is to make it harder to use a stolen PoP; Once the PoP has reached the server, that PoP is useless since the server will generate a new nonce for every PoP request. === Process === # A proof of payment request is sent from the server to the wallet. The PoP request contains: ## a random nonce ## a destination where to send the PoP, for example a https URL ## data hinting the wallet which transaction to create a proof for. For example: ##* txid, if known by the server ##* PaymentRequest.PaymentDetails.merchant_data (in case of a BIP0070 payment) ##* amount, label, message or other information from a BIP0021 URI # The wallet identifies a transaction T, if possible. Otherwise it asks the user to select among the ones that match the hints in 1.iii. # The wallet creates an unsigned PoP (UPoP) for T, and asks the user to sign it. # The user confirms # The UPoP(T) is signed by the wallet, creating PoP(T). # The PoP is sent to the destination in 1.ii. # The server receiving the PoP validates it and responds with “valid” or “invalid”. # The wallet displays the response in some way to the user. '''Remarks:''' * The method of transferring the PoP request at step 1 is not specified here. Instead that is specified in separate specifications, see BIP0121. * The nonce must be randomly generated by the server for every new PoP request. === Validating a PoP === The server needs to validate the PoP and reply with "valid" or "invalid". That process is outlined below. If any step fails, the validation is aborted and "invalid" is returned: # Check the format of the PoP. It must pass normal transaction checks, except that the inputs may already be spent. # Check that lock_time is 499999999. # Check that there is exactly one output. This output must have value 0 and conform to the OP_RETURN output format outlined above. # Check that the nonce is the same as the one requested. # Check that the inputs of the PoP are exactly the same as in transaction T, except that the sequence numbers must all be 0. The ordering of the inputs must also be the same as in T. # Run the scripts of all the inputs. All scripts must return true. # Check that the txid in the PoP output is the transaction you actually want proof for. If you don’t know exactly what transaction you want proof for, check that the transaction actually pays for the product/service you deliver. # Return "valid". == Security considerations == * Someone can intercept the PoP-request and change any parameter in it. These can be mitigated by using secure connections. Examples of tampered parameters: ** Pop destination - Stealing your PoP. ** label - Trick you to sign an unintended pop or set a label that your wallet doesn't have any record for, resulting in a broken service. Always check the PoP before signing. ** nonce - Your pop will not validate on server. * Someone can steal a PoP, for example by tampering with the PoP request, and try to use the service hoping to get a matching nonce. Probability per try: 1/(2^48). The server should have a mechanism for detecting a brute force attack of this kind, or at least slow down the process by delaying the PoP request by some 100 ms or so. * Even if a wallet has no funds it might still be valuable as a generator for PoPs. This makes it important to keep the security of the wallet after it has been emptied. * Transaction malleability may cause the server to have a different transaction id for a payment than the client's wallet. In that case the wallet will not be able to prove the transaction to the server. Wallets should not rely on the transaction id of the outgoing transaction. Instead it should listen for the transaction on the network and put that in its list of transactions. == Reference implementation == [https://github.com/kallerosenbaum/poppoc PoP Demo server on GitHub] [https://github.com/kallerosenbaum/wallet PoP-enabled Mycelium fork on GitHub] == References == [https://github.com/bitcoin/bips/blob/master/bip-0021.mediawiki BIP0021]: URI Scheme [https://github.com/bitcoin/bips/blob/master/bip-0070.mediawiki BIP0070]: Payment Protocol [https://github.com/bitcoin/bips/blob/master/bip-0121.mediawiki BIP0121]: Proof of Payment URI scheme ================================================ FILE: bip-0121.mediawiki ================================================
  BIP: 121
  Layer: Applications
  Title: Proof of Payment URI scheme
  Authors: Kalle Rosenbaum 
  Status: Closed
  Type: Specification
  Assigned: 2015-07-27
== Abstract == This is a proposal for a URI scheme to be used in the Proof of Payment process. == Motivation == To make a Proof of Payment, the party that wants the proof needs to transfer a Proof of Payment request to the wallet software of the other party. To facilitate that transfer, a new URI scheme representing the PoP request is proposed. This URI can then be encoded in QR images or be sent over NFC in order to transfer it to the wallet. == Specification == The specification is the same as BIP0021, with the following differences: * The URI scheme is btcpop instead of bitcoin * The path component, i.e. the address part, is always empty. * A mandatory p parameter whose value contains the destination for the PoP. This could for example be a https: URL or a mailto: URI. * A mandatory n parameter representing the nonce, base58 encoded. * An optional txid parameter containing the Base58 encoded hash of the transaction to prove. Just as in BIP0021, elements of the query component may contain characters outside the valid range. These must first be encoded according to UTF-8, and then each octet of the corresponding UTF-8 sequence must be percent-encoded as described in RFC 3986. All parameters except p and n are hints to the wallet on which transaction to create a PoP for. The extensibility of BIP0021 applies to this scheme as well. For example, a date parameter or a toaddr parameter might be useful. req-* parameters are also allowed and obey the same rules as in BIP0021, clients not supporting a req-* parameter must consider the URI invalid. === Keep URIs short === Implementations should keep the URIs as short as possible. This is because it makes QR decoding more stable. A camera with a scratched lens or low resolution may run into problems scanning huge QR codes. This is why the txid parameter is encoded in Base58 instead of the classic hex encoded string. We get away with 44 characters instead of 64. Also, the nonce parameter is Base58 encoded for the same reason. == Interpretation == === Transaction hints === The wallet processing the URI must use the hints in the PoP request to filter its transaction set. The label, amount and message parameters must, if present in the URI, exactly match the data associated with the original payment according to the following table: {| | btcpop: URI parameter || bitcoin: URI parameter || BIP70 PaymentDetails data |- | label || label || memo |- | amount || amount || sum of outputs.amount |- | message || message || - |} The txid parameter value must match the transaction hash of the payment. After filtering, the resulting transaction set is displayed to the user who selects one of them to prove. An implementation could also automatically select a transaction in the filtered set, but there must still be a way for the user to select freely among the matching transactions. If the filtered set is empty, no transaction fits the hints and a message about that is presented to the user. If the filtered set contains exactly one transaction, which is preferable, that transaction can be automatically selected. As a fallback, there must also be a way for the user to select any transaction from the wallet regardless of the transaction hints. This can be useful if the metadata of the wallet is lost, possibly due to a restore from backup. === PoP destination p === The p parameter value is the destination where to send the PoP to. This destination is typically a https: URL or a http: URL, but it could be any type of URI, for example mailto:. To keep btcpop: URIs short, users should not make their p parameter unnecessarily long. ==== http: and https: URLs ==== Wallet implementations must support the http: and https: schemes in which case POST method must be used. The PoP is sent as a binary serialized transaction. The content type of the POST request must be set to application/bitcoin-pop == Examples == Send PoP for a transaction with label "video 42923" to https://www.example.com/pop/352, using nonce 0x73 0xd5 0x1a 0xbb 0xd8 0x9c:
 btcpop:?p=https://www.example.com/pop/352&n=zgWTm8yH&label=video%2042923
Send PoP through mail using mailto:pop@example.com?subject=pop444, amount is 13370000 satoshis, nonce is 0x6f 0xe 0xfb 0x68 0x92 0xf9. Note that the ? before subject is OK according to RFC3986, since the query part starts from the first ?:
 btcpop:?p=mailto:pop@example.com?subject%3Dpop444&n=xJdKmEbr&amount=0.1337
Send PoP for transaction with id cca7507897abc89628f450e8b1e0c6fca4ec3f7b34cccf55f3f531c659ff4d79 to pizza place at http://pizza.example.com/pop/laszlo111 using nonce 0xfc 0xcc 0x2c 0x35 0xf0 0xb8
 btcpop:?p=http://pizza.example.com/pop/laszlo111&n=3AtNpVrPh&txid=Emt9MPvt1joznqHy5eEHkNtcuQuYWXzYJBQZN6BJm6NL
== Reference implementation == [https://github.com/kallerosenbaum/poppoc PoP Demo server on GitHub] [https://github.com/kallerosenbaum/wallet PoP-enabled Mycelium fork on GitHub] == References == [https://github.com/bitcoin/bips/blob/master/bip-0021.mediawiki BIP0021]: URI Scheme [https://github.com/bitcoin/bips/blob/master/bip-0120.mediawiki BIP0120]: Proof of Payment [https://www.ietf.org/rfc/rfc3986.txt RFC3986]: Uniform Resource Identifier (URI): Generic Syntax ================================================ FILE: bip-0122.mediawiki ================================================
  BIP: 122
  Layer: Applications
  Title: URI scheme for Blockchain references / exploration
  Authors: Marco Pontello 
  Status: Draft
  Type: Specification
  Assigned: 2015-08-29
  License: PD
  Discussion: https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2015-August/010712.html
==Abstract== This BIP proposes a URI scheme for looking up blocks, transactions and addresses on a Blockchain explorer, or in general to make proper Blockchain references. ==Motivation== The purpose of this URI scheme is to enable users to handle all the requests for details about blocks, transactions, etc. with their preferred tool (being that a web service or a local application). Currently a Bitcoin client usually points to an arbitrary blockchain explorer when the user looks for the details of a transaction or allows the user to choose from a set of alternatives. Resorting to copy + paste into a browser is often required. The same happens with posts and messages that reference some particular txs or blocks, if they provide links at all. ==Specification== The URI follow this form: blockchain:[//]// Where: {| class="wikitable" ! style="text-align: center;" | Element ! colspan="2" style="text-align: center;" | Description ! Required? |- | chain | colspan="2" | '''chain ID''' (see below) of the desired chain, leading 0s included. If omitted (which would be the usual case), Bitcoin main net is assumed. | optional |- | rowspan="3" | type | tx | for transactions. | rowspan="3" | required |- | block | for blocks (supports both hash or height). |- | address | for addresses. |- | hash | colspan="2" | the relevant hash to refer to (leading zeros included), or block height. | required |} ====ABNF grammar====
blockchainuri = "blockchain:" ["//" chain] "/" object
object = ("tx" "/" hash) / ("block" "/" (hash / blockheight)) /
         ("address" "/" address)
chain = hash
hash = 64HEXDIG
blockheight = 1*15DIGIT ; 15 is somehow arbitrary, i.e. a "small" int.
address = base58 ; https://en.wikipedia.org/wiki/Base58
---- ===Definition of chain ID=== The '''chain ID''' of a chain is the block hash of the corresponding genesis block. For forked chains, it's the block hash of the first block after fork. So, for example:
Bitcoin main   : 000000000019d6689c085ae165831e934ff763ae46a2a6c172b3f1b60a8ce26f
Bitcoin test   : 000000000933ea01ad0ee984209779baaec3ced90fa3f408719526f8d77f4943
Bitcoin regtest: 0f9188f13cb7b2c71f2a335e3a4fc328bf5beb436012afca590b1a11466e2206
An example of forked chain (Feathercoin, that forked Litecoin):
Litecoin   : 12a765e31ffd4059bada1e25190f6e98c99d9714d334efa41a195a7e7e04bfe2
Feathercoin: fdbe99b90c90bae7505796461471d89ae8388ab953997aa06a355bbda8d915cb
==Examples== A transaction on Bitcoin main net: blockchain:/tx/b462ae6eb8bdae2e060239a2a3ea5d9c3e0f9ef34d9717beb2dcf0ed42cee7da A block on Bitcoin main net: blockchain:/block/00000000000000000119af5bcae2926df54ae262e9071a94a99c913cc217cc72 or blockchain:/block/372338 An address on Bitcoin main net: blockchain:/address/16EW6Rv9P9AxFDBrZV816dD4sj1EAYUX3f A transaction on Bitcoin test net: blockchain://000000000933ea01ad0ee984209779baaec3ced90fa3f408719526f8d77f4943/tx/3b95a766d7a99b87188d6875c8484cb2b310b78459b7816d4dfc3f0f7e04281a ==Rationale== From the point of view of a wallet (or other Blockchain related tool) developers which need to reference Blockchain data, using this scheme mean that he can simply make it a `blockchain:` link without having to worry about any specific Blockchain explorer or provide a means for the user to select one. Blockchain explorers in turn will simply offer to handle the `blockchain:` URI schema, the first time the user visit their website, or launch/install the application, or even set themselves if there isn't already one. Users can link directly to their preferred block explorer (avoiding copy + paste which can be awkward on mobile devices). == Sample implementation == [https://github.com/MarcoPon/blockchain-exploration Demo Blockchain: URI handler on GitHub] ==Acknowledgements== Thanks to Btc Drak for suggesting support for different networks and Jorge Timon for the suggestion that we could identify each network by its genesis block hash. Thanks to Richard Moore, Matt Whitlock, Andreas Schildbach for help with the structure and hierarchy of the URI scheme. ==Copyright== This document is placed in the public domain. ================================================ FILE: bip-0123.mediawiki ================================================
  BIP: 123
  Title: BIP Classification
  Authors: Eric Lombrozo 
  Status: Deployed
  Type: Process
  Assigned: 2015-08-26
  License: CC0-1.0 OR FSFAP
==Abstract== This document describes a classification scheme for BIPs. BIPs are classified by system layers with lower numbered layers involving more intricate interoperability requirements. The specification defines the layers and sets forth specific criteria for deciding to which layer a particular standards BIP belongs. ==Copyright== This BIP is dual-licensed under the Creative Commons CC0 1.0 Universal and FSF All Permissive licenses. ==Motivation== Bitcoin is a system involving a number of different standards. Some standards are absolute requirements for interoperability while others can be considered optional, giving implementers a choice of whether to support them. In order to have a BIP process which more closely reflects the interoperability requirements, it is necessary to categorize BIPs accordingly. Lower layers present considerably greater challenges in getting standards accepted and deployed. ==Specification== Standards BIPs are placed in one of four layers: # Consensus # Peer Services # API/RPC # Applications Non-standards BIPs may be placed in these layers, or none at all. ===1. Consensus Layer=== The consensus layer defines cryptographic commitment structures. Its purpose is ensuring that anyone can locally evaluate whether a particular state and history is valid, providing settlement guarantees, and assuring eventual convergence. The consensus layer is not concerned with how messages are propagated on a network. Disagreements over the consensus layer can result in network partitioning, or forks, where different nodes might end up accepting different incompatible histories. We further subdivide consensus layer changes into soft forks and hard forks. ====Soft Forks==== In a soft fork, some structures that were valid under the old rules are no longer valid under the new rules. Structures that were invalid under the old rules continue to be invalid under the new rules. ====Hard Forks==== In a hard fork, structures that were invalid under the old rules become valid under the new rules. ===2. Peer Services Layer=== The peer services layer specifies how nodes find each other and propagate messages. Only a subset of all specified peer services are required for basic node interoperability. Nodes can support further optional extensions. It is always possible to add new services without breaking compatibility with existing services, then gradually deprecate older services. In this manner, the entire network can be upgraded without serious risks of service disruption. ===3. API/RPC Layer=== The API/RPC layer specifies higher level calls accessible to applications. Support for these BIPs is not required for basic network interoperability but might be expected by some client applications. There's room at this layer to allow for competing standards without breaking basic network interoperability. ===4. Applications Layer=== The applications layer specifies high level structures, abstractions, and conventions that allow different applications to support similar features and share data. ==Classification of existing BIPs== {| class="wikitable sortable" style="width: auto; text-align: center; font-size: smaller; table-layout: fixed;" !Number !Layer !Title !Owner !Type !Status |- style="background-color: #cfffcf" | [[bip-0001.mediawiki|1]] | | BIP Purpose and Guidelines | Amir Taaki | Process | Active |- | [[bip-0002.mediawiki|2]] | | BIP process, revised | Luke Dashjr | Process | Draft |- style="background-color: #cfffcf" | [[bip-0009.mediawiki|9]] | | Version bits with timeout and delay | Pieter Wuille, Peter Todd, Greg Maxwell, Rusty Russell | Informational | Final |- style="background-color: #ffcfcf" | [[bip-0010.mediawiki|10]] | Applications | Multi-Sig Transaction Distribution | Alan Reiner | Informational | Withdrawn |- style="background-color: #cfffcf" | [[bip-0011.mediawiki|11]] | Applications | M-of-N Standard Transactions | Gavin Andresen | Standard | Final |- style="background-color: #ffcfcf" | [[bip-0012.mediawiki|12]] | Consensus (soft fork) | OP_EVAL | Gavin Andresen | Standard | Withdrawn |- style="background-color: #cfffcf" | [[bip-0013.mediawiki|13]] | Applications | Address Format for pay-to-script-hash | Gavin Andresen | Standard | Final |- style="background-color: #cfffcf" | [[bip-0014.mediawiki|14]] | Peer Services | Protocol Version and User Agent | Amir Taaki, Patrick Strateman | Standard | Final |- | [[bip-0015.mediawiki|15]] | Applications | Aliases | Amir Taaki | Standard | Deferred |- style="background-color: #cfffcf" | [[bip-0016.mediawiki|16]] | Consensus (soft fork) | Pay to Script Hash | Gavin Andresen | Standard | Final |- style="background-color: #ffcfcf" | [[bip-0017.mediawiki|17]] | Consensus (soft fork) | OP_CHECKHASHVERIFY (CHV) | Luke Dashjr | Standard | Withdrawn |- style="background-color: #ffffcf" | [[bip-0018.mediawiki|18]] | Consensus (soft fork) | hashScriptCheck | Luke Dashjr | Standard | Accepted |- | [[bip-0019.mediawiki|19]] | Applications | M-of-N Standard Transactions (Low SigOp) | Luke Dashjr | Standard | Draft |- style="background-color: #ffcfcf" | [[bip-0020.mediawiki|20]] | Applications | URI Scheme | Luke Dashjr | Standard | Replaced |- style="background-color: #cfffcf" | [[bip-0021.mediawiki|21]] | Applications | URI Scheme | Nils Schneider, Matt Corallo | Standard | Final |- style="background-color: #cfffcf" | [[bip-0022.mediawiki|22]] | API/RPC | getblocktemplate - Fundamentals | Luke Dashjr | Standard | Final |- style="background-color: #cfffcf" | [[bip-0023.mediawiki|23]] | API/RPC | getblocktemplate - Pooled Mining | Luke Dashjr | Standard | Final |- style="background-color: #cfffcf" | [[bip-0030.mediawiki|30]] | Consensus (soft fork) | Duplicate transactions | Pieter Wuille | Standard | Final |- style="background-color: #cfffcf" | [[bip-0031.mediawiki|31]] | Peer Services | Pong message | Mike Hearn | Standard | Final |- style="background-color: #cfffcf" | [[bip-0032.mediawiki|32]] | Applications | Hierarchical Deterministic Wallets | Pieter Wuille | Informational | Final |- | [[bip-0033.mediawiki|33]] | Peer Services | Stratized Nodes | Amir Taaki | Standard | Draft |- style="background-color: #cfffcf" | [[bip-0034.mediawiki|34]] | Consensus (soft fork) | Block v2, Height in Coinbase | Gavin Andresen | Standard | Final |- style="background-color: #cfffcf" | [[bip-0035.mediawiki|35]] | Peer Services | mempool message | Jeff Garzik | Standard | Final |- | [[bip-0036.mediawiki|36]] | Peer Services | Custom Services | Stefan Thomas | Standard | Draft |- style="background-color: #cfffcf" | [[bip-0037.mediawiki|37]] | Peer Services | Connection Bloom filtering | Mike Hearn, Matt Corallo | Standard | Final |- | [[bip-0038.mediawiki|38]] | Applications | Passphrase-protected private key | Mike Caldwell, Aaron Voisine | Standard | Draft |- style="background-color: #ffffcf" | [[bip-0039.mediawiki|39]] | Applications | Mnemonic code for generating deterministic keys | Marek Palatinus, Pavol Rusnak, Aaron Voisine, Sean Bowe | Standard | Accepted |- | [[bip-0042.mediawiki|42]] | Consensus (soft fork) | A finite monetary supply for Bitcoin | Pieter Wuille | Standard | Draft |- | [[bip-0043.mediawiki|43]] | Applications | Purpose Field for Deterministic Wallets | Marek Palatinus, Pavol Rusnak | Informational | Draft |- style="background-color: #ffffcf" | [[bip-0044.mediawiki|44]] | Applications | Multi-Account Hierarchy for Deterministic Wallets | Marek Palatinus, Pavol Rusnak | Standard | Accepted |- style="background-color: #ffffcf" | [[bip-0045.mediawiki|45]] | Applications | Structure for Deterministic P2SH Multisignature Wallets | Manuel Araoz, Ryan X. Charles, Matias Alejo Garcia | Standard | Accepted |- | [[bip-0047.mediawiki|47]] | Applications | Reusable Payment Codes for Hierarchical Deterministic Wallets | Justus Ranvier | Informational | Draft |- | [[bip-0049.mediawiki|49]] | Applications | Derivation scheme for P2WPKH-nested-in-P2SH based accounts | Daniel Weigl | Informational | Draft |- style="background-color: #cfffcf" | [[bip-0050.mediawiki|50]] | | March 2013 Chain Fork Post-Mortem | Gavin Andresen | Informational | Final |- | [[bip-0060.mediawiki|60]] | Peer Services | Fixed Length "version" Message (Relay-Transactions Field) | Amir Taaki | Standard | Draft |- style="background-color: #cfffcf" | [[bip-0061.mediawiki|61]] | Peer Services | Reject P2P message | Gavin Andresen | Standard | Final |- style="background-color: #ffcfcf" | [[bip-0062.mediawiki|62]] | Consensus (soft fork) | Dealing with malleability | Pieter Wuille | Standard | Withdrawn |- | [[bip-0064.mediawiki|64]] | Peer Services | getutxo message | Mike Hearn | Standard | Draft |- style="background-color: #cfffcf" | [[bip-0065.mediawiki|65]] | Consensus (soft fork) | OP_CHECKLOCKTIMEVERIFY | Peter Todd | Standard | Final |- style="background-color: #cfffcf" | [[bip-0066.mediawiki|66]] | Consensus (soft fork) | Strict DER signatures | Pieter Wuille | Standard | Final |- style="background-color: #ffffcf" | [[bip-0067.mediawiki|67]] | Applications | Deterministic Pay-to-script-hash multi-signature addresses through public key sorting | Thomas Kerin, Jean-Pierre Rupp, Ruben de Vries | Standard | Accepted |- style="background-color: #cfffcf" | [[bip-0068.mediawiki|68]] | Consensus (soft fork) | Relative lock-time using consensus-enforced sequence numbers | Mark Friedenbach, BtcDrak, Nicolas Dorier, kinoshitajona | Standard | Final |- style="background-color: #ffffcf" | [[bip-0069.mediawiki|69]] | Applications | Lexicographical Indexing of Transaction Inputs and Outputs | Kristov Atlas | Informational | Accepted |- style="background-color: #cfffcf" | [[bip-0070.mediawiki|70]] | Applications | Payment Protocol | Gavin Andresen, Mike Hearn | Standard | Final |- style="background-color: #cfffcf" | [[bip-0071.mediawiki|71]] | Applications | Payment Protocol MIME types | Gavin Andresen | Standard | Final |- style="background-color: #cfffcf" | [[bip-0072.mediawiki|72]] | Applications | bitcoin: uri extensions for Payment Protocol | Gavin Andresen | Standard | Final |- style="background-color: #cfffcf" | [[bip-0073.mediawiki|73]] | Applications | Use "Accept" header for response type negotiation with Payment Request URLs | Stephen Pair | Standard | Final |- | [[bip-0074.mediawiki|74]] | Applications | Allow zero value OP_RETURN in Payment Protocol | Toby Padilla | Standard | Draft |- | [[bip-0075.mediawiki|75]] | Applications | Out of Band Address Exchange using Payment Protocol Encryption | Justin Newton, Matt David, Aaron Voisine, James MacWhyte | Standard | Draft |- | [[bip-0080.mediawiki|80]] | | Hierarchy for Non-Colored Voting Pool Deterministic Multisig Wallets | Justus Ranvier, Jimmy Song | Informational | Deferred |- | [[bip-0081.mediawiki|81]] | | Hierarchy for Colored Voting Pool Deterministic Multisig Wallets | Justus Ranvier, Jimmy Song | Informational | Deferred |- | [[bip-0083.mediawiki|83]] | Applications | Dynamic Hierarchical Deterministic Key Trees | Eric Lombrozo | Standard | Draft |- | [[bip-0099.mediawiki|99]] | | Motivation and deployment of consensus rule changes ([soft/hard]forks) | Jorge Timón | Informational | Draft |- style="background-color: #ffcfcf" | [[bip-0101.mediawiki|101]] | Consensus (hard fork) | Increase maximum block size | Gavin Andresen | Standard | Withdrawn |- | [[bip-0102.mediawiki|102]] | Consensus (hard fork) | Block size increase to 2MB | Jeff Garzik | Standard | Draft |- | [[bip-0103.mediawiki|103]] | Consensus (hard fork) | Block size following technological growth | Pieter Wuille | Standard | Draft |- | [[bip-0105.mediawiki|105]] | Consensus (hard fork) | Consensus based block size retargeting algorithm | BtcDrak | Standard | Draft |- | [[bip-0106.mediawiki|106]] | Consensus (hard fork) | Dynamically Controlled Bitcoin Block Size Max Cap | Upal Chakraborty | Standard | Draft |- | [[bip-0107.mediawiki|107]] | Consensus (hard fork) | Dynamic limit on the block size | Washington Y. Sanchez | Standard | Draft |- | [[bip-0109.mediawiki|109]] | Consensus (hard fork) | Two million byte size limit with sigop and sighash limits | Gavin Andresen | Standard | Draft |- style="background-color: #ffffcf" | [[bip-0111.mediawiki|111]] | Peer Services | NODE_BLOOM service bit | Matt Corallo, Peter Todd | Standard | Accepted |- style="background-color: #cfffcf" | [[bip-0112.mediawiki|112]] | Consensus (soft fork) | CHECKSEQUENCEVERIFY | BtcDrak, Mark Friedenbach, Eric Lombrozo | Standard | Final |- style="background-color: #cfffcf" | [[bip-0113.mediawiki|113]] | Consensus (soft fork) | Median time-past as endpoint for lock-time calculations | Thomas Kerin, Mark Friedenbach | Standard | Final |- | [[bip-0114.mediawiki|114]] | Consensus (soft fork) | Merkelized Abstract Syntax Tree | Johnson Lau | Standard | Draft |- | [[bip-0120.mediawiki|120]] | Applications | Proof of Payment | Kalle Rosenbaum | Standard | Draft |- | [[bip-0121.mediawiki|121]] | Applications | Proof of Payment URI scheme | Kalle Rosenbaum | Standard | Draft |- | [[bip-0122.mediawiki|122]] | Applications | URI scheme for Blockchain references / exploration | Marco Pontello | Standard | Draft |- | [[bip-0123.mediawiki|123]] | | BIP Classification | Eric Lombrozo | Process | Draft |- | [[bip-0124.mediawiki|124]] | Applications | Hierarchical Deterministic Script Templates | Eric Lombrozo, William Swanson | Informational | Draft |- style="background-color: #ffffcf" | [[bip-0125.mediawiki|125]] | Applications | Opt-in Full Replace-by-Fee Signaling | David A. Harding, Peter Todd | Standard | Accepted |- | [[bip-0126.mediawiki|126]] | | Best Practices for Heterogeneous Input Script Transactions | Kristov Atlas | Informational | Draft |- style="background-color: #ffffcf" | [[bip-0130.mediawiki|130]] | Peer Services | sendheaders message | Suhas Daftuar | Standard | Accepted |- | [[bip-0131.mediawiki|131]] | Consensus (hard fork) | "Coalescing Transaction" Specification (wildcard inputs) | Chris Priest | Standard | Draft |- style="background-color: #ffcfcf" | [[bip-0132.mediawiki|132]] | | Committee-based BIP Acceptance Process | Andy Chase | Process | Withdrawn |- | [[bip-0133.mediawiki|133]] | Peer Services | feefilter message | Alex Morcos | Standard | Draft |- | [[bip-0134.mediawiki|134]] | Consensus (hard fork) | Flexible Transactions | Tom Zander | Standard | Draft |- | [[bip-0140.mediawiki|140]] | Consensus (soft fork) | Normalized TXID | Christian Decker | Standard | Draft |- | [[bip-0141.mediawiki|141]] | Consensus (soft fork) | Segregated Witness (Consensus layer) | Eric Lombrozo, Johnson Lau, Pieter Wuille | Standard | Draft |- | [[bip-0142.mediawiki|142]] | Applications | Address Format for Segregated Witness | Johnson Lau | Standard | Deferred |- | [[bip-0143.mediawiki|143]] | Consensus (soft fork) | Transaction Signature Verification for Version 0 Witness Program | Johnson Lau, Pieter Wuille | Standard | Draft |- | [[bip-0144.mediawiki|144]] | Peer Services | Segregated Witness (Peer Services) | Eric Lombrozo, Pieter Wuille | Standard | Draft |- | [[bip-0145.mediawiki|145]] | API/RPC | getblocktemplate Updates for Segregated Witness | Luke Dashjr | Standard | Draft |- | [[bip-0146.mediawiki|146]] | Consensus (soft fork) | Dealing with signature encoding malleability | Johnson Lau, Pieter Wuille | Standard | Draft |- | [[bip-0147.mediawiki|147]] | Consensus (soft fork) | Dealing with dummy stack element malleability | Johnson Lau | Standard | Draft |- | [[bip-0150.mediawiki|150]] | Peer Services | Peer Authentication | Jonas Schnelli | Standard | Draft |- | [[bip-0151.mediawiki|151]] | Peer Services | Peer-to-Peer Communication Encryption | Jonas Schnelli | Standard | Draft |- | [[bip-0152.mediawiki|152]] | Peer Services | Compact Block Relay | Matt Corallo | Standard | Draft |} ================================================ FILE: bip-0124.mediawiki ================================================
  BIP: 124
  Layer: Applications
  Title: Hierarchical Deterministic Script Templates
  Authors: Eric Lombrozo 
           William Swanson 
  Status: Closed
  Type: Informational
  Assigned: 2015-11-20
  License: PD
  Discussion: http://lists.linuxfoundation.org/pipermail/bitcoin-dev/2015-November/011795.html
==Abstract== This BIP defines a script template format that can be used by wallets to deterministically generate scripts with specific authorization policies using the key derivation mechanism defined in BIP32. ==Motivation== Currently existing wallets typically issue scripts in only a tiny handful of widely used formats. The most popular formats are pay-to-pubkey-hash and m-of-n pay-to-script-hash (BIP16). However, different wallets tend to use mutually incompatible derivation schemes to generate signing keys and construct scripts from them. Moreover, with the advent of hashlocked and timelocked contracts (BIP65, BIP112), it is necessary for different wallets to be able to cooperatively generate even more sophisticated scripts. In addition, there's a lot of ongoing work in the development of multilayered protocols that use the blockchain as a settlement layer (i.e. the Lightning Network). These efforts require sufficiently generalized templates to allow for rapidly evolving script designs. This BIP provides a generalized format for constructing a script template that guarantees that different wallets will all produce the same scripts for a given set of derivation paths according to BIP32. ==Specification== ===Keys=== An individual key is determined by a BIP32 derivation path and an index. For convenience, we introduce the following notation: '''A'''k = (derivation path for A)/k ===Key Groups=== Let '''m'''i denote distinct BIP32 derivation paths. We define a key group of n keys as a set of key derivation paths with a free index k: {'''K'''k} = { '''m'''1/k, '''m'''2/k, '''m'''3/k, ..., '''m'''n/k } Key groups are useful for constructing scripts that are symmetric in a set of keys. Scripts are symmetric in a set of keys if the semantics of the script is unaffected by permutations of the keys. Key groups enforce a canonical form and can improve privacy. ===Sorting=== We define a lexicographic sorting of the keys. (TODO: specification of sorting conventions - compressed pubkeys, encoding, etc...) Define {'''K'''k}j to be the jth element of the sorted keys for derivation index k. ===Script Templates=== We construct script templates by inserting placeholders for data into a script. To denote a placeholder, we use the following notation: ''Script''('''A''') = opcodes ['''A'''] opcodes We extend this notation to an arbitrary number of placeholders: ''Script''('''X1''', '''X2''', ..., '''Xn''') = opcodes ['''X1'''] opcodes ['''X2'''] opcodes ... opcodes ['''Xn'''] opcodes We introduce the following convenient notation for sorted key groups: [{'''K'''k}] = [{'''K'''k}1] [{'''K'''k}2] ... [{'''K'''k}n] ===Operations on Keys=== In some applications, we might want to insert the result of some operation performed on a key rather than the key itself into the script. For example, we might want to insert a Hash160 of key '''A'''k. We can use the following notation: [''Hash160''('''A'''k)] ===Encoding=== TODO ==Examples== ===2-of-3 Multisig=== The script template is defined by: ''Script''('''X''') = 2 ['''X'''] 3 OP_CHECKMULTISIG Letting '''K'''k = { '''m'''1/k, '''m'''2/k, '''m'''3/k }, the ''k''th script for this key group is denoted by ''Script''({'''K'''k}). ===1-of-1 or 2-of-3=== The script template is defined by: ''Script''('''A''', '''B''') =
        OP_DUP ['''A'''] OP_CHECKSIG
        OP_NOTIF
                2 ['''B'''] 3 OP_CHECKMULTISIGVERIFY
        OP_NOTIF
        OP_ENDIF
        OP_TRUE
Let '''M'''k = '''m'''/k be a key of a superuser that can authorize all transactions and {'''K'''k} be a key group of three users that can only authorize transactions if at least two of them agree. The ''k''th script is given by ''Script''('''M'''k, {'''K'''k}). ===Timelocked Contract=== The output is payable to Alice immediately if she knows the private key for '''A'''k. Bob must know the private key for '''B'''k and also wait for a timeout '''t''' before being able to spend the output. The script template is defined by: ''Script''('''A''', '''B''', '''T''') =
        OP_IF
                OP_DUP OP_HASH160 [''Hash160''('''A''')] OP_EQUALVERIFY OP_CHECKSIG
        OP_ELSE
                ['''T'''] OP_CHECKLOCKTIMEVERIFY OP_DROP
                OP_DUP OP_HASH160 [''Hash160''('''B''')] OP_EQUALVERIFY OP_CHECKSIG
        OP_ENDIF The ''k''th script with timeout '''t''' is given by ''Script''('''A'''k, '''B'''k, '''t'''). ==References== * [[bip-0016.mediawiki|BIP16 - Pay to Script Hash]] * [[bip-0032.mediawiki|BIP32 - Hierarchical Deterministic Wallets]] * [[bip-0065.mediawiki|BIP65 - OP_CHECKLOCKTIMEVERIFY]] * [[bip-0112.mediawiki|BIP112 - CHECKSEQUENCEVERIFY]] * [[https://lightning.network/lightning-network-paper.pdf|Lightning Network Whitepaper]] ==Copyright== This document is placed in the public domain. ================================================ FILE: bip-0125.mediawiki ================================================
  BIP: 125
  Layer: Applications
  Title: Opt-in Full Replace-by-Fee Signaling
  Authors: David A. Harding 
           Peter Todd 
  Comments-Summary: No comments yet.
  Comments-URI: https://github.com/bitcoin/bips/wiki/Comments:BIP-0125
  Status: Deployed
  Type: Specification
  Assigned: 2015-12-04
  License: PD
==Abstract== Many nodes today will not replace any transaction in their mempool with another transaction that spends the same inputs, making it difficult for spenders to adjust their previously-sent transactions to deal with unexpected confirmation delays or to perform other useful replacements. The opt-in full Replace-by-Fee (opt-in full-RBF) signaling policy described here allows spenders to add a signal to a transaction indicating that they want to be able to replace that transaction in the future. In response to this signal, * Nodes may allow transactions containing this signal to be replaced in their mempools. * The recipient or recipients of a transaction containing this signal may choose not to treat it as payment until it has been confirmed, eliminating the risk that the spender will use allowed replacements to defraud them. Nodes and recipients may continue to treat transactions without the signal the same way they treated them before, preserving the existing status quo. ==Summary== This policy specifies two ways a transaction can signal that it is replaceable. * '''Explicit signaling:''' A transaction is considered to have opted in to allowing replacement of itself if any of its inputs have an nSequence number less than (0xffffffff - 1). * '''Inherited signaling:''' Transactions that don't explicitly signal replaceability are replaceable under this policy for as long as any one of their ancestors signals replaceability and remains unconfirmed. ===Implementation Details=== The initial implementation expected in Bitcoin Core 0.12.0 uses the following rules: One or more transactions currently in the mempool (original transactions) will be replaced by a new transaction (replacement transaction) that spends one or more of the same inputs if, # The original transactions signal replaceability explicitly or through inheritance as described in the above Summary section. # The replacement transaction may only include an unconfirmed input if that input was included in one of the original transactions. (An unconfirmed input spends an output from a currently-unconfirmed transaction.) # The replacement transaction pays an absolute fee of at least the sum paid by the original transactions. # The replacement transaction must also pay for its own bandwidth at or above the rate set by the node's minimum relay fee setting. For example, if the minimum relay fee is 1 satoshi/byte and the replacement transaction is 500 bytes total, then the replacement must pay a fee at least 500 satoshis higher than the sum of the originals. # The number of original transactions to be replaced and their descendant transactions which will be evicted from the mempool must not exceed a total of 100 transactions. The initial implementation may be seen in [https://github.com/bitcoin/bitcoin/pull/6871 Bitcoin Core PR#6871] and specifically the master branch commits from 5891f870d68d90408aa5ce5b597fb574f2d2cbca to 16a2f93629f75d182871f288f0396afe6cdc8504 (inclusive). ===Receiving wallet policy=== Wallets that display unconfirmed transactions to users or that provide data about unconfirmed transactions to automated systems should consider doing one of the following: # Conveying additional suspicion about opt-in full-RBF transactions to the user or data consumer. # Ignoring the opt-in transaction until it has been confirmed. Because descendant transactions may also be replaceable under this policy through inherited signaling, any method used to process opt-in full-RBF transactions should be inherited by any descendant transactions for as long as any ancestor opt-in full-RBF transactions remain unconfirmed. ===Spending wallet policy=== Wallets that don't want to signal replaceability should use either a max sequence number (0xffffffff) or a sequence number of (0xffffffff-1) when they also want to use locktime; all known wallets currently do this. They should also take care not to spend any unconfirmed transaction that signals replaceability explicitly or through inherited signaling; most wallets also currently do this by not spending any unconfirmed transactions except for those they created themselves. Wallets that do want to make replacements should use explicit signaling and meet the criteria described above in the Implementation Details section. A [https://en.bitcoin.it/wiki/Transaction_replacement Bitcoin Wiki page] has been created to help wallet authors track deployed mempool policies relating to transaction replacement. The initial implementation makes use of P2P protocol reject messages for rejected replacements, allowing P2P clients to determine whether their replacements were initially accepted by their peers. Standard P2P lightweight client practice of sending to some peers while listening for relays from other peers should allow clients to determine whether the replacement has propagated. ==Motivation== Satoshi Nakamoto's original Bitcoin implementation provided the nSequence number field in each input to [https://github.com/trottier/original-bitcoin/blob/master/src/main.cpp#L434 allow replacement] of transactions containing that input within the mempool. When receiving replacements, nodes were supposed to replace transactions whose inputs had lower sequence numbers with transactions that had higher sequence numbers. In that implementation, replacement transactions did not have to pay additional fees, so there was no direct incentive for miners to include the replacement and no built-in rate limiting that prevented overuse of relay node bandwidth. Nakamoto [https://github.com/bitcoin/bitcoin/commit/05454818dc7ed92f577a1a1ef6798049f17a52e7#diff-118fcbaaba162ba17933c7893247df3aR522 removed replacement] from Bitcoin version 0.3.12, leaving only the comment, "Disable replacement feature for now". Replacing transactions with higher-fee transactions provided a way for spenders to align their desires with miners, but by the time a Replace-by-Fee (RBF) patch was available to re-enable replacement, some receivers had begun to expect that the first version of a transaction they saw was highly likely to be the version of the transaction to be confirmed, and so some users advocated that replacement should be disallowed. To address those concerns, a variation on RBF was created that required that the replacement transaction pay all of the same outputs as the original transaction in equal or greater amount. This was called RBF First Seen Safe (RBF-FSS), and the original RBF became known as full-RBF. Although agreeable to recipients who relied on the first-seen version of a transaction, each use of RBF-FSS required adding an extra input to a transaction, resulting in wallets being unable to use it if they had no spare inputs, a loss of privacy when inputs from different origins get used in the same transaction, and a wasteful increase in transaction byte size. Opt-in full-RBF uses Nakamoto's original semantics (with a slight tweak to allow locktime users to opt-out) to signal that replacement is possible, providing first-seen users with the ability to ignore those transactions while also allowing for the efficiency benefits of full-RBF. There are no known problematic interactions between opt-in full-RBF and other uses of nSequence. Specifically, opt-in full-RBF is compatible with consensus-enforced locktime as provided in the Bitcoin 0.1 implementation, BIP68 (Relative lock-time using consensus-enforced sequence numbers), and BIP112 (CHECKSEQUENCEVERIFY). ==Deployment== Now, and since Bitcoin's first release, 100% of the network hash rate mines transactions using opt-in full-RBF semantics (sequence less than (0xffffffff - 1)). Opt-in full-RBF as a default mempool replacement policy among nodes and miners is expected to become widespread as they upgrade to Bitcoin Core 0.12.0 (release expected Jan/Feb 2016) and similar node software such as Bitcoin LJR. Actual replacement may be unreliable until two conditions have been satisfied: # Enough nodes have upgraded to support it, providing a relay path for replacements to go from spending wallets to miners controlling significant amounts of hash rate. # Enough hash rate has upgraded to support replacement, allowing for reasonable probability that a replacement can be mined. ==Backwards compatibility== At the time opt-in RBF support was added/proposed, no known wallet created transactions by default with nSequence set below (0xffffffff - 1), so no known wallet explicitly signaled replaceability by default. Also no known popular wallet spent other users' unconfirmed transactions by default, so no known wallets signaled inherited replaceability. ==See also== # [https://en.bitcoin.it/wiki/Transaction_replacement Transaction Replaceability on Bitcoin Wiki] targeted at helping wallet authors use RBF # Tools for creating opt-in full-RBF transactions: https://github.com/petertodd/replace-by-fee-tools#replace-by-fee-tools # [https://www.reddit.com/r/Bitcoin/comments/3urm8o/optin_rbf_is_misunderstood_ask_questions_about_it/ Reddit: Questions about opt-in RBF] targeted at helping community members understand opt-in full-RBF ==Copyright== This document is placed in the public domain. ================================================ FILE: bip-0126.mediawiki ================================================
  BIP: 126
  Title: Best Practices for Heterogeneous Input Script Transactions
  Authors: Kristov Atlas 
  Status: Draft
  Type: Informational
  Assigned: 2016-02-10
  License: PD
==Abstract== When a Bitcoin transaction contains inputs that reference previous transaction outputs sent to different Bitcoin addresses, personally identifiable information of the user will leak into the blockchain in an uncontrolled manner. While undesirable, these transactions are frequently unavoidable due to the natural fragmentation of wallet balances over time. This document proposes a set of best practice guidelines which minimize the uncontrolled disclosure of personally identifiable information by defining standard forms for transactions containing heterogeneous input scripts. ==Copyright== This BIP is in the public domain. ==Definitions== * '''Heterogenous input script transaction (HIT)''': A transaction containing multiple inputs where the scripts of the previous transaction outputs being consumed are not identical (e.g. a transaction spending outputs which were sent to more than one Bitcoin address) * '''Unavoidable heterogeneous input script transaction''': A HIT created as a result of a user’s desire to create a new output with a value larger than the value of his wallet's largest existing unspent output * '''Intentional heterogeneous input script transaction''': A HIT created as part of a user protection protocol for reducing uncontrolled disclosure of personally-identifying information (PII) Throughout this procedure, when input scripts are evaluated for uniqueness, "input script" should be interpreted to mean, "the script of the previous output referenced by an input to a transaction". ==Motivations== The recommendations in this document are designed to accomplish three goals: # Maximise the effectiveness of user-protecting protocols: Users may find that protection protocols are counterproductive if such transactions have a distinctive fingerprint which renders them ineffective. # Minimise the adverse consequences of unavoidable heterogeneous input transactions: If unavoidable HITs are indistinguishable from intentional HITs, a user creating an unavoidable HIT benefits from ambiguity with respect to graph analysis. # Limiting the effect on UTXO set growth: To date, non-standardized intentional HITs tend to increase the network's UTXO set with each transaction; this standard attempts to minimize this effect by standardizing unavoidable and intentional HITs to limit UTXO set growth. In order to achieve these goals, this specification proposes a set of best practices for heterogeneous input script transaction creation. These practices accommodate all applicable requirements of both intentional and unavoidable HITs while maximising the effectiveness of both in terms of preventing uncontrolled disclosure of PII. In order to achieve this, two forms of HIT are proposed: Standard form and alternate form. ==Interaction with Other Procedures== Applications which wish to comply both with this procedure and BIP69 should apply this procedure prior to applying BIP69. ==Standard form heterogeneous input script transaction== ===Rules=== A HIT is Standard form if it adheres to all of the following rules: # The number of unique output scripts must be equal to the number of unique input scripts (irrespective of the number of inputs and outputs). # All output scripts must be unique. # At least one pair of outputs must be of equal value. # The largest output in the transaction is a member of a set containing at least two identically-sized outputs. ===Rationale=== The requirement for equal numbers of unique input/output scripts instead of equal number of inputs/outputs accommodates user-protecting UTXO selection behavior. Wallets may contain spendable outputs with identical scripts due to intentional or accidental address reuse, or due to dusting attacks. In order to minimise the adverse consequences of address reuse, any time a UTXO is included in a transaction as an input, all UTXOs with the same spending script should also be included in the transaction. The requirement that all output scripts are unique prevents address reuse. Restricting the number of outputs to the number of unique input scripts prevents this policy from growing the network’s UTXO set. A standard form HIT transaction will always have a number of inputs greater than or equal to the number of outputs. The requirement for at least one pair of outputs in an intentional HIT to be of equal value results in optimal behavior, and causes intentional HITs to resemble unavoidable HITs. ==Alternate form heterogeneous input script transactions== The formation of a standard form HIT is not possible in the following cases: # The HIT is unavoidable, and the user’s wallet contains an insufficient number or size of UTXOs to create a standard form HIT. # The user wishes to reduce the number of utxos in their wallet, and does not have any sets of utxos with identical scripts. When one of the following cases exist, a compliant implementation may create an alternate form HIT by constructing a transaction as follows: ===Procedure=== # Find the smallest combination of inputs whose value is at least the value of the desired spend. ## Add these inputs to the transaction. ## Add a spend output to the transaction. ## Add a change output to the transaction containing the difference between the current set of inputs and the desired spend. # Repeat step 1 to create a second pair of outputs, where one output has the same value as the spend output of the previous step. # (optional) Repeat step 2 until the desired number of inputs have been consumed and/or the desired number outputs have been created. # Adjust the change outputs as necessary to pay the desired transaction fee. Clients which create intentional HITs must have the capability to form alternate form HITs, and must do so for a non-zero fraction of the transactions they create. ===Rules=== An HIT formed via the preceding procedure will adhere to the following conditions: # The number of unique input scripts must exceed the number of output scripts. # All output scripts must be unique. # At least one pair of outputs must be of equal value. ## "Standard outputs" refers to the set of outputs with equal value ## "Standard value" refers to the value of the standard outputs ## "Change outputs" refers to all outputs which are not standard outputs # For a HIT containing n standard outputs, there must exist at least one possible way to organize the inputs and outputs into n sets, where all sets satisfy the following: ## The set contains one or more inputs, exactly one standard output, and exactly one change output ## An input or output that appears in one set must not appear in any other set ## The sum of the inputs in the set minus the value of the change output is equal to the standard value with a tolerance equal to the transaction fee. ## Change outputs with a value of zero (virtual change outputs) are permitted. The are defined for the purpose of testing whether or not a HIT adheres to this specification but are not present in the version of the transaction which is broadcast to the network. ==Non-compliant heterogeneous input script transactions== If a user wishes to create an output that is larger than half the total size of their spendable outputs, or if their inputs are not distributed in a manner in which the alternate form procedure can be completed, then the user can not create a transaction which is compliant with this procedure. ==Reference== * [[bip-0069.mediawiki|BIP69 - Lexicographical Indexing of Transaction Inputs and Outputs]] ================================================ FILE: bip-0127.mediawiki ================================================
  BIP: 127
  Layer: Applications
  Title: Simple Proof-of-Reserves Transactions
  Authors: Steven Roose 
  Status: Draft
  Type: Specification
  Assigned: 2019-01-28
  License: CC0-1.0
==Abstract== This BIP describes a simple way to construct proof-of-reserves transactions. This proposal formalizes a standard format for constructing such proofs, easing their construction with existing wallet infrastructure and enabling general proof-verification software. It relies on existing standards such as regular Bitcoin transaction serialization/validation and the BIP 174 PSBT format. The proposal also includes the description of a PSBT extension for a better user experience. ==Copyright== This BIP is licensed under the Creative Commons CC0 1.0 Universal license. ==Motivation== From the very early days in the history of Bitcoin, there have been companies managing bitcoins for their users. These users give up control over their coins in return for a certain service. Inevitably, there have been many cases of companies losing their users' bitcoins without timely disclosing such events to the public. Proofs of Reserves are a way for companies managing large amounts of bitcoins to prove ownership over a given amount of funds. The regular proof of control helps to ensure that no significant loss has occurred. While the term proof-of-reserves is not new by any means, the procedure is not very common among high-value custodian companies. One of the reasons for this is that every company that wants to perform a proof-of-reserves has to construct its own way to do so. Accordingly, their users have to understand the construction of the proof in order to be able to verify it. This raises the bar of entry both for custodians and for users. ===What this BIP is not doing=== The proof-of-reserve construction described in this document has some known shortcomings, mostly with regards to its privacy properties. While there exists research about improved proof-of-reserves mechanisms that have much better privacy propertiesDagher, Gaby G., Benedikt Bünz, Joseph Bonneau, Jeremy Clark, and Dan Boneh. "Provisions: Privacy-preserving proofs of solvency for Bitcoin exchanges." (2015)., this BIP intentionally only formalizes the de-facto existing method. ==Specification== Our specification consists of two parts: # the format for the actual proofs # a file format used to package a set of proofs and relevant metadata The final construction should have the following properties: * flexible proof construction to support complex wallet infrastructures * easy integration with existing wallet solutions (both hardware and software wallets) * support for verification via a standard procedure, regardless of publisher of the proof * proof prevents reuse of proofs by other parties by committing to a message * allow validating that the issuer had the funds under his control at a certain block, regardless of what happened after that block ===Proof Format=== To allow for maximal compatibility with existing systems, proofs are formatted as regular Bitcoin transactions. However, one small adaptation to the transaction is made that has two functions: # make the transaction unspendable to avoid putting funds at risk # link the proof to the issuer of the proof to prevent copying proofs from other custodians The resulting construction is a Bitcoin transaction with the following characteristics: * The first input (the "commitment input") ** MUST have the txid part of the previous outpoint set to the SHA-256 hash of the commitment message prefixed with "Proof-of-Reserves: "If the message is "Some Message", the txid part should be SHA-256("Proof-of-Reserves: Some Message") with the string encoded as UTF-8. and index 0. * The remaining inputs ** MUST have signatures that commit to the commitment input (e.g. using SIGHASH_ALL). * The transaction MUST have a single output that is the exact sum of all the inputs, assuming the commitment input to have 0 value; this means the transaction has no miner fee. The existence of the first input (which is just a commitment hash) ensures that this transaction is invalid and can never be confirmed. ===Proof File Format=== In theory, the first part of the specification would be sufficient as a minimum viable standard. However, there are a number of motivations to extend the standard with an extra layer of metadata: # constructing and combining multiple proofs #:Having thousands of UTXOs spread across different offline and online wallets could make it difficult to construct a single proof transaction with all UTXOs. Allowing multiple proof transactions with the same commitment message and block number gives extra flexibility to custodians with complex wallet infrastructure without making the combined proof less secure. # metadata for verification #:Not all systems that will be used for verification have access to a full index of all transactions. However, proofs should be easily verifiable even after some of the UTXOs used in the proof are no longer unspent. Metadata present in the proof allows for relatively efficient verification of proofs even if no transaction index is available. # potential future improvements #:The extensible metadata format allows for amending the standard in the future. One potential improvement would be having UTXO set commitments. These would allow the proofs-of-reserves to come with accompanying proofs-of-inclusion of all used UTXOs in the UTXO set at the block of proof construction (making validation even more efficient). The proposed proof-file format provides a standard way of combining multiple proofs and associated metadata. The specification of the format is in the Protocol Buffershttps://github.com/protocolbuffers/protobuf/ format.
syntax = "proto3";
import "google/protobuf/any.proto";

message OutputMeta {
	// Identify the outpoint.
	bytes txid = 1;
	uint32 vout = 2;

	// The block hash of the block where this output was created.
	bytes block_hash = 3;
}

message FinalProof {
	// The proof transaction.  Should be able to be parsed like a regular
	// Bitcoin transaction.
	bytes proof_tx = 1;

	// The metadata of the outputs used in the proof transaction.
	repeated OutputMeta output_metadata = 2;
}

message ProofOfReserves {
	// A version number for this format to enable extending it with
	// additional fields.
	uint32 version = 1;

	// The network magic for the network in which the proofs are valid.
	// 0xD9B4BEF9 for mainnet, 0x0709110B for testnet
	//TODO consider BIP44 coin type ids instead:
	// https://github.com/satoshilabs/slips/blob/master/slip-0044.md
	uint32 network_magic = 2;

	// The commitment message for this proof-of-reserves.
	// This message is global for all the proofs.
	string message = 3;

	// The block at which this proof is supposed to be validated.
	// Verification should take into account unspentness of outputs at this
	// block height.
	bytes block_hash = 4;

	// The set of final proof transactions with their output metadata.
	repeated FinalProof final_proofs = 5;

	// Reserved field that can potentially be used by proof-construction tools.
	// It can be ignored for verification.
	repeated google.protobuf.Any pending_proofs = 6;
}
The last field, pending_proofs, leaves open some space in the same file that can be used by proof-construction tools. This allows them to construct different proofs incrementally without having to switch between file formats. ===PSBT (BIP 174) extension=== The "commitment input" detailed in the proof format section does not spend an existing UTXO and thus shouldn't be signed (empty scriptSig and witness). This can cause some problems when signing this type of transactions. For example, hardware wallets often require the signer to provide information about all inputs of transactions they are signing, such as the previous output or previous transaction; this data obviously doesn't exist for the commitment inputs. For most existing devices, it's possible to circumvent these requirements by providing dummy data or by instructing the device to ignore this specific input. However, there is still a UX problem. Because the hardware wallet device doesn't recognize the transaction as a proof-of-reserves transaction it will think it is signing a regular transaction that is spending all the money in the UTXOs. Most devices will ask for confirmation with a message along the lines of "Are you sure you want to send XXX BTC to address [...]?". This is not the best user experience. An addition to the BIP 174 PSBT format could help signing devices to recognize proof-of-reserve transactions. The following field is added to the BIP 174 INPUT map: * Type: Proof-of-reserves commitment PSBT_IN_POR_COMMITMENT = 0x09 ** Key: None. The key must only contain the 1 byte type. *** {0x09} ** Value: The UTF-8 encoded commitment message string for the proof-of-reserves. *** {porCommitment} Wallets processing an input that has this field set * MUST make sure the txid of the previous outpoint is set to the SHA-256 hash of the prefixed commitment message string, as detailed above; * MUST assume the input value to be 0 (without requiring the previous output or transaction to be provided); * SHOULD display the commitment message to ask the user for confirmation before signing any inputs; * SHOULD only provide signatures with a signature hash that commits to this input; * SHOULD accept an empty scriptSig for this input (as if the scriptPubKey was OP_TRUE). ==Compatibility== The proof transaction specification is based on the Bitcoin transaction serialization protocol and will thus always be compatible with serializers that can interpret Bitcoin transactions. The protobuf file format is custom to this BIP and has a version byte to enable updates while attempting to remain backwards compatible. ==Implementations== A proof-of-concept implementation of the PSBT extension in the [https://github.com/rust-bitcoin/rust-bitcoin rust-bitcoin] project can be found in the psbt-por branch here: https://github.com/stevenroose/rust-bitcoin/tree/psbt-por A work-in-progress implementation of a tool that produces and verifies proofs in the described format can be found here: https://github.com/stevenroose/reserves An implementation of the custom proof PSBTs is part of the [https://bitcoindevkit.org/ BDK], and can be found here: https://crates.io/crates/bdk-reserves == Footnotes == ================================================ FILE: bip-0128.mediawiki ================================================
  BIP: 128
  Layer: Applications
  Title: Timelock-Recovery Storage Format
  Authors: Oren Z 
  Status: Draft
  Type: Specification
  Assigned: 2026-02-05
  License: BSD-2-Clause
  Discussion: https://groups.google.com/g/bitcoindev/c/K1NpJp9_BYk
== Abstract == This document proposes a standard format for saving timelock-recovery plans, to allow different wallets to generate them, and different services to monitor/execute them. == Motivation == Pre-signed transactions are one way to create a recovery-plan, for use in case of seed loss or inheritance. The most common example is a single pre-signed transaction with an nLocktime set to a future date, as explained in [[bip-0065.mediawiki|BIP-65]]. One limitation of this approach is that in the happy-flow scenario, when the seed is not lost, and the nLocktime is about to be reached, the user must access their wallet and spend one of its UTXOs - in order to revoke the pre-signed transaction and prevent it from being able to move the funds with no cancellation period. This could be frustrating, for example, for users that split their seed over multiple geographic locations. ''Timelock-Recovery plans'' are a way to pre-sign a pair of transactions that eventually move the funds to one or more secondary wallets - with a special nSequence relative-locktime in the second transaction, so that the user always has a cancellation-period. Executing and monitoring a ''Timelock-Recovery plan'' thus requires more than broadcasting and monitoring a single transaction. It also requires mechanisms for accelerating the first transaction (which does not move most funds to the secondary wallet), for checking whether the relative-timelock has passed, and a more nuanced handling of reorgs. This BIP proposes a standard format for exporting ''Timelock-Recovery plans'' from the wallet that generated them, and importing them into apps/services for monitoring/execution. === Comparison with Script-Based Wallets === Script-based wallets are another way to create recovery mechanisms, and can use absolute and relative locktimes using OP_CHECKLOCKTIMEVERIFY ([[bip-0065.mediawiki|BIP-65]]) and OP_CHECKSEQUENCEVERIFY ([[bip-0112.mediawiki|BIP-112]]). For example, we can build a script that allows one main key to spend the funds at any time, and a secondary key to spend the funds only in transactions with nLocktime above a certain date/block-height, or only in transactions with nSequence above a certain relative time-gap/number-of-blocks. This makes the secondary key useful only after an absolute date/block-height, or after a relative time since the funds were received (each UTXO independently). This approach does have some advantages over pre-signed transactions, for example the recovery-mechanism automatically applies to new funds received into the wallet. However, script-based wallets have some disadvantages over a sequence of pre-signed transactions: * Script-based wallets are harder to implement correctly by hardware wallets, and harder to backup properly (i.e. users may forget to backup wallet-descriptors even for basic multisig wallets). * As of the time of writing, scripts can limit when secondary-keys can be used, but not how they can be used: if the user doesn't touch the wallets' UTXOs for long-enough time, the secondary key will eventually become useable and could move the funds anywhere. This is true whether we measure the time in absolute terms (OP_CHECKLOCKTIMEVERIFY) or relative terms compared to when the wallets' UTXOs were created (OP_CHECKSEQUENCEVERIFY). This means that even in the happy-flow scenario of an untouched wallet, where no recovery is needed, the user must periodically "renew" the recovery-mechanism by spending the UTXO to a new wallet/address. This may be inconvenient in ultra-cold-storage scenarios (i.e. multisig with main keys hidden in different geographic locations). New opcode suggestions, such as OP_CHECKTEMPLATEVERIFY ([[bip-0119.mediawiki|BIP-119]]) and OP_CHECKCONTRACTVERIFY ([[bip-0443.mediawiki|BIP-443]]), discuss possible recovery-mechanisms in which in order for a secondary key to have full control over the funds, some onchain operations must be performed, with a required time-gap between them - giving the user enough time to revoke the whole process and move the funds elsewhere (assuming they still have the main key and the recovery-mechanism was triggered unintentionally). However, these suggestions are still in the discussion phase and even if ever implemented, their adoption may be slow. * New Bitcoiners today typically don't think of such recovery-mechanisms in advance, and start with a P2WPKH wallet. They can pre-sign transactions with this wallet, but to utilize script-based features they would need to create a new wallet and move the funds there - an operation that might seem intimidating for large amounts. == Specification == A ''Timelock-Recovery plan'' consists of two transactions: * ''Alert Transaction'': A mostly-consolidation transaction that keeps most funds in the original wallet, except for a fee and a small fixed amount that goes to ''anchor-addresses'' - addresses which can be used to accelerate the ''Alert Transaction'' via CPFP. The majority of funds should remain on the original wallet, in a new previously-unused address which we call the ''alert-address''. We use the term ''Alert Transaction'' because monitoring the blockchain and looking for it should alert the user that the recovery-plan has been initiated (intentionally, unintentionally or maliciously). * ''Recovery Transaction'': The transaction that moves the funds from the alert-address UTXO from the ''Alert Transaction'' to one or more addresses of secondary wallets (each may receive a different amount). This transaction should have a special nSequence relative-locktime according to the size of cancellation-period requested by the user, following the rules of [[bip-0068.mediawiki|BIP-68]]. With a reliable tool to monitor the blockchain for the ''Alert Transaction'' or the ''Alert Address'', the user can safely store online backups of the recovery plan's JSON file (or, even without a tool, by checking the blockchain manually from time to time). If the presigned transactions leak and the ''Alert Transaction'' is broadcast unintentionally, the user has the cancellation period (expected to be at least a few days) to prevent most funds from moving by sending them to a new address, thereby invalidating the ''Recovery Transaction''. It is important that the ''Alert Transaction'' will be non-malleable (e.g. by using [[bip-0140.mediawiki|BIP-140]]). If a malleable ''Alert Transaction'' is used, a malicious miner could replace the ''Alert Transaction'' with a similar transaction with a different txid, making the ''Recovery Transaction'' invalid (pointing to a non-existent UTXO). The nLocktime of both transactions should not be higher than the current block height. The ''anchor-addresses'' mentioned above, which are used for CPFP acceleration, could possibly be P2A addresses (described in [[bip-0433.mediawiki|BIP-433]]), or other addresses under the participants' control (i.e. addresses from the secondary wallets). As of the time of writing, P2A is not widely adopted, and less-technical users may struggle using them for CPFP acceleration - so we currently recommend using regular addresses. === nSequence calculation === Users will specify the cancellation-period in whole days between 2-388. Following [[bip-0068.mediawiki|BIP-68]], the nSequence can represent a timespan in units of 512 seconds, when bit (1 << 22) is set. An example calculation is provided below: n_sequence = (1 << 22) | round(cancellation_period_days * 24 * 60 * 60 / 512) Users should be notified that the cancellation-period is not guaranteed to be exact (due to miners' manipulation of block-timestamps). Less than 2 days of cancellation-period and partial-days are not supported, as they are not useful. More than 388 days of cancellation-period will overflow the nSequence field bits allocated for the relative-locktime, and is not supported. === JSON format === For simplicity, this BIP proposes that a ''Timelock-Recovery plan'' will be saved as a JSON object. The JSON object will have the following fields: * kind (mandatory): must be "timelock-recovery-plan". * id (mandatory): a non-empty string of up to 100 characters, to represent the plan uniquely (i.e. a UUID, or a server generated ID). * name (optional): a name for the plan, decided by the user. A string of up to 200 characters. * description (optional): a description for the plan, decided by the user. A string of up to 10,000 characters. * created_at (mandatory): an ISO 8601 timestamp of the plan creation time, including timezone offset ('Z' if the timezone is UTC). * plugin_version (optional): The version of the plugin that generated the plan. A string of up to 100 characters. * wallet_version (mandatory): The version of the wallet that generated the plan. A string of up to 100 characters. * wallet_name (mandatory): The human-readable name of the wallet app that generated the plan. A string of up to 100 characters. * wallet_kind (mandatory): The internal name of the wallet app that generated the plan. A string of up to 100 characters. * timelock_days (mandatory): The cancellation period in whole days. A number between 2 and 388. * anchor_amount_sats (mandatory): The amount in satoshis sent to each anchor address in the Alert Transaction. We recommend using 600 sats, which is above the dust limit. * anchor_addresses (mandatory): An array of up to 10,000 Bitcoin addresses that receive the anchor amount in the Alert Transaction. Each address is a string of up to 100 characters. * alert_address (mandatory): The Bitcoin address that receives the majority of funds in the Alert Transaction. A string of up to 100 characters. * alert_inputs (mandatory): An array of up to 2439 inputs spent by the Alert Transaction. Each input is a string in the format "txid:vout" where txid is a 64-character lowercase hexadecimal string and vout is a decimal number of up to 6 digits. The maximal length of 2439 is calculated from a standard transaction of 400,000 wu where each input contains at least 41 bytes. * alert_tx (mandatory): The raw Alert Transaction in uppercase hexadecimal format. A string of up to 800,000 characters. * alert_txid (mandatory): The transaction ID of the Alert Transaction. A 64-character lowercase hexadecimal string. * alert_fee (mandatory): The total fee paid by the Alert Transaction in satoshis. A non-negative integer. * alert_weight (mandatory): The weight of the Alert Transaction. A positive integer, not higher than 400,000. * recovery_tx (mandatory): The raw Recovery Transaction in uppercase hexadecimal format. A string of up to 800,000 characters. * recovery_txid (mandatory): The transaction ID of the Recovery Transaction. A 64-character lowercase hexadecimal string. * recovery_fee (mandatory): The total fee paid by the Recovery Transaction in satoshis. A non-negative integer. * recovery_weight (mandatory): The weight of the Recovery Transaction. A positive integer, not higher than 400,000. * recovery_outputs (mandatory): An array of up to 10,000 outputs from the Recovery Transaction. Each output is a tuple containing: [address, amount_sats, label?] where: ** address is a mandatory Bitcoin address string (up to 100 characters). ** amount_sats is a mandatory positive integer representing the amount in satoshis. ** label is an optional string of up to 200 characters. * metadata (optional): A string of up to 10,000 characters for additional metadata, for example a digital-signature. * checksum (mandatory): A checksum for verifying the integrity of the plan. A string of 8 to 64 characters. === Checksum Calculation === Notice that besides the top-level JSON object, all the internal values are either primitive or arrays. This is intentional, so a conversion of the values to JSON strings will be deterministic. The checksum is calculated by converting the top-level JSON object to an array of [key, value] pairs, sorting the array, stringifying, calculating the SHA256 hash of the result in lowercase hexadecimal format, and taking a prefix of at least 8 characters. "stringifying" in this context means converting the array to a JSON string following [https://262.ecma-international.org/16.0/index.html#sec-json.stringify ECMAScript's JSON.stringify function specification] (without additional replacer or space arguments). This specification covers special cases such as non-ascii characters and newlines. Optional fields without a value should not be included in the key-value pairs array. Also, there should not be a key-value pair for the "checksum" field itself. Code example: delete recoveryPlanJson.checksum; // In case the checksum was calculated previously and the object was then modified const checksumData = new TextEncoder().encode( JSON.stringify(Object.entries(recoveryPlanJson).sort()), ); const checksum = new Uint8Array(await crypto.subtle.digest('SHA-256', checksumData)); recoveryPlanJson.checksum = Array.from(checksum).map(b => b.toString(16).padStart(2, '0')).join('').slice(0, 8); Checksum hex string should be at least 8 characters long. Wallets may choose to use a longer checksum. == Rationale == The JSON object will contain the raw transactions, in addition to other information - some of which could technically be extracted from the raw transactions. This is intentional, to let frontend UIs display the plan before uploading it to any service, without the need for complicated parsing in the frontend. Backend services that receive the JSON object for monitoring/execution are expected to validate that the information is consistent with the raw transactions. Also, if some wallet apps did not implement the specifications correctly, the services could write custom code based on the wallet_kind, wallet_version and plugin_version fields. Servers may decide to put more restrictions on JSON objects, for example to refuse storing very large transactions. Notice that the raw transactions (alert_tx and recovery_tx) are expected to be in uppercase hexadecimal format. This is useful for frontend UIs to display them as QR codes, which are more compact when using uppercase-only alphanumeric characters. === Monitoring Timelock-Recovery Plans === Checking whether the Alert Transaction is valid is trivial, via the testmempoolaccept RPC call in bitcoin core 0.17+. However, checking whether the Recovery Transaction is valid is more complex, since it depends on a UTXO created by the Alert Transaction. The testmempoolaccept RPC can receive a list of transactions in which the later transactions may depend on earlier transactions - however in our case the Recovery Transaction has an nSequence relative-locktime, and therefore calling testmempoolaccept 'alert-tx' 'recovery-tx' will fail, claiming that the Alert Transaction UTXO is not confirmed (and the required time window has not passed). We recommend services that want to verify the entire Timelock-Recovery plan to parse the Recovery Transaction and check its signatures manually, and reject complicated spending scripts. Discovering that the Recovery Transaction is invalid only at the time of execution, could lead to funds being locked forever. == Reference Implementation == JSON files can be generated using the Timelock Recovery plugin on [https://electrum.org Electrum Wallet]: https://github.com/spesmilo/electrum/tree/master/electrum/plugins/timelock_recovery Demo Video: https://drive.google.com/file/d/10uXRouQbH1kz_HC14WnmRnYHa3gPZY8l/preview Example JSON file: { "kind": "timelock-recovery-plan", "id": "exported-692452189b301b561ed57cbe", "name": "Recovery Plan ac300e72-7612-497e-96b0-df2fdeda59ea", "description": "RITREK APP 1.1.0: Trezor Account #1", "created_at": "2025-11-24T12:39:53.532Z", "plugin_version": "1.0.1", "wallet_version": "1.0.1", "wallet_name": "RITREK Service", "wallet_kind": "RITREK BACKEND", "timelock_days": 2, "anchor_amount_sats": 600, "anchor_addresses": [ "bc1qnda6x2gxdh3yujd2zjpsd7qzx3awxmlaf9wwlk" ], "alert_address": "bc1qj0f9sjenwyjs0u7mlgvptjp05z3syzq7mru3ep", "alert_inputs": [ "a265a485df4c6417019b91379257eb387bceeda96f7bb6311794b8ed358cf104:0", "2f621c2151f33173983133cbc1000e3b603b8a18423b0379feffe8513171d5d3:0" ], "alert_tx": "0200000000010204F18C35EDB8941731B67B6FA9EDCE7B38EB579237919B0117644CDF85A465A20000000000FDFFFFFFD3D5713151E8FFFE79033B42188A3B603B0E00C1CB3331987331F351211C622F0000000000FDFFFFFF0258020000000000001600149B7BA329066DE24E49AA148306F802347AE36FFD205600000000000016001493D2584B33712507F3DBFA1815C82FA0A302081E02483045022100DCDBAE77C35EB4A0B3ED0DE5484206AB6B07041BE99B2BBAF0243C125916523C0220396959C3C52B2B1F9E472AEEE7C5D9540531B131C3221DE942754C6D0941397D012103C08FF3ADBA14B742646572BCA6F07AEB910666FB28E4DDDC40E33755E7C869D30248304502210089084472FDA3CF82D6ABC11BF1A5E77C9B423617C8B840F58C02746035B3BA6302203942AA1FA13F952F49FB114D48130A9AAF70151E7D09036D15734DB1F41A8B6001210397064EDED7DAD7D662290DC2847E87C5C27DA8865B89DDB58FDE9A006BA7DB3900000000", "alert_txid": "f1413fedadaf30697820bcd8f6a393fcc73ea00a15bea3253f89d5658690d2f7", "alert_fee": 231, "alert_weight": 834, "recovery_tx": "02000000000101F7D2908665D5893F25A3BE150AA03EC7FC93A3F6D8BC20786930AFADED3F41F101000000005201400001A6550000000000001600149B7BA329066DE24E49AA148306F802347AE36FFD0247304402204AFF87C2127F5697F300C6522067A8D5E5290CA8D140D2E5BCEF4A36606C5FE5022056673BEC5BB459DFFBD4D266EE95AEF0D701383ED80BD433A02C3C486A826D76012102774DBCD59F2D08EFF718BC09972ADC609FBC31C26B551B3E4EA30A1D43EEDB9700000000", "recovery_txid": "bc304610e8f282036345e87163d4cba5b16488a3bf2e4d738379d7bda3a0bca3", "recovery_fee": 122, "recovery_weight": 437, "recovery_outputs": [ [ "bc1qnda6x2gxdh3yujd2zjpsd7qzx3awxmlaf9wwlk", 21926, "My Backup Wallet" ] ], "metadata": "sig:825d6b3858c175c7fc16da3134030e095c4f9089c3c89722247eeedc08a7ef4f", "checksum": "92f8b3da" } == Copyright == This document is licensed under the 2-clause BSD license. ================================================ FILE: bip-0129.mediawiki ================================================
  BIP: 129
  Layer: Applications
  Title: Bitcoin Secure Multisig Setup (BSMS)
  Authors: Hugo Nguyen 
           Peter Gray 
           Marko Bencun 
           Aaron Chen 
           Rodolfo Novak 
  Status: Complete
  Type: Specification
  Assigned: 2020-11-10
  License: BSD-2-Clause
  Requires: 32, 174, 322, 380, 381, 382, 383
==Introduction== ===Abstract=== This document proposes a mechanism to set up multisig wallets securely. ===Copyright=== This BIP is licensed under the 2-clause BSD license. ===Motivation=== The Bitcoin multisig experience has been greatly streamlined under [https://github.com/bitcoin/bips/blob/master/bip-0174.mediawiki BIP-0174 (Partially Signed Bitcoin Transaction)]. However, what is still missing is a standardized process for setting up multisig wallets securely across different vendors. There are a number of concerns when it comes to setting up a multisig wallet: # Whether the multisig configuration, such as Signer membership, script type, derivation paths and number of signatures required, is correct and not tampered with. # Whether the keys or the multisig configuration are leaked during the setup. # Whether the Signer persists the multisig configuration in their respective storage, and under what format. # Whether the Signer's storage is tamper-proof. # Whether the Signer subsequently uses the multisig configuration to generate and verify receive and change addresses. An attacker who can modify the multisig configuration can steal or hold funds for ransom by duping the user into sending funds to the wrong address. An attacker who cannot modify the configuration but can learn about the keys and/or the configuration can monitor transactions in the wallet, resulting in loss of privacy. This proposal seeks to address concerns #1, #2 and #3: to mitigate the risk of tampering during the initial setup phase, and to define an interoperable multisig configuration format. Concerns #4 and #5 should be handled by Signers and are out of scope of this proposal. ==Specification== ===Prerequisites=== This proposal assumes the parties in the multisig support [https://github.com/bitcoin/bips/blob/master/bip-0032.mediawiki BIP-0032], [https://github.com/bitcoin/bips/blob/master/bip-0322.mediawiki BIP-0322], [https://github.com/bitcoin/bips/blob/master/bip-0380.mediawiki BIP-0380 Output Script Descriptors] ([https://github.com/bitcoin/bips/blob/master/bip-0381.mediawiki BIP-0381],[https://github.com/bitcoin/bips/blob/master/bip-0382.mediawiki BIP-0382],[https://github.com/bitcoin/bips/blob/master/bip-0383.mediawiki BIP-0383]) and [https://tools.ietf.org/html/rfc3686 AES encryption]. ===File Extensions=== All descriptor and key records should have a .bsms file extension. Encrypted data should have a .dat extension. ===Newline=== This specification uses line feed (LF) control character \n. ===Roles=== ====Coordinator==== The Coordinator initiates the multisig setup. The Coordinator determines what type of multisig is used and the exact policy script. If encryption is enabled, the Coordinator also distributes a shared secret or shared secrets to the parties involved for secure communication. The Coordinator gathers information from the Signers to generate a descriptor record. The Coordinator distributes the descriptor record back to the Signers. ====Signer==== The Signer is any software or hardware that controls the private keys and can sign using those keys. The Signer is a participating member in the multisig. Its responsibilities include providing its key record -- which contains a public key or an Extended Public Key (XPUB) -- to the Coordinator, verifying that its KEY is included in the descriptor record and persisting the descriptor record in its storage. ===Setup Process=== ====Round 1==== =====Coordinator===== * The Coordinator creates a new multisig wallet creation session. The Coordinator constructs the multisig script and its policy parameters, such as the required number of signatures and the total number of Signers (M and N). * The session should expire after some time period determined by the Coordinator, e.g., 24 hours. The timeout allows the encryption key to have lower entropy. * If encryption is enabled, the Coordinator distributes a secret TOKEN to each Signer over a secure channel. The Signer can use the TOKEN to derive an ENCRYPTION_KEY. Refer to the [[#Encryption]] section below for details on the TOKEN, the key derivation function and the encryption scheme. Depending on the use case, the Coordinator can decide whether to share one common TOKEN for all Signers, or to have one per Signer. * If encryption is disabled, the TOKEN is set to 0x00, and all the encryption/decryption steps below can be skipped. =====Signer===== * The Signer initiates the multisig wallet creation session by setting the TOKEN. The Signer derives an ENCRYPTION_KEY from the TOKEN. The Signer can keep the session open until a different value for the TOKEN is set. * The Signer generates a key record by prompting the user for a multisig derivation path and retrieves the KEY at that derivation path. Alternatively, the Signer can choose a path on behalf of the user. If the Signer chooses the path, it should try to avoid reusing KEYs for different wallets. * The first line in the record must be the specification version (BSMS 1.0 as of this writing). The second line must be the hex-encoded TOKEN. The third line must be the KEY. The KEY is a public key or an XPUB plus the key origin information, written in the descriptor-defined format, i.e.: [{master key fingerprint}/{derivation path}]{KEY}. The fourth line is a text description of the key, 80 characters maximum. The fifth line must be a SIG, whereas SIG is the signature generated by using the private key associated with the public key or XPUB to sign the first four lines. The signature should follow [https://github.com/bitcoin/bips/blob/master/bip-0322.mediawiki BIP-0322], legacy format accepted. * The Signer calculates the Message Authentication Code (MAC) for the record. The first 16 bytes of the MAC serves as the Initialization Vector (IV) for the encryption. * The Signer encrypts the key record with the ENCRYPTION_KEY and IV. * The Signer encodes the MAC and the ciphertext into hexadecimal format, then concatenates the results: (MAC || ciphertext). ====Round 2==== =====Coordinator===== * The Coordinator gathers key records from all participating Signers. The Coordinator verifies that there are exactly N unique key records before the wallet setup session expires. * For each key record, the Coordinator extracts the MAC from the data, sets IV to the first 16 bytes of the MAC, then decrypts the ciphertext using the ENCRYPTION_KEY and IV. * The Coordinator verifies that the included MAC is valid given the plaintext. * The Coordinator verifies that the key records have compatible specification versions. * The Coordinator verifies that the included SIG is valid given the KEY. * If all key records look good, the Coordinator fills in all necessary information to generate a descriptor record. * The first line in the descriptor record must be the specification version (BSMS 1.0 as of this writing). The second line must be a descriptor or a descriptor template. The third line must be a comma-separated list of derivation path restrictions. The paths must start with / and use non-hardened derivation. If there are no template or restrictions, it must say No path restrictions. The fourth line must be the wallet's first address. If there are path restrictions, use the first address from the first path restriction. * The Coordinator calculates the MAC for the record. The first 16 bytes of the MAC serves as the IV for the encryption.. * The Coordinator encrypts the descriptor record with the ENCRYPTION_KEY and IV. * The Coordinator encodes the MAC and the ciphertext into hexadecimal format, then concatenates the results: (MAC || ciphertext). * The Coordinator sends the encrypted descriptor record to all participating Signers. =====Signer===== * The Signer imports the descriptor record. * The Signer extracts the MAC from the data, sets IV to the first 16 bytes of the MAC, then decrypts the ciphertext using the ENCRYPTION_KEY (derived from the open session) and IV. * The Signer verifies that the included MAC is valid given the plaintext. * The Signer verifies that it can support the included specification version. * The Signer verifies that it can support the descriptor or descriptor template. * The Signer checks that its KEY is included in the descriptor or descriptor template, using path and fingerprint information provided. The check must perform an exact match on the KEYs and not using shortcuts such as matching fingerprints, which is trivial to spoof. * The Signer verifies that it is compatible with the derivation path restrictions. * The Signer verifies that the wallet's first address is valid. * For confirmation, the Signer must display to the user the wallet's first address and policy parameters, including, but not limited to: the derivation path restrictions, M, N, and the position(s) of the Signer's own KEY in the policy script. The total number of Signers, N, is important to prevent a KEY insertion attack. The position is important for scripts where KEY order matters. When applicable, all positions of the KEY must be displayed. The full descriptor or descriptor template must also be available for review upon user request. * Parties must check with each other that all Signers have the same confirmation (except for the KEY positions). * If all checks pass, the Signer must persist the descriptor record in its storage. This completes the setup. ===Encryption=== ====The Token==== We define three modes of encryption. # NO_ENCRYPTION : the TOKEN is set to 0x00. Encryption is disabled. # STANDARD : the TOKEN is a 64-bit nonce. # EXTENDED : the TOKEN is a 128-bit nonce. The TOKEN can be converted to one of these formats: * A decimal number (recommended). The number must not exceed the maximum value of the nonce. * A mnemonic phrase using [https://github.com/bitcoin/bips/blob/master/bip-0039.mediawiki BIP-0039] word list. This would be 6 words in STANDARD mode. This encoding is not recommended in EXTENDED mode as it can result in potential confusion between seed mnemonics and TOKEN mnemonics. * A QR code. * Other formats. The flexibility in the data format allows each Signer to customize the User Experience based on its respective capabilities. ====Key Derivation==== The key derivation function is [https://tools.ietf.org/html/rfc2898 PBKDF2], with PRF = SHA512. Specifically: DKey = PBKDF2(PRF, Password, Salt, c, dkLen) Whereas: * PRF = SHA512 * Password = "No SPOF" * Salt = TOKEN * c = 2048 * dkLen = 256 bits (32 bytes) * DKey = Derived ENCRYPTION_KEY ====Encryption Scheme==== The encryption scheme is [https://tools.ietf.org/html/rfc3686 AES-256-CTR]. MAC = HMAC-SHA256(HMAC_Key, hex-encoded TOKEN || Data) IV = First 16 bytes of MAC Ciphertext = AES-256-CTR-Encrypt(Plaintext, DKey, IV) Plaintext = AES-256-CTR-Decrypt(Ciphertext, DKey, IV) Whereas: * DKey = ENCRYPTION_KEY * HMAC_Key = SHA256(ENCRYPTION_KEY) * Data = the plaintext, e.g. the entire key record in round 1 and the entire descriptor record in round 2 The MAC is to be sent along with the key and descriptor record, as specified above. Because it is a MAC over the entire plaintext, this is essentially an [https://en.wikipedia.org/wiki/Authenticated_encryption#Encrypt-and-MAC_(E&M) Encrypt-and-MAC] form of authenticated encryption. ===Descriptor Template=== The output descriptor language only supports one-dimensional lists. This proposal introduces a descriptor template to represent multi-dimensional lists: XPUB/** Whereas /** can be replaced by any number of derivation path restrictions. A descriptor template must be accompanied by derivation path restrictions. Signers should expand the template into concrete descriptors by replacing /** with the restrictions. For example, the following template and derivation path restrictions: * wsh(sortedmulti(2,XPUB1/**,XPUB2/**)) * /0/*,/1/* Should translate to two concrete descriptors: * wsh(sortedmulti(2,XPUB1/0/*,XPUB2/0/*)) * wsh(sortedmulti(2,XPUB1/1/*,XPUB2/1/*)) ==QR Codes== For signers that use QR codes to transmit data, key and descriptor records can be converted to QR codes, following [https://github.com/BlockchainCommons/Research/blob/master/papers/bcr-2020-005-ur.md the BCR standard]. Also refer to [https://github.com/BlockchainCommons/Research/blob/master/papers/bcr-2020-015-account.md UR Type Definition for BIP44 Accounts] and [https://github.com/BlockchainCommons/Research/blob/master/papers/bcr-2020-010-output-desc.md UR Type Definition for Bitcoin Output Descriptors] for more details. ==Compatibility== This specification is not backwards compatible with existing multisig implementations. BSMS is opt-in, meaning existing multisig implementations can continue working as-is, with the caveat that they are likely to have various pitfalls. Some of the problems with existing solutions have been described in the [[#Motivation]] section. To comply with this standard, a Signer must be able to persist the descriptor record in its storage. To use BSMS for a multisig wallet, the user should wait until all participating Signers in the multisig have implemented BSMS. ==Security== This proposal introduces two layers of protection. The first one is a temporary, secret TOKEN. The second one is the confirmation of the wallet's first address. The TOKEN is used to encrypt the two rounds of communication between the Signer and the Coordinator. A MAC is also generated from the TOKEN and plaintext to authenticate the data being exchanged. The TOKEN is only needed during the setup phase, and can be safely discarded afterwards. It is not recommended to use the same TOKEN for multiple wallet creation sessions. The wallet's first address, on the other hand, can be used to verify the integrity of the multisig configuration. An attacker who tampers with the multisig configuration must also change the wallet's first address. Parties must check with each other that all Signers confirm to the same address and policy parameters to reduce the chance of tampering. ==Privacy== Encryption helps improve the privacy of the wallet by avoiding sharing keys and descriptors in plaintext. If the parties wish to have stronger privacy, it is recommended to use a higher number of bits for the TOKEN, and to completely erase knowledge of the TOKEN after the multisig wallet has been set up. ==Test Vectors== ===Mode: NO_ENCRYPTION with Public Keys=== ====ROUND 1==== * Coordinator ** M-of-N: 1/2 ** ADDRESS_TYPE: NATIVE_SEGWIT ** TOKEN: 0x00 * Signer 1 ** MASTER_KEY_FINGERPRINT: 59865f44 ** PRIVATE_KEY (m/48'/0'/0'/2'): L5TXU4SdD9e6QGgBjxeegJKxt4FgATLG1TCnFM8JLyEkFuyHEqNM ** Public Key (m/48'/0'/0'/2'): 026d15412460ba0d881c21837bb999233896085a9ed4e5445bd637c10e579768ba ** Legacy signature ** signer_1_key.bsms:
BSMS 1.0
00
[59865f44/48'/0'/0'/2']026d15412460ba0d881c21837bb999233896085a9ed4e5445bd637c10e579768ba
Signer 1 key
H6DXgqkCb353BDPkzppMFpOcdJZlpur0WRetQhIBqSn6DFzoQWBtm+ibP5wERDRNi0bxxev9B+FIvyQWq0s6im4=
* Signer 2 ** MASTER_KEY_FINGERPRINT: b7044ca6 ** PRIVATE_KEY (m/48'/0'/0'/2'): KwT7BZDWjos4JAdfKi8NqF46Kj3rppTwN8KGhPbzmmugiZioFW3r ** Public Key (m/48'/0'/0'/2'): 030baf0497ab406ff50cb48b4013abac8a0338758d2fd54cd934927afa57cc2062 ** Legacy signature ** signer_2_key.bsms:
BSMS 1.0
00
[b7044ca6/48'/0'/0'/2']030baf0497ab406ff50cb48b4013abac8a0338758d2fd54cd934927afa57cc2062
Signer 2 key
H08mGNGN+NxX/snt+6eX2Q1HjjfDkOtotglshHi7xdsBdIrTVMCQbgQ5SdACNZ0B2AJcifK11nJj43SvaitSemI=
====ROUND 2==== * Coordinator ** my_multisig_wallet.bsms:
BSMS 1.0
wsh(sortedmulti(1,[59865f44/48'/0'/0'/2']026d15412460ba0d881c21837bb999233896085a9ed4e5445bd637c10e579768ba,[b7044ca6/48'/0'/0'/2']030baf0497ab406ff50cb48b4013abac8a0338758d2fd54cd934927afa57cc2062))#rzx9dffd
No path restrictions
bc1quqy523xu3l8che3s8vja8n33qtg0uyugr9l5z092s3wa50p8t7rqy6zumf
===Mode: NO_ENCRYPTION=== ====ROUND 1==== * Coordinator ** M-of-N: 2/2 ** ADDRESS_TYPE: NATIVE_SEGWIT ** TOKEN: 0x00 * Signer 1 ** MASTER_KEY_FINGERPRINT: 1cf0bf7e ** PRIVATE_KEY (m/48'/0'/0'/2'): L3q1sg7iso1L3QfzB1riC9bQpqMynWyBeuLLSKwCDGkHkahB7MgU ** XPUB (m/48'/0'/0'/2'): xpub6FL8FhxNNUVnG64YurPd16AfGyvFLhh7S2uSsDqR3Qfcm6o9jtcMYwh6DvmcBF9qozxNQmTCVvWtxLpKTnhVLN3Pgnu2D3pAoXYFgVyd8Yz ** Legacy signature ** signer_1_key.bsms:
BSMS 1.0
00
[1cf0bf7e/48'/0'/0'/2']xpub6FL8FhxNNUVnG64YurPd16AfGyvFLhh7S2uSsDqR3Qfcm6o9jtcMYwh6DvmcBF9qozxNQmTCVvWtxLpKTnhVLN3Pgnu2D3pAoXYFgVyd8Yz
Signer 1 key
IB7v+qi1b+Xrwm/3bF+Rjl8QbIJ/FMQ40kUsOOQo1SqUWn5QlFWbBD8BKPRetfo1L1N7DmYjVscZNsmMrqRJGWw=
* Signer 2 ** MASTER_KEY_FINGERPRINT: 4fc1dd4a ** PRIVATE_KEY (m/48'/0'/0'/2'): L4JNkJfLBDyWfTLbKJ1H3w56GUMsvdfjCkzRo5RHXfJ6bdHqm6cN ** XPUB (m/48'/0'/0'/2'): xpub6EebMbEps7ZcV3FYEnddRsvrFWDrt2tiPmCeM7pPXQEmphvq9ZfJ1LWFUDjf3vxCeBuPrfyGrMazWUsYsetrnHatQZVLJH7LsgCjtMqdzgj ** Legacy signature ** signer_2_key.bsms:
BSMS 1.0
00
[4fc1dd4a/48'/0'/0'/2']xpub6EebMbEps7ZcV3FYEnddRsvrFWDrt2tiPmCeM7pPXQEmphvq9ZfJ1LWFUDjf3vxCeBuPrfyGrMazWUsYsetrnHatQZVLJH7LsgCjtMqdzgj
Signer 2 key
HzUa4Z76PFHMl54flIIF3XKiHZ+KbWjjxCEG5G3ZqZSqTd6OgTiFFLqq9PXJXdfYm6/cnL8IVWQgjFF9DQhIqQs=
====ROUND 2==== * Coordinator ** my_multisig_wallet.bsms:
BSMS 1.0
wsh(sortedmulti(2,[1cf0bf7e/48'/0'/0'/2']xpub6FL8FhxNNUVnG64YurPd16AfGyvFLhh7S2uSsDqR3Qfcm6o9jtcMYwh6DvmcBF9qozxNQmTCVvWtxLpKTnhVLN3Pgnu2D3pAoXYFgVyd8Yz/**,[4fc1dd4a/48'/0'/0'/2']xpub6EebMbEps7ZcV3FYEnddRsvrFWDrt2tiPmCeM7pPXQEmphvq9ZfJ1LWFUDjf3vxCeBuPrfyGrMazWUsYsetrnHatQZVLJH7LsgCjtMqdzgj/**))
/0/*,/1/*
bc1qrgc6p3kylfztu06ysl752gwwuekhvtfh9vr7zg43jvu60mutamcsv948ej
===Mode: STANDARD Encryption=== ====ROUND 1==== * Coordinator ** M-of-N: 2/2 ** ADDRESS_TYPE: NATIVE_SEGWIT ** TOKEN (hex): a54044308ceac9b7 *** TOKEN (decimal): 11907592390080907703 *** TOKEN (mnemonic): pipe acquire around border prosper swift ** ENCRYPTION_KEY (hex): 7673ffd9efd70336a5442eda0b31457f7b6cdf7b42fe17f274434df55efa9839 * Signer 1 ** MASTER_KEY_FINGERPRINT: b7868815 ** PRIVATE_KEY (m/48'/0'/0'/2'): KyKvR9kf8r7ZVtdn3kB9ifipr6UKnTNTpWJkGZbHwARDCz5iZ39E ** XPUB (m/48'/0'/0'/2'): xpub6FA5rfxJc94K1kNtxRby1hoHwi7YDyTWwx1KUR3FwskaF6HzCbZMz3zQwGnCqdiFeMTPV3YneTGS2YQPiuNYsSvtggWWMQpEJD4jXU7ZzEh ** Legacy signature ** signer_1_key.bsms:
BSMS 1.0
a54044308ceac9b7
[b7868815/48'/0'/0'/2']xpub6FA5rfxJc94K1kNtxRby1hoHwi7YDyTWwx1KUR3FwskaF6HzCbZMz3zQwGnCqdiFeMTPV3YneTGS2YQPiuNYsSvtggWWMQpEJD4jXU7ZzEh
Signer 1 key
H8DYht5P6ko0bQqDV6MtUxpzBSK+aVHxbvMavA5byvLrOlCEGmO1WFR7k2wu42J6dxXD8vrmDQSnGq5MTMMbZ98=
* Signer 1 encryption ** HMAC_KEY (hex): 3d4c422806ba8964c9ee45070cd675c024d96648a0ddb4001325818c84951de2 ** MAC (hex): fbdbdb64e6a8231c342131d9f13dcd5a954b4c5021658fa5afcb3fc74dc82706 ** IV (hex) : fbdbdb64e6a8231c342131d9f13dcd5a ** CIPHERTEXT (hex): 53f491cfd1431c292d922ea5a5dec3eb8ddaa6ed38ae109e7b040f0f23013e89a89b4d27476761a01197a3277850b2bc1621ae626efe65f2081eec6eb571c4f787bf1c49d061b43f70fd73cb3f37fa591d2400973ac0644c8941a83f1d4155e98f01fa2fdeb9f86c2e2413154fd18566a28fb0d9d8bd6172efabcfa6dab09ee7029bf3dd43376df52c118a6d291ec168f4ec7f7df951dfc6135fd8cb4b234da62eaea6017dfe5ca418f083e02e3aba2962ba313ba17b6468c7672fb218329a9f3fe4e4887fb87dac57c63ebff0e715a44498d18de8afc10e1cfeb46a1fc65ce871fef8a43b289305433a90c342d025aa4c19454fcfbcf911e9e2f928d5affd0536a6ddc2e816 ** signer_1_key.dat:
fbdbdb64e6a8231c342131d9f13dcd5a954b4c5021658fa5afcb3fc74dc8270653f491cfd1431c292d922ea5a5dec3eb8ddaa6ed38ae109e7b040f0f23013e89a89b4d27476761a01197a3277850b2bc1621ae626efe65f2081eec6eb571c4f787bf1c49d061b43f70fd73cb3f37fa591d2400973ac0644c8941a83f1d4155e98f01fa2fdeb9f86c2e2413154fd18566a28fb0d9d8bd6172efabcfa6dab09ee7029bf3dd43376df52c118a6d291ec168f4ec7f7df951dfc6135fd8cb4b234da62eaea6017dfe5ca418f083e02e3aba2962ba313ba17b6468c7672fb218329a9f3fe4e4887fb87dac57c63ebff0e715a44498d18de8afc10e1cfeb46a1fc65ce871fef8a43b289305433a90c342d025aa4c19454fcfbcf911e9e2f928d5affd0536a6ddc2e816
* Signer 2 ** MASTER_KEY_FINGERPRINT: eedff89a ** PRIVATE_KEY (m/48'/0'/0'/2'): Kz1ijnkDXmc65NWTYdg47DDaQgSGJAPfhJG9Unm36oqZPpPXuNR6 ** XPUB (m/48'/0'/0'/2'): xpub6EhJvMneoLWAf8cuyLBLQiKiwh89RAmqXEqYeFuaCEHdHwxSRfzLrUxKXEBap7nZSHAYP7Jfq6gZmucotNzpMQ9Sb1nTqerqW8hrtmx6Y6o ** Legacy signature ** signer_2_key.bsms:
BSMS 1.0
a54044308ceac9b7
[eedff89a/48'/0'/0'/2']xpub6EhJvMneoLWAf8cuyLBLQiKiwh89RAmqXEqYeFuaCEHdHwxSRfzLrUxKXEBap7nZSHAYP7Jfq6gZmucotNzpMQ9Sb1nTqerqW8hrtmx6Y6o
Signer 2 key
H/IHW5dMGYsrRdYEz3ux+kKnkWBtxHzfYkREpnYbco38VnMvIxCbDuf7iu6960qDhBLR/RLjlb9UPtLmCMbczDE=
* Signer 2 encryption ** HMAC_KEY (hex): 3d4c422806ba8964c9ee45070cd675c024d96648a0ddb4001325818c84951de2 ** MAC (hex): 383d05b7351a2cef7cca2850450f5efbbc4a3f8ea35707dda87a3692f0f2ebae ** IV (hex) : 383d05b7351a2cef7cca2850450f5efb ** CIPHERTEXT (hex): 71860b7c69f3a7665c3c3e85c45735bff78535a37ec6610b724627c73696820d519a9251703b17626b63898580233bebbb310aedbc370224b044ee19600bfe583445a6f26fb9bb5790bae516892655adb0e5dfc12be4609c2e0818d4f1f3bfccc4cd1a36f419d6cd842c913ae81eef4865ad473c32c3ee69cd98d6d0a088e2abdd01fe68b5c0503bb9183f9a912506204e5a9c6bd5a1626ff7eac30312a0b85004307c525e52fa3ad45a0b02eabc8cfaea0215bb6e60ee5f32d6673955290e008fbaef362977a21fd9830e3a604f9bb318cdcde456eae91dbedaa069bcd1efb0f981d5b0e502bd4dada903205458a00914887226a8dde317c02a8be4342acb97a8fee79fbe23 ** signer_2_key.dat:
383d05b7351a2cef7cca2850450f5efbbc4a3f8ea35707dda87a3692f0f2ebae71860b7c69f3a7665c3c3e85c45735bff78535a37ec6610b724627c73696820d519a9251703b17626b63898580233bebbb310aedbc370224b044ee19600bfe583445a6f26fb9bb5790bae516892655adb0e5dfc12be4609c2e0818d4f1f3bfccc4cd1a36f419d6cd842c913ae81eef4865ad473c32c3ee69cd98d6d0a088e2abdd01fe68b5c0503bb9183f9a912506204e5a9c6bd5a1626ff7eac30312a0b85004307c525e52fa3ad45a0b02eabc8cfaea0215bb6e60ee5f32d6673955290e008fbaef362977a21fd9830e3a604f9bb318cdcde456eae91dbedaa069bcd1efb0f981d5b0e502bd4dada903205458a00914887226a8dde317c02a8be4342acb97a8fee79fbe23
====ROUND 2==== *Coordinator ** my_multisig_wallet.bsms:
BSMS 1.0
wsh(sortedmulti(2,[b7868815/48'/0'/0'/2']xpub6FA5rfxJc94K1kNtxRby1hoHwi7YDyTWwx1KUR3FwskaF6HzCbZMz3zQwGnCqdiFeMTPV3YneTGS2YQPiuNYsSvtggWWMQpEJD4jXU7ZzEh/**,[eedff89a/48'/0'/0'/2']xpub6EhJvMneoLWAf8cuyLBLQiKiwh89RAmqXEqYeFuaCEHdHwxSRfzLrUxKXEBap7nZSHAYP7Jfq6gZmucotNzpMQ9Sb1nTqerqW8hrtmx6Y6o/**))
/0/*,/1/*
bc1qhs4u273g4azq7kqqpe6vh5wfhasfmrq7nheyzsnq77humd7rwtkqagvakf
*Coordinator encryption ** HMAC_KEY (hex): 3d4c422806ba8964c9ee45070cd675c024d96648a0ddb4001325818c84951de2 ** MAC (hex): 734ce791b466861945e1ef6f74c63faec590793de54831f0036b28d08714b71a ** IV (hex) : 734ce791b466861945e1ef6f74c63fae ** CIPHERTEXT (hex): 273cad18a5e1eff37dba6d850749594c9a3fd32b2069e8c69983ea269c5044b6bcaea26d9dbc8ad5d28bb8abfa02e3bfc7632fcc5c2b76e9abb1982ff11295858cfe44a8b97110ae970f58fff3fb6477f38ca9609eec78eedb1d640eaba489fd5e41e787b8d0bde48f1fa99cca641cabbee0f513fb1040cb73df10a57c9a34e4efcb069cd4c75467442c15d878ed9f40e3dffb98294931a6da4f444ae46f739b7fe002ce19fcfe71b05b9783d797ba45d568febbc8a2b0850da67f349d8567342352e1712c3d2a7ea1b2721df5efdb844431f0e5dcfa4acacb194c20785c9bb6dde90d64352fc913e9073b3b416be713bcc7632c821bbfddafa6199d471c54fb899f347f5fc706787ccaa82332dc8b93aeb3de3497d8e5c75f0f5d718c74bc6f8194fe999948e517f1c98398d9cb907d200f1d045394704b074dfb10e587f54fd78e95ef4bcbe77bf1376b390c3f47c91c12b2ed14073ea56bceab41f924302e62183c456b06d96b3da30439cb4320c764a0d6d1b3dabc06fc ** my_multisig_wallet.dat:
734ce791b466861945e1ef6f74c63faec590793de54831f0036b28d08714b71a273cad18a5e1eff37dba6d850749594c9a3fd32b2069e8c69983ea269c5044b6bcaea26d9dbc8ad5d28bb8abfa02e3bfc7632fcc5c2b76e9abb1982ff11295858cfe44a8b97110ae970f58fff3fb6477f38ca9609eec78eedb1d640eaba489fd5e41e787b8d0bde48f1fa99cca641cabbee0f513fb1040cb73df10a57c9a34e4efcb069cd4c75467442c15d878ed9f40e3dffb98294931a6da4f444ae46f739b7fe002ce19fcfe71b05b9783d797ba45d568febbc8a2b0850da67f349d8567342352e1712c3d2a7ea1b2721df5efdb844431f0e5dcfa4acacb194c20785c9bb6dde90d64352fc913e9073b3b416be713bcc7632c821bbfddafa6199d471c54fb899f347f5fc706787ccaa82332dc8b93aeb3de3497d8e5c75f0f5d718c74bc6f8194fe999948e517f1c98398d9cb907d200f1d045394704b074dfb10e587f54fd78e95ef4bcbe77bf1376b390c3f47c91c12b2ed14073ea56bceab41f924302e62183c456b06d96b3da30439cb4320c764a0d6d1b3dabc06fc
===Mode: EXTENDED Encryption=== ====ROUND 1==== *Coordinator ** M-of-N: 2/3 ** ADDRESS_TYPE: NESTED_SEGWIT ** TOKEN for Signer 1 (hex): 108a2360adb302774eb521daebbeda5e *** TOKEN (decimal): 21984902443033505423410071144203475550 *** ENCRYPTION_KEY (hex): 63dc1e57dfdc21fa11109d5088be01fb8078a383d2296925ad2b7612b7179777 ** TOKEN for Signer 2 (hex): d3fabc873b98165254fe18a71b5335b0 *** TOKEN (decimal): 281769005132501859744421970528095647152 *** ENCRYPTION_KEY (hex): 3dc860a53471ec03af14617fef60921cf215b45a9d684462fa65b9d804ad3ee7 ** TOKEN for Signer 3 (hex): 78a7d5e7549453d719150de5459c9ce5 *** TOKEN (decimal): 160378811550692397333855096016467696869 *** ENCRYPTION_KEY (hex): 62b90b4c08c03a0ee872e57aae73f9acfafb6cc09d20b5c9bc0bafaef33619db * Signer 1 ** MASTER_KEY_FINGERPRINT: 793cc70b ** PRIVATE_KEY (m/48'/0'/0'/1'): L1ZEgZ4zNYxyNc8UyeqwyKW1UHVMp9sxwPgSi3s9SW8mc7KsiSwJ ** XPUB (m/48'/0'/0'/1'): xpub6ErVmcYYHmavsMgxEcTZyzN5sqth1ZyRpFNJC26ij1wYGC2SBKYrgt9yariSbn7HLRoZUvhUhmPfsRTPrdhhGFscpPZzmch6UTdmRP1aZUj ** Legacy signature ** signer_1_key.bsms:
BSMS 1.0
108a2360adb302774eb521daebbeda5e
[793cc70b/48'/0'/0'/1']xpub6ErVmcYYHmavsMgxEcTZyzN5sqth1ZyRpFNJC26ij1wYGC2SBKYrgt9yariSbn7HLRoZUvhUhmPfsRTPrdhhGFscpPZzmch6UTdmRP1aZUj
Signer 1 key
ILG47LpCtjoD9UxL87jo5QFqA90t8g9fDQp/KBojdKgPPGB1pMx2bf9hPdORNZIOdCc/2+Gs6AOs3BEK9ubIuBw=
* Signer 1 encryption ** HMAC_KEY (hex): 1162cdace4ac9fcde1f96924b93714143d057a701de83ebaed248d1c9154f9fd ** MAC (hex): ea12776c73de4bd5ea57c2d19eb8e0be856ac0d7f5651f7b74be4563d61ba5b1 ** IV (hex) : ea12776c73de4bd5ea57c2d19eb8e0be ** CIPHERTEXT (hex): a36f34232bff47a853092654a718fea4f5f57d6a1f3d38fede04e2414da12c90cefc24ef662f736886d9a7fd6e7db636ca47217803c86b7fbcebe4ad6b71cffc261069c135bd2b2430fb2b446ff0203df34fbbc6801243e8a930b9d0cd3a9b160b8dcdc9131ce6e97641e6314b3285ff341013f302e308c1b2eba7ced0103a8999fe2bd86f844392938e7926cd26d023b764d0b8ff92b2fbdf995884c738414b83563ef2a0050279bf46d0e8271ea5d6af8154847c5736129a7a83a35a3cc747b2be4b389886cb57456678353b60473ebc4ab85d9c9131a17a1e288717343d9008825b16c48d7e93927f37b530033192c67b70dec0411a3e5952d2525c7eb80721676e1a6299248c17f8078202f3bb0932e9f263b0ab ** signer_1_key.dat:
ea12776c73de4bd5ea57c2d19eb8e0be856ac0d7f5651f7b74be4563d61ba5b1a36f34232bff47a853092654a718fea4f5f57d6a1f3d38fede04e2414da12c90cefc24ef662f736886d9a7fd6e7db636ca47217803c86b7fbcebe4ad6b71cffc261069c135bd2b2430fb2b446ff0203df34fbbc6801243e8a930b9d0cd3a9b160b8dcdc9131ce6e97641e6314b3285ff341013f302e308c1b2eba7ced0103a8999fe2bd86f844392938e7926cd26d023b764d0b8ff92b2fbdf995884c738414b83563ef2a0050279bf46d0e8271ea5d6af8154847c5736129a7a83a35a3cc747b2be4b389886cb57456678353b60473ebc4ab85d9c9131a17a1e288717343d9008825b16c48d7e93927f37b530033192c67b70dec0411a3e5952d2525c7eb80721676e1a6299248c17f8078202f3bb0932e9f263b0ab
* Signer 2 ** MASTER_KEY_FINGERPRINT: b3118e52 ** PRIVATE_KEY (m/48'/0'/0'/1'): L4SnPjcHszMg3Wi2YYxEYnzM2zFeFkFr5NcLZ18YQeyJwaSFbTud ** XPUB (m/48'/0'/0'/1'): xpub6Du5Jn6eYZE96ccmAc1ZTFPzdnzrvqfG4mpamDun2qZYKywoiQJMCbS3kWWMr6U3XW6s125RLsaPABWgv2yA749ieaMe67FxkTjMsbcxCch ** Legacy signature ** signer_2_key.bsms:
BSMS 1.0
d3fabc873b98165254fe18a71b5335b0
[b3118e52/48'/0'/0'/1']xpub6Du5Jn6eYZE96ccmAc1ZTFPzdnzrvqfG4mpamDun2qZYKywoiQJMCbS3kWWMr6U3XW6s125RLsaPABWgv2yA749ieaMe67FxkTjMsbcxCch
Signer 2 key
IDK4d/oO0pgfrwRu4Zb8vqlPEmJb9aKT1K2CCnI3RKepVAKs3fZsBrypcCdQfUy1TG/3O5vAR3gjldxcCA1Wzg8=
* Signer 2 encryption ** HMAC_KEY (hex): 43a4e704bd1bade703023004b00290f1a7b005474a581d869a217068eedf3f57 ** MAC (hex): 4a3ff970d027010e83b4fbf2845a23907a301b3df692a9265e2ca679697ac718 ** IV (hex) : 4a3ff970d027010e83b4fbf2845a2390 ** CIPHERTEXT (hex): c8f4a6a6714eff90aa48cbefe6750c2ee3cc72182eb455e964f0ba59ada3ecd758c29f0fab7e33aaa82a340a18d9c793ddab09dc7e714864faac1ecea370d4f102533b739da38aa0491433f35eadec08f203685f04d1f6ec35d397d99e4f8096a5691075e3f54fd9ff58faf947f276bbe1031f827b274bd2f60fcb526add7058889104b189d7da22ac7be1f7ddd380bbebd5c6983a8a3c5fa86913e3d23c40935072ce03d9bdeb07791dc836d44b4d4c62f364d0e4f3580369ea8f6ebb774b7fda4a7ac6f5ae6b2f52b10cd71bdf3cdb5889e77d5eb1f2f647b798cdd6b3e5b964c9265daea3668d7e4cb53f724151923da1a87bbcd2abd8b164de474d865c51af69885431d26f88a5c8eea7d0dfdb52ca622017808a ** signer_2_key.dat:
4a3ff970d027010e83b4fbf2845a23907a301b3df692a9265e2ca679697ac718c8f4a6a6714eff90aa48cbefe6750c2ee3cc72182eb455e964f0ba59ada3ecd758c29f0fab7e33aaa82a340a18d9c793ddab09dc7e714864faac1ecea370d4f102533b739da38aa0491433f35eadec08f203685f04d1f6ec35d397d99e4f8096a5691075e3f54fd9ff58faf947f276bbe1031f827b274bd2f60fcb526add7058889104b189d7da22ac7be1f7ddd380bbebd5c6983a8a3c5fa86913e3d23c40935072ce03d9bdeb07791dc836d44b4d4c62f364d0e4f3580369ea8f6ebb774b7fda4a7ac6f5ae6b2f52b10cd71bdf3cdb5889e77d5eb1f2f647b798cdd6b3e5b964c9265daea3668d7e4cb53f724151923da1a87bbcd2abd8b164de474d865c51af69885431d26f88a5c8eea7d0dfdb52ca622017808a
* Signer 3 ** MASTER_KEY_FINGERPRINT: 842bd2ed ** PRIVATE_KEY (m/48'/0'/0'/1'): L1ehZHpo2UFHc1yaBWDU4bKVycUwcU2TESm92wbfq6xK6qpZZJP6 ** XPUB (m/48'/0'/0'/1'): xpub6Ex81KopPkEt9hJiWHabYy8LNsSR4A7sUQoFBk9dR8XxHrr4p9HrYWN3NCf5uwfopHnQkCG7FYnZMztKbtRtbh6tzZC4xtHPbmVVxRSN7ic ** Legacy signature ** signer_3_key.bsms:
BSMS 1.0
78a7d5e7549453d719150de5459c9ce5
[842bd2ed/48'/0'/0'/1']xpub6Ex81KopPkEt9hJiWHabYy8LNsSR4A7sUQoFBk9dR8XxHrr4p9HrYWN3NCf5uwfopHnQkCG7FYnZMztKbtRtbh6tzZC4xtHPbmVVxRSN7ic
Signer 3 key
IL77mML0xo/O9dJn0T5EpQLuyRPPrdpgVJbtsdAugW5iX0MQ3Ci0f8jVnXu68Xm07CYjYGKX8af72jmkQKhNud0=
* Signer 3 encryption ** HMAC_KEY (hex): ab93ce7bf0f91c62a66d00ea9bf5e5c00b854ee2cfc2fb06f6eeff738abcdc26 ** MAC (hex): e82cfcccbd4bd4d3b76e28133eecd13f7362f4a8b4c4baa3e5f6ba2dfb4d69b8 ** IV (hex) : e82cfcccbd4bd4d3b76e28133eecd13f ** CIPHERTEXT (hex): b44433f0b564ec35a1e71371f25844088084b47402c90d52fee7237167b58a60a28c234af9123e104773136e8446d799541c8566882787caee7cd1fa8628aba63aa9e9d7cca0ddee92f96dd881535b19a131a1f487a1909e42d62945fd0ba08dacd7dc09a22ffe47e0410b8b85df92e4a8bbf9b46f0062da02e3ae94144a00bae917acc1246d8d1a4dca105708f55379caefef9d4c152f56b65ab4bd7b48f60233f57ba6d705387c79aeaa2a279e3314004bf16fcd7e7d2adef34b0ab3c22bc5461f2c09dce69065605e4fb96958c55984391712b3547e3914ad4ecca2c088be280dfcfe374a112515674aeca57b885e81dbef6a353ca387f4514db3158eb69f0d2725d42ad8102c05c26ad501d48b889c624035ead4 ** signer_3_key.dat:
e82cfcccbd4bd4d3b76e28133eecd13f7362f4a8b4c4baa3e5f6ba2dfb4d69b8b44433f0b564ec35a1e71371f25844088084b47402c90d52fee7237167b58a60a28c234af9123e104773136e8446d799541c8566882787caee7cd1fa8628aba63aa9e9d7cca0ddee92f96dd881535b19a131a1f487a1909e42d62945fd0ba08dacd7dc09a22ffe47e0410b8b85df92e4a8bbf9b46f0062da02e3ae94144a00bae917acc1246d8d1a4dca105708f55379caefef9d4c152f56b65ab4bd7b48f60233f57ba6d705387c79aeaa2a279e3314004bf16fcd7e7d2adef34b0ab3c22bc5461f2c09dce69065605e4fb96958c55984391712b3547e3914ad4ecca2c088be280dfcfe374a112515674aeca57b885e81dbef6a353ca387f4514db3158eb69f0d2725d42ad8102c05c26ad501d48b889c624035ead4
====ROUND 2==== * Coordinator ** my_multisig_wallet.bsms:
BSMS 1.0
sh(wsh(multi(2,[793cc70b/48'/0'/0'/1']xpub6ErVmcYYHmavsMgxEcTZyzN5sqth1ZyRpFNJC26ij1wYGC2SBKYrgt9yariSbn7HLRoZUvhUhmPfsRTPrdhhGFscpPZzmch6UTdmRP1aZUj/**,[b3118e52/48'/0'/0'/1']xpub6Du5Jn6eYZE96ccmAc1ZTFPzdnzrvqfG4mpamDun2qZYKywoiQJMCbS3kWWMr6U3XW6s125RLsaPABWgv2yA749ieaMe67FxkTjMsbcxCch/**,[842bd2ed/48'/0'/0'/1']xpub6Ex81KopPkEt9hJiWHabYy8LNsSR4A7sUQoFBk9dR8XxHrr4p9HrYWN3NCf5uwfopHnQkCG7FYnZMztKbtRtbh6tzZC4xtHPbmVVxRSN7ic/**)))
/0/*,/1/*
3GzMtFXahiu4TpGNGFc4bHMvAcvz5vVQrT
* Send to Signer 1: ** HMAC_KEY (hex): 1162cdace4ac9fcde1f96924b93714143d057a701de83ebaed248d1c9154f9fd ** MAC (hex): 01bf557b6d44b3fbf07f8ec155cbdec42d85d856e174342563dd83b40ad7c025 ** IV (hex) : 01bf557b6d44b3fbf07f8ec155cbdec4 ** CIPHERTEXT (hex): 617ed25b4b8fd88b806cbebcc1731b071465514a805f7ba2de60e291bc9493f31aa0f9b0665ba822cf9a2e21c02649b5c3f7dbad317ae898292cb6fe992520f68c0ebe9d1434b348af10453f1be0a392a616d43ba21e5e7fa3c995dce54db947fe5dbad4a9a77f37b3aef58c54ee3e496c8312d3033359aed0de8cf28b82035ee7a38c9b23c9d95682fb15936bf2247546d2ba9b3ada605f5c89f0a3bbaa86cb4b5dded9a65004912c0afbbfd01f0115447f5625e8523f9de16165d32c4b21103d8ac965e2f7e17641ee1a8c5902e8dbb461c6c7d05141f7bba66b8b3608037fb251b55fa461c9441c6427921545a34a1798127d5bf9cc92423f7e62c769e232c65db8cc5124577012d49941143c3b4758212a8afa0475c9b3597da2e99d585039339b7d73611aa277878d212875051683053db9c630391e0b32356523e9fa8a58a334e16fe6650472f336ddaa8c587992b6c0c0e480b680261579a11cf9d036614abc113dde53653273f5ce82ea0bc10e38ca52ac66838aa49ff46c3a7d5096db439c15d3c2e8de55e4ac7315a57eb9997f219c378af86c858867ce583ed84e4d9c68aecfbca9ebff16b0ac91531125e273b215db688ffe52c8033eb78914b87c0fa2001c52e90c92765712e50384ddcf4d0953ac3cc8137abcb2a85d603a6cc207472677 ** my_multisig_wallet_for_signer_1.dat:
01bf557b6d44b3fbf07f8ec155cbdec42d85d856e174342563dd83b40ad7c025617ed25b4b8fd88b806cbebcc1731b071465514a805f7ba2de60e291bc9493f31aa0f9b0665ba822cf9a2e21c02649b5c3f7dbad317ae898292cb6fe992520f68c0ebe9d1434b348af10453f1be0a392a616d43ba21e5e7fa3c995dce54db947fe5dbad4a9a77f37b3aef58c54ee3e496c8312d3033359aed0de8cf28b82035ee7a38c9b23c9d95682fb15936bf2247546d2ba9b3ada605f5c89f0a3bbaa86cb4b5dded9a65004912c0afbbfd01f0115447f5625e8523f9de16165d32c4b21103d8ac965e2f7e17641ee1a8c5902e8dbb461c6c7d05141f7bba66b8b3608037fb251b55fa461c9441c6427921545a34a1798127d5bf9cc92423f7e62c769e232c65db8cc5124577012d49941143c3b4758212a8afa0475c9b3597da2e99d585039339b7d73611aa277878d212875051683053db9c630391e0b32356523e9fa8a58a334e16fe6650472f336ddaa8c587992b6c0c0e480b680261579a11cf9d036614abc113dde53653273f5ce82ea0bc10e38ca52ac66838aa49ff46c3a7d5096db439c15d3c2e8de55e4ac7315a57eb9997f219c378af86c858867ce583ed84e4d9c68aecfbca9ebff16b0ac91531125e273b215db688ffe52c8033eb78914b87c0fa2001c52e90c92765712e50384ddcf4d0953ac3cc8137abcb2a85d603a6cc207472677
* Send to Signer 2: ** HMAC_KEY (hex): 43a4e704bd1bade703023004b00290f1a7b005474a581d869a217068eedf3f57 ** MAC (hex): 974ba77900c43c463dadaa6eaf24aaeb1b25b443cf155229b719bcbf8b343092 ** IV (hex) : 974ba77900c43c463dadaa6eaf24aaeb ** CIPHERTEXT (hex): 86288c97a6341974a35015f97fbbc8db7655639c839fc438706f82fce36a82dd17e2d4d4a674516c4fc5c3a33d6097dd8fc5c6605018946741ed9f58d8fe530a808f16f0dd705cacfd273e34a158bd7566774dd31506b8280e448fabb72d0e7dfc05cee1142b61921dfaf0b0039d885cc0aa76c429025efc2ba49a8af15b58e75a5a83ba4838a9a4c9f13725f5aecefd8511513d93797f37b93150b9dca725685883188e39142dd8d3cf4b617c7936bdb3875415bbf6dfb2fe1a39ae2aed9fd2909aebd0355a5cc9a55bcb84048c851a1873948e495180f336edeb63f54bcf83feaa4d2453251260e24293e49815c2369c1c045083c412c973987fd7c9296a71cda424823ed32380ba442394500b7d2d2335818099090aaf08ca4e180869c546f58da4cb4ff0f95b796a35c40ea455e2ddd3e08bc494ffddc706aaf4d479f4f359e6a89a90df7c9b8f23cab355855a72b90795a0db83a96bce0dd4f77e3f58c0957b4ffe9663251565098e6c31fd4bbf3e1295faaff05e29912d9c37cb944da379a9b2193b466910d05a681e53a2dbe5aa18a2b4874153fe36d8a1aa4cc6e612bd6dbc9abb8e1e61b927fc5458d8e1be9536cd462e4c37672af7928c39e94bdc124a2da7b1bd3cad2cfe559adc33e62eb45bff89db8a47a72dda4f49f21c01a9432f4802a1 ** my_multisig_wallet_for_signer_2.dat:
974ba77900c43c463dadaa6eaf24aaeb1b25b443cf155229b719bcbf8b34309286288c97a6341974a35015f97fbbc8db7655639c839fc438706f82fce36a82dd17e2d4d4a674516c4fc5c3a33d6097dd8fc5c6605018946741ed9f58d8fe530a808f16f0dd705cacfd273e34a158bd7566774dd31506b8280e448fabb72d0e7dfc05cee1142b61921dfaf0b0039d885cc0aa76c429025efc2ba49a8af15b58e75a5a83ba4838a9a4c9f13725f5aecefd8511513d93797f37b93150b9dca725685883188e39142dd8d3cf4b617c7936bdb3875415bbf6dfb2fe1a39ae2aed9fd2909aebd0355a5cc9a55bcb84048c851a1873948e495180f336edeb63f54bcf83feaa4d2453251260e24293e49815c2369c1c045083c412c973987fd7c9296a71cda424823ed32380ba442394500b7d2d2335818099090aaf08ca4e180869c546f58da4cb4ff0f95b796a35c40ea455e2ddd3e08bc494ffddc706aaf4d479f4f359e6a89a90df7c9b8f23cab355855a72b90795a0db83a96bce0dd4f77e3f58c0957b4ffe9663251565098e6c31fd4bbf3e1295faaff05e29912d9c37cb944da379a9b2193b466910d05a681e53a2dbe5aa18a2b4874153fe36d8a1aa4cc6e612bd6dbc9abb8e1e61b927fc5458d8e1be9536cd462e4c37672af7928c39e94bdc124a2da7b1bd3cad2cfe559adc33e62eb45bff89db8a47a72dda4f49f21c01a9432f4802a1
* Send to Signer 3: ** HMAC_KEY (hex): ab93ce7bf0f91c62a66d00ea9bf5e5c00b854ee2cfc2fb06f6eeff738abcdc26 ** MAC (hex): bb3c93b67d758f244de7ee73e5e61261cea6dff5b3852df8faf265cdf1c73dae ** IV (hex) : bb3c93b67d758f244de7ee73e5e61261 ** CIPHERTEXT (hex): 7ac33bd9719a3cef6c68e09b3c9677565418933f188bbe50dc70f46329706732fe28ab230468e2a8798d3fbf641867d5b3322113204a372e7650ed06cf94d6df5cc7425b1b3a07690a32e12fd9cdad2c9f42d496c1b02215a7d8d63565aa4935bb2b087af39eebc02d4a2d30a4dbf1e72b9a0dab11473c7254ecf9065eb4f9d80a164c489d5fdae0d15d97b6100b79c3999b91341dfb4f599f738d4d631ae413c17b55daa09a67cb34b40d89c26f0e95ddfbf416033f869da32e502815d720bb342ec1c0e5c6910c598f32162016229cd37ea030b4d3b60f560105abb75531dc960ddf6830c26604c67c2da05b8adc45297dda58b2da4671104969b819cdf1c362bc20d7bdfe4a2fbdb79b4a69e285434d991c269e3d23ce3d95675a0acbec2cae04a310581148d3422c1c0a621fb6d79ecac1743b0e76837389b67cd4734ec5ab560c43a183de35fa98834e1f347a0c0c9b14273b76233f55f04553efcde873de92d766f3cdc5e56bc649bf0cc4951f051619ee9b931cd3872044b0e62ea2c2dacad978dbb8df3afa0b9386535278c295c6a30a56950e57f805770568e937ffafbadb226120991d5ec10effa9f4334800010d141a2ddddc00ac743efa821af37f69840487e4db48036c1e0730788cddbca2f68b3769ec6989d76161e6605af50651b6e86e ** my_multisig_wallet_for_signer_3.dat:
bb3c93b67d758f244de7ee73e5e61261cea6dff5b3852df8faf265cdf1c73dae7ac33bd9719a3cef6c68e09b3c9677565418933f188bbe50dc70f46329706732fe28ab230468e2a8798d3fbf641867d5b3322113204a372e7650ed06cf94d6df5cc7425b1b3a07690a32e12fd9cdad2c9f42d496c1b02215a7d8d63565aa4935bb2b087af39eebc02d4a2d30a4dbf1e72b9a0dab11473c7254ecf9065eb4f9d80a164c489d5fdae0d15d97b6100b79c3999b91341dfb4f599f738d4d631ae413c17b55daa09a67cb34b40d89c26f0e95ddfbf416033f869da32e502815d720bb342ec1c0e5c6910c598f32162016229cd37ea030b4d3b60f560105abb75531dc960ddf6830c26604c67c2da05b8adc45297dda58b2da4671104969b819cdf1c362bc20d7bdfe4a2fbdb79b4a69e285434d991c269e3d23ce3d95675a0acbec2cae04a310581148d3422c1c0a621fb6d79ecac1743b0e76837389b67cd4734ec5ab560c43a183de35fa98834e1f347a0c0c9b14273b76233f55f04553efcde873de92d766f3cdc5e56bc649bf0cc4951f051619ee9b931cd3872044b0e62ea2c2dacad978dbb8df3afa0b9386535278c295c6a30a56950e57f805770568e937ffafbadb226120991d5ec10effa9f4334800010d141a2ddddc00ac743efa821af37f69840487e4db48036c1e0730788cddbca2f68b3769ec6989d76161e6605af50651b6e86e
==Acknowledgement== Special thanks to Pavol Rusnak, Dmitry Petukhov, Christopher Allen, Craig Raw, Robert Spigler, Gregory Sanders, Ta Tat Tai, Michael Flaxman, Pieter Wuille, Salvatore Ingala, Ava Chow and others for their feedback on the specification. ==References== Related mailing list threads: * https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2021-February/018385.html * https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2021-April/018732.html ================================================ FILE: bip-0130.mediawiki ================================================
  BIP: 130
  Layer: Peer Services
  Title: sendheaders message
  Authors: Suhas Daftuar 
  Status: Deployed
  Type: Specification
  Assigned: 2015-05-08
  License: PD
==Abstract== Add a new message, "sendheaders", which indicates that a node prefers to receive new block announcements via a "headers" message rather than an "inv". ==Motivation== Since the introduction of "headers-first" downloading of blocks in 0.10, blocks will not be processed unless they are able to connect to a (valid) headers chain. Consequently, block relay generally works as follows: # A node (N) announces the new tip with an "inv" message, containing the block hash # A peer (P) responds to the "inv" with a "getheaders" message (to request headers up to the new tip) and a "getdata" message for the new tip itself # N responds with a "headers" message (with the header for the new block along with any preceding headers unknown to P) and a "block" message containing the new block However, in the case where a new block is being announced that builds on the tip, it would be generally more efficient if the node N just announced the block header for the new block, rather than just the block hash, and saved the peer from generating and transmitting the getheaders message (and the required block locator). In the case of a reorg, where 1 or more blocks are disconnected, nodes currently just send an "inv" for the new tip. Peers currently are able to request the new tip immediately, but wait until the headers for the intermediate blocks are delivered before requesting those blocks. By announcing headers from the last fork point leading up to the new tip in the block announcement, peers are able to request all the intermediate blocks immediately. ==Specification== # The sendheaders message is defined as an empty message where pchCommand == "sendheaders" # Upon receipt of a "sendheaders" message, the node will be permitted, but not required, to announce new blocks by sending the header of the new block (along with any other blocks that a node believes a peer might need in order for the block to connect). # Feature discovery is enabled by checking protocol version >= 70012 ==Additional constraints== As support for sendheaders is optional, software that implements this may also optionally impose additional constraints, such as only honoring sendheaders messages shortly after a connection is established. ==Backward compatibility== Older clients remain fully compatible and interoperable after this change. ==Implementation== https://github.com/bitcoin/bitcoin/pull/6494 ==Copyright== This document is placed in the public domain. ================================================ FILE: bip-0131.mediawiki ================================================
  BIP: 131
  Layer: Consensus (hard fork)
  Title: "Coalescing Transaction" Specification (wildcard inputs)
  Authors: Chris Priest 
  Status: Closed
  Type: Specification
  Assigned: 2015-11-30
  License: PD
==Abstract== This specification defines a new type of transaction that supplements (not replaces) normal "non coalescing" bitcoin transactions. ==Motivation== Normal "non-coalescing" Bitcoin Transactions have one large inefficiency: When you want to spend from multiple inputs with the exact same scriptPubKey, you have to list each input separately, along with the same signature multiple times, even though the signature expresses the same information. This bloats the transaction size and makes it expensive to spend from small value inputs. Because small value inputs are expensive to send, they remain in the UTXO pool which full nodes have to keep around. It is believed that long term increase of the UTXO set can have negative scaling consequences on the network. If maximum blocksize is made to increase *slower* than the actual number of transactions bitcoin users are sending to the network, this problem is projected to get worse. In other words, as transaction fees increase, the minimum economical value of a spending a UTXO will increase. ==Specification== === Redefinition of Transaction version === First, this BIP redefines the version field on transactions. The first four bytes are defined as the version number, while the last four bytes are defined as the transaction type. Type "0000" denotes normal transactions, and "0001" defines coalescing transaction. Examples: version 1 transaction with normal inputs: version: 10000000 version 2 transaction with normal inputs: version: 20000000 version 2 transaction with coalescing inputs: version: 20000001 Essentially the last bit in the version field is set to 1 to enable wildcard inputs for all inputs present in the transaction. === Wildcard inputs === A coalescing transaction is formulated the exact same way as a version 1 transaction with one exception: each input is treated as a "wildcard input". A wildcard input being the value of all inputs with the exact same scriptPubKey in a block lower or equal to the block the wildcard input is confirmed into. == Changes needed to implement == The bitcoin code needs to be modified in three places in order to handle Coalescing Transactions. 1. Full Node Coalescing validation - When a full node receives a coalescing transaction, it has to aggregate the value of all the UTXOs in the blockchain older than the input with the same scriptPubKey. If this value is greater than or equal to the amount of all outputs, then that coalescing transaction is valid and can be propagated. 2. Full Node Non-Coalescing validation - When a non-coalescing transaction comes in, the code needs to be modified to check if each input has not been spent by a coalescing transaction. If there exist any coalescing transaction in the blockchain with the same scriptPubKey found in a block *after* that input, then the UTXO has been spent and the transaction is invalid. 3. Wallet - The user facing wallet portion of the reference client should notify the user when their wallet contains many UTXOs that qualify it to benefit from a coalescing transaction. Wallets should not simply replace non-coalescing transactions with coalescing transactions in all instances. == Isn't this BIP bad because it encourage address re-use? == Address re-use comes in two forms: re-use by the ''sender'', and re-use by the ''receiver''. Re-use by the sender is basically using the same address for the change output. This is generally considered bad since people looking through your transaction history can determine who you do business with. When you generate a new address for every change, your privacy is conserved as it is impossible to know which output is a recipient, and which output is the change output. This BIP has '''no effect''' on re-use by the sender. On the other hand, address re-use by the ''receiver'' occurs under completely different circumstances. When you publish an address and have multiple people send to that address, you are engaging in address re-use from the receiver. This activity has historically been considered bad because it leads to re-using a private key. When you re-use a private key too many times, you run the risk of an attacker performing statistical analysis on the multiple signatures, which can lead to an attacker finding out your private key. This BIP introduces a way to spend multiple inputs ''without'' re-using the private key. In a sense, this BIP fixes the problem that makes address re-use bad for the receiver. After this BIP becomes implemented and deployed, address re-use by the receiver will no longer be considered bad form. ==Copyright== This document is placed in the public domain. ================================================ FILE: bip-0132.mediawiki ================================================
  BIP: 132
  Title: Committee-based BIP Acceptance Process
  Authors: Andy Chase 
  Status: Closed
  Type: Process
  Assigned: 2015-08-31
  License: PD
== Abstract == The current process for accepting a BIP is not clearly defined. While [https://github.com/bitcoin/bips/blob/master/bip-0001.mediawiki BIP-0001] defines the process for writing and submitting a Bitcoin Improvement Proposal to the community it does not specify the precise method for which BIPs are considered accepted or rejected. This proposal sets up a method for determining BIP acceptance. This BIP has two parts: * It sets up a '''process''' which a BIP goes through for comments and acceptance. The Process is: ** BIP Draft ** Submitted for comments (2 weeks) ** Waiting on opinion (2 weeks) ** BIP becomes either Accepted or Deferred * It sets up '''committees''' for reviewing comments and indicating acceptance under precise conditions. ** Committees are authorized groups that represent client authors, miners, merchants, and users (each as a segment). Each one must represent at least 1% stake in the Bitcoin ecosystem. BIP acceptance is defined as at least 70% of the represented percentage stake in 3 out of the 4 Bitcoin segments. == Copyright == This document is placed into the public domain. == Motivation == BIPs represent important improvements to Bitcoin infrastructure, and in order to foster continued innovation, the BIP process must have clearly defined stages and acceptance acknowledgement. == Rationale == A committee system is used to organize the essential concerns of each segment of the Bitcoin ecosystem. Although each segment may have many different viewpoints on each BIP, in order to seek a decisive yes/no on a BIP, a representational authoritative structure is sought. This structure should be fluid, allowing people to move away from committees that do not reflect their views and should be re-validated on each BIP evaluation. == Weaknesses == Each committee submits a declaration including their claim to represent a certain percentage of the Bitcoin ecosystem in some way. Though guidelines are given, it's up to each committee to prove their stake, and it's up to the reader of the opinions to decide if a BIP was truly accepted or rejected. The author doesn't believe this is a problem because a BIP cannot be forced on client authors, miners, merchants, or users. Ultimately this BIP is a tool for determining whether a BIP is overwhelmingly accepted. If one committee's validity claim becomes the factor that decides whether the BIP will succeed or fail, this process simply didn't return a clear answer and the BIP should be considered deferred. == Process == * '''Submit for Comments.''' The first BIP champion named in the proposal can call a "submit for comments" at any time by posting to the [https://lists.linuxfoundation.org/mailman/listinfo/bitcoin-dev Dev Mailing List] mailing with the BIP number and a statement that the champion intends to immediately submit the BIP for comments. ** The BIP must have been assigned BIP-number (i.e. been approved by the BIP editor) to be submitted for comments. * '''Comments.''' ** After a BIP has been submitted for comments, a two-week waiting period begins in which the community should transition from making suggestions about a proposal to publishing their opinions or concerns on the proposal. * '''Reported Opinions.''' ** After the waiting period has past, committees must submit a summary of the comments which they have received from their represented communities. ** The deadline for this opinion is four weeks after the BIP was submitted for comments. ** Committees cannot reverse their decision after the deadline, but at their request may flag their decision as "likely to change if another submit for comments is called". Committees can change their decision if a resubmit is called. ** Opinions must include: *** One of the following statements: "Intend to accept", "Intent to implement", "Decline to accept", "Intend to accept, but decline to implement". *** If rejected, the opinion must cite clear and specific reasons for rejecting including a checklist for what must happen or be change for their committee to accept the proposal. *** If accepted, the committee must list why they accepted the proposal and also include concerns they have or what about the BIP that, if things changed, would cause the committee to likely reverse their decision if another submit for comments was called. * '''Accepted.''' ** If at least 70% of the represented percentage stake in 3 out of 4 segments accept a proposal, the BIP is considered accepted. ** If a committee fails to submit an opinion, consider the opinion "Decline to accept". ** The BIP cannot be substantially changed at this point, but can be replaced. Minor changes or clarifications are allowed but must be recorded in the document. * '''Deferred.''' ** If the acceptance test above is not met, the BIP is sent back into suggestions. ** BIP can be modified and re-submitted for a comments no sooner than two months after the date of the previous submit for comments is called. ** The BIP is marked rejected after two failed submission attempts. A rejected BIP can still be modified and re-submitted. == Committees == '''BIP Committees.''' * BIP Committees are representational structures that represent critical segments of the Bitcoin ecosystem. * Each committee must prove and maintain a clear claim that they represent at least 1% of the Bitcoin ecosystem in some form. * If an organization or community does not meet that requirement, it should conglomerate itself with other communities and organizations so that it does. * The segments that committees can be based around are: ** Bitcoin software ** Exchanges/Merchants/services/payment processors ** Mining operators ** User communities * A person may be represented by any number of segments, but a committee cannot re-use the same resource as another committee in the same segment. '''Committee Declarations.''' * At any point, a Committee Declaration can be posted. * This Declaration must contain details about: ** The segment the Committee is representing ** Who the committee claim to represent and it's compositional makeup (if made up of multiple miner orgs, user orgs, companies, clients, etc). ** Proof of claim and minimum 1% stake via: *** Software: proof of ownership and user base (Min 1% of Bitcoin userbase) *** Merchant: proof of economic activity (Min 1% of Bitcoin economic activity) *** Mining: proof of work (Min 1% of Hashpower) *** For a user organization, auditable signatures qualifies for a valid committee (Min 1% of Bitcoin userbase) ** Who is running the committee, their names and roles ** How represented members can submit comments to the committee ** A code of conduct and code of ethics which the committee promises to abide by * A committee declaration is accepted if: ** The declaration includes all of the required elements ** The stake is considered valid ** Committee validation is considered when considering the results of opinions submitted by committee on a BIP. A committee must have met the required stake percentage before a BIP is submitted for comments, and have maintained that stake until a valid opinion is submitted. * Committees can dissolve at any time or submit a declaration at any time * Declaration must have been submitted no later than the third day following a BIP's request for comments to be eligible for inclusion in a BIP == BIP Process Management Role == BIPs, Opinions, and Committee Declaration must be public at all times. A BIP Process Manager should be chosen who is in charge of: * Declaring where and how BIPs, Opinions, and Committee Declaration should be posted and updated officially. * Maintaining the security and authenticity of BIPs, Opinions, and Committee Declarations * Publishing advisory documents about what kinds of proof of stakes are valid and what kinds should be rejected. * Naming a series of successors for the roles of the BIP Process Manager and BIP Editor (BIP-001) as needed. == Conditions for activation == In order for this process BIP to become active, it must succeed by its own rules. At least a 4% sample of the Bitcoin community must be represented, with at least one committee in each segment included. Once at least one committee has submitted a declaration, a request for comments will be called and the process should be completed from there. ================================================ FILE: bip-0133.mediawiki ================================================
  BIP: 133
  Layer: Peer Services
  Title: feefilter message
  Authors: Alex Morcos 
  Status: Deployed
  Type: Specification
  Assigned: 2016-02-13
  License: PD
==Abstract== Add a new message, "feefilter", which serves to instruct peers not to send "inv"'s to the node for transactions with fees below the specified fee rate. ==Motivation== The concept of a limited mempool was introduced in Bitcoin Core 0.12 to provide protection against attacks or spam transactions of low fees that are not being mined. A reject filter was also introduced to help prevent repeated requests for the same transaction that might have been recently rejected for insufficient fee. These methods help keep resource utilization on a node from getting out of control. However, there are limitations to the effectiveness of these approaches. The reject filter is reset after every block which means transactions that are inv'ed over a longer time period will be rerequested and there is no method to prevent requesting the transaction the first time. Furthermore, inv data is sent at least once either to or from each peer for every transaction accepted to the mempool and there is no mechanism by which to know that an inv sent to a given peer would not result in a getdata request because it represents a transaction with too little fee. After receiving a feefilter message, a node can know before sending an inv that a given transaction's fee rate is below the minimum currently required by a given peer, and therefore the node can skip relaying an inv for that transaction to that peer. ==Specification== # The feefilter message is defined as a message containing an int64_t where pchCommand == "feefilter" # Upon receipt of a "feefilter" message, the node will be permitted, but not required, to filter transaction invs for transactions that fall below the feerate provided in the feefilter message interpreted as satoshis per kilobyte. # The fee filter is additive with a bloom filter for transactions so if an SPV client were to load a bloom filter and send a feefilter message, transactions would only be relayed if they passed both filters. # Inv's generated from a mempool message are also subject to a fee filter if it exists. # Feature discovery is enabled by checking protocol version >= 70013 ==Considerations== The propagation efficiency of transactions across the network should not be adversely affected by this change. In general, transactions which are not accepted to a node's mempool are not relayed by this node and the functionality implemented with this message is meant only to filter those transactions. There could be a small number of edge cases where a node's mempool min fee is actually less than the filter value a peer is aware of and transactions with fee rates between these values will now be newly inhibited. Feefilter messages are not sent to whitelisted peers if the "-whitelistforcerelay" option is set. In that case, transactions are intended to be relayed even if they are not accepted to the mempool. There are privacy concerns with deanonymizing a node by the fact that it is broadcasting identifying information about its mempool min fee. To help ameliorate this concern, the implementation quantizes the filter value broadcast with a small amount of randomness, in addition, the messages are broadcast to different peers at individually randomly distributed times. If a node is using prioritisetransaction to accept transactions whose actual fee rates might fall below the node's mempool min fee, it may want to consider disabling the fee filter to make sure it is exposed to all possible txid's. ==Backward compatibility== Older clients remain fully compatible and interoperable after this change. Also, clients implementing this BIP can choose to not send any feefilter messages. ==Implementation== https://github.com/bitcoin/bitcoin/pull/7542 ==Copyright== This document is placed in the public domain. ================================================ FILE: bip-0134.mediawiki ================================================
  BIP: 134
  Layer: Consensus (hard fork)
  Title: Flexible Transactions
  Authors: Tom Zander 
  Status: Closed
  Type: Specification
  Assigned: 2016-07-27
==Abstract== This BIP describes the next step in making Bitcoin's most basic element, the transaction, more flexible and easier to extend. At the same time this fixes all known cases of malleability and resolves significant amounts of technical debt. ==Summary== Flexible Transactions uses the fact that the first 4 bytes in a transaction determine the version and that the majority of the clients use a non-consensus rule (a policy) to not accept transaction version numbers other than those specifically defined by Bitcoin. This BIP chooses a new version number, 4, and defines that the data following the bytes for the version is in a format called Compact Message Format (CMF). CMF is a flexible, token based format where each token is a combination of a name, a format and a value. Because the name is added we can skip unused tokens and we can freely add new tokens in a simple manner in future. Soft fork upgrades will become much easier and cleaner this way. This protocol upgrade cleans up past soft fork changes like BIP68 which reuse existing fields and do them in a better to maintain and easier to parse system. It creates the building blocks to allow new features to be added much cleaner in the future. It also shows to be possible to remove signatures from transactions with minimal upgrades of software and still maintain a coherent transaction history. Tests show that this can reduce space usage to about 75%. ==Motivation== After 8 years of using essentially the same transaction version and layout Bitcoin is in need of an upgrade and lessons learned in that time are taking into account when designing it. The most important detail is that we have seen a need for more flexibility. For instance when the 'sequence' fields were introduced in the old transaction format, and later deprecated again, the end result was that all transactions still were forced to keep those fields and grow the blockchain while they all were set to the default value. The way towards that flexibility is to use a generic concept made popular various decades ago with the XML format. The idea is that we give each field a name and this means that new fields can be added or optional fields can be omitted from individual transactions. Some other ideas are the standardization of data-formats (like integer and string encoding) so we create a more consistent system. One thing we shall not inherit from XML is its text-based format. Instead we use the [https://github.com/bitcoinclassic/documentation/blob/master/spec/compactmessageformat.md Compact Message Format] (CMF) which is optimized to keep the size small and fast to parse. Token based file-formats are not new, systems like XML and HTMl use a similar system to allow future growth and they have been quite successful for decades in part because of this property. Next to that this protocol upgrade will re-order the data-fields which allows us to cleanly fix the malleability issue which means that future technologies like Lightning Network will depend on this BIP being deployed. At the same time, due to this re-ordering of data fields, it becomes very easy to remove signatures from a transaction without breaking its tx-id, which is great for future pruning features. === Features === * Fixes malleability * Linear scaling of signature checking * Very flexible future extensibility * Makes transactions smaller * Supports the Lightning Network Additionally, in the v4 (flextrans) format we add the support for the following proofs; * input amount. Including the amount means we sign this transaction only if the amount we are spending is the one provided. Wallets that do not have the full UTXO DB can safely sign knowing that if they were lied to about the amount being spent, their signature is useless. * scriptBase is the combined script of input and output, without signatures naturally. Providing this to a hardware wallet means it knows what output it is spending and can respond properly. Including it in the hash means its signature would be broken if we lied.. * Double spent-proof. Should a node detect a double spent he can notify his peers about this fact. Instead of sending the entire transactions, instead he sends only a proof. The node needs to send two pairs of info that proves that in both transactions the CTxIn are identical. === Tokens === In the compact message format we define tokens and in this specification we define how these tokens are named, where they can be placed and which are optional. To refer to XML, this specification would be the schema of a transaction. [https://github.com/bitcoinclassic/documentation/blob/master/spec/compactmessageformat.md CMF] tokens are triplets of name, format (like PositiveInteger) and value. Names in this scope are defined much like an enumeration where the actual integer value (id, below) is equally important to the written name. If any token found that is not covered in the next table it will make the transaction that contains it invalid. {| class="wikitable" |- ! Name !! id !! Format !! Default Value !! Description |- |TxEnd || 0 ||BoolTrue || Required ||A marker that is the end of the transaction |- |TxInPrevHash || 1 ||ByteArray|| Required ||TxId we are spending |- |TxPrevIndex || 2 ||Integer || 0 ||Index in prev tx we are spending (applied to previous TxInPrevHash) |- |TxInputStackItem || 3 ||ByteArray||   ||A 'push' of the input script |- |TxInputStackItemContinued||4||ByteArray|| &nsbp; ||Another section for the same input |- |TxOutValue || 5 ||Integer || Required ||Amount of Satoshis to transfer |- |TxOutScript || 6 ||ByteArray|| Required ||The output script |- |TxRelativeBlockLock|| 7 ||Integer || Optional ||Part of the input stating the amount of blocks (max 0XFFFF) after that input was mined, it can be mined |- |TxRelativeTimeLock || 8 ||Integer || Optional ||Part of the input stating the amount of time (max 0XFFFF) after that input was mined, it can be mined. 1 Unit is 512 seconds |- |CoinbaseMessage || 9 ||ByteArray|| Optional ||A message and some data for a coinbase transaction. Can't be used in combination with any TxIn\* tags |- |NOP_1x || 1x ||  || Optional ||Values that will be ignored by anyone parsing the transaction |- |} === Scripting changes === In Bitcoin transactions version 1, checking of signatures is performed by various opcodes. The OP_CHECKSIG, OP_CHECKMULTISIG and their equivalents that immediately VERIFY. These are used to validate the cryptographic proofs that users have to provide in order to spend outputs. We additionally have some hashing-types in like SIGHASH_SINGLE that all specify slightly different subsections of what part of a transaction will be hashed in order to be signed. For transactions with version 4 we calculate a sha256 hash for signing an individual input based on the following content; # If the hash-type is 0 or 1 we hash the tx-id of the transaction. For other hash types we selectively ignore parts of the transaction exactly like it has always worked. With the caveat that we never serialize any signatures. # the TxId of the transaction we are spending in this input. # the index of output of the transaction we are spending in this input. # the input script we are signing (without the signature, naturally). # the amount, as a var-int. # the hash-type as a var-int. === Serialization order=== To keep in line with the name Flexible Transactions, there is very little requirement to have a specific order. The only exception is cases where there are optional values and reordering would make unclear what is meant. For this reason the TxInPrevHash always has to be the first token to start a new input. This is because the TxPrevIndex is optional. The tokens TxRelativeTimeLock and TxRelativeBlockLock are part of the input and similarly have to be set after the TxInPrevHash they belong to. Similarly, the TxInputStackItem always has to be the first and can be followed by a number of TxInputStackItemContinued items. At a larger scope we define 3 sections of a transaction. {| class="wikitable" !Segment !! Tags !! Description |- |Transaction||all not elsewhere used||This section is used to make the TxId |- |Signatures||TxInputStackItem, TxInputStackItemContinued||The input-proofs |- |TxEnd||TxEnd||  |} The TxId is calculated by taking the serialized transaction without the Signatures and the TxEnd and hashing that. TxEnd is there to allow a parser to know when one transaction in a stream has ended, allowing the next to be parsed. === Block-malleability === The effect of leaving the signatures out of the calculation of the transaction-id implies that the signatures are also not used for the calculation of the merkle tree. This means that changes in signatures would not be detectable and open an attack vector. For this reason the merkle tree is extended to include (append) the hash of the v4 transactions. The merkle tree will continue to have all the transactions' tx-ids but appended to that are the v4 hashes that include the signatures as well. Specifically the hash is taken over a data-blob that is built up from: # the tx-id # The entire bytearray that makes up all of the transactions signatures. This is a serialization of all of the signature tokens, so the TxInputStackItem and TxInputStackItemContinued in the order based on the inputs they are associated with. === Future extensibility === The NOP_1x wildcard used in the table explaining tokens is actually a list of 10 values that currently are specified as NOP (no-operation) tags. Any implementation that supports the v4 transaction format should ignore this field in a transaction. Interpreting and using the transaction as if that field was not present at all. Future software may use these fields to decorate a transaction with additional data or features. Transaction generating software should not trivially use these tokens for their own usage without cooperation and communication with the rest of the Bitcoin ecosystem as miners certainly have the option to reject transactions that use unknown-to-them tokens. The amount of tokens that can be added after number 19 is practically unlimited and they are currently specified to not be allowed in any transaction and the transaction will be rejected if they are present. In the future a protocol upgrade may chance that and specify meaning for any token not yet specified here. Future upgrades should thus be quite a lot smoother because there is no change in concepts or in format. Just new data. ==Backwards compatibility == Fully validating older clients will not be able to understand or validate version 4 transactions and will need to be updated to restore that ability. SPV (simple payment validation) wallets need to be updated to receive or create the new transaction type. This BIP introduces a new transaction format without changing or deprecating the existing one or any of its practices. Therefore it is backwards compatible for any existing data or parsing-code. ==Reference Implementation== Bitcoin Classic includes an implementation that is following this spec. The spec-author rejects the notion of reference implementation. The specification is always authoritative, the implementation is not. The official spec can be found at; https://github.com/bitcoinclassic/documentation/blob/master/spec/transactionv4.md ==Deployment== To be determined ==References== [https://github.com/bitcoinclassic/documentation/blob/master/spec/compactmessageformat.md] CMF ==Copyright== Copyright (c) 2016 Tom Zander This document is dual-licensed under the Creative-Commons BY-SA license v4.0 and the Open Publication License v1.0 with the following licence-options: Distribution of substantively modified versions of this document is prohibited without the explicit permission of the copyright holder. Distribution of the work or derivative of the work in any standard (paper) book form is prohibited unless prior permission is obtained from the copyright holder. ================================================ FILE: bip-0135.mediawiki ================================================
  BIP: 135
  Title: Generalized version bits voting
  Authors: Sancho Panza 
  Status: Closed
  Type: Informational
  Assigned: 2017-03-29
  License: CC0-1.0 OR FSFAP
  Discussion: https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2017-April/013969.html
              https://bitco.in/forum/threads/bip9-generalized-version-bits-voting-bip-genvbvoting.1968/
  Replaces: 9
==Abstract== BIP9 introduced a mechanism for using the version bits to signal support for backwards-compatible changes (soft-forks) using a tally over the previous 2016 blocks computed at re-targeting intervals. It provided for a fixed threshold and non-configurable lock-in interval applicable to all deployments on a chain. This document describes a generalized signaling scheme which allows each signaling bit to have its own configurable threshold, window size (number of blocks over which it is tallied) and a configurable lock-in period. It extends the semantics of the signaling bits to cover arbitrary consensus changes, referred to under the general term 'forks'. The same range of version bits is used for signaling. The states of the BIP9 state machine and its original parameters (name, bit, starttime, timeout) are retained. Some state transition conditions are extended by additional parameters ('threshold', 'windowsize', 'minlockedblocks', 'minlockedtime') to provide for fine-tuning of threshold and grace period. ==Motivation== The Bitcoin protocol requires a flexible scheme for finding consensus on protocol changes, to ensure that it can adapt to the needs of the market and remain competitive as an electronic payment system. While BIP9 has served the community well for previous deployments, there are some shortcomings in its approach: * it specifically applies only to backward-compatible changes * its fixed 95% threshold is not flexible enough to allow for a 'spectrum of contentiousness' to be represented * small minorities can veto proposed changes, which can lead to undesirable stagnation A generalized revision of the BIP9 specification can address these issues and satisfy the needs of the market for both soft and hard fork changes as well as more flexible activation thresholds and upgrade (grace) periods. The proposal should allow more freedom of choice in activation strategies while remaining backward compatible with respect to existing BIP9-based deployments. ==Terms and conventions== The version bits used by this proposal for signaling deployment of forks are referred to as 'signaling bits' or shortened to 'bits' where unambiguous. All times in this specification are in seconds since the epoch [1]. Durations / time offsets are in seconds. The term 'MTP' refers to the 'median time past' which is calculated as the median nTime of a block and its 10 predecessors. It is treated as a monotonic clock defined by a chain, and evaluated on the ancestor of a block, i.e. MTP := '''GetMedianTimePast(block.parent)''' The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED", "MAY", and "OPTIONAL" in this document are to be interpreted as described in RFC 2119. ==Specification== ===Backward compatibility=== This specification SHALL enable strict backward compatibility with existing BIP9-based deployments through suitable parameter configuration. Any part of the specification preventing full backward compatibility SHALL be considered as erroneous and amended. As before, a set of configuration parameters SHALL exist for the version bits for each chain supported by an implementation. This permits each bit to be configured independently for each chain (mainnet, testnet, etc.) ===Signaling bits=== The signaling bits SHALL comprise the 29 least significant bits of the nVersion block header field. nVersion is a 32-bit field which is treated as a little-endian integer. Signaling bits SHALL be assigned numbers from 0..28 ranging from the least significant (bit 0) to the most significant (bit 28) in the range. The top 3 bits of nVersion MUST be set to 001 , yielding a range of possible nVersion values between [0x20000000...0x3FFFFFFF], inclusive. If a block's nVersion does not have its top 3 bits set to 001, all its signaling bits MUST be treated as if they are 0 (see also: 'Tallying' section below). ===Deployment states=== With each block and fork, we associate a deployment state. The possible states are: # '''DEFINED''' is the first state that each fork starts out as. The genesis block for any chain SHALL by definition be in this state for each deployment. # '''STARTED''' for blocks past the starttime. # '''LOCKED_IN''' after STARTED, if at least threshold out of windowsize blocks have the associated bit set in nVersion, measured at next height that is evenly divisible by the windowsize. # '''ACTIVE''' for all blocks after the grace period conditions have been met. # '''FAILED''' if past the timeout time and LOCKED_IN was not reached. In accordance with BIP9, a block's state SHALL never depend on its own nVersion; only on that of its ancestors. ===Fork deployment parameters=== Each fork deployment is specified by the following per-chain parameters: # The '''name''' specifies a very brief description of the fork, reasonable for use as an identifier. For deployments described in a single BIP, it is recommended to use the name "bipN" where N is the appropriate BIP number. # The '''bit''' determines which bit in the nVersion field of the block is to be used to signal the fork deployment. It is chosen from the set {0,1,2,...,28}. # The '''starttime''' specifies a minimum median time past (MTP) of a block at which the bit gains its meaning. # The '''timeout''' specifies a time at which the deployment is considered failed. If the MTP of a block >= timeout and the fork has not yet locked in (including this block's bit state), the deployment is considered failed on all descendants of the block. # The '''windowsize''' specifies the number of past blocks (including the block under consideration) to be taken into account for locking in a fork. # The '''threshold''' specifies a number of blocks, in the range of 1..windowsize, which must signal for a fork in order to lock it in. The support is measured when the chain height is evenly divisible by the windowsize. If the windowsize is set to 2016 (as in BIP9) this coincides with the 2016-block re-targeting intervals. # The '''minlockedblocks''' specifies a minimum number of blocks which a fork must remain in locked-in state before it can become active. Both minlockedblocks and minlockedtime (see below) must be satisfied before a fork can become active. # The '''minlockedtime''' specifies a minimum grace time, an earliest time after lock-in at which the fork can become active. If the MTP of a block >= (minlockedtime + median time of the block that locked in the fork), then the fork becomes activated. Both minlockedtime and minlockedblocks (see above) must be satisfied before a fork can become active. ===Tallying=== If a block's nVersion does not have its top 3 bits set to 001, all its signaling bits MUST be treated as if they are '0'. A signaling bit value of '1' SHALL indicate support of a fork and SHALL count towards its tally on a chain. A signaling bit value of '0' SHALL indicate absence of support of a fork and SHALL NOT count towards its tally on a chain. The signaling bits SHALL be tallied whenever the head of the active chain changes (including after reorganizations). ===State transitions=== The following diagram illustrates the generalized state machine:
'''NOTES:''' The genesis block of any chain SHALL have the state DEFINED for each deployment. A given deployment SHALL remain in the DEFINED state until it either passes the starttime (and becomes STARTED) or the timeout time (and becomes FAILED). Once a deployment has STARTED, the signal for that deployment SHALL be tallied over the past windowsize blocks whenever a new block is received on that chain. A transition from the STARTED state to the LOCKED_IN state SHALL only occur when all of these are true: * the height of the received block is an integer multiple of the window size * the MTP is below the timeout time * at least threshold out of windowsize blocks have signaled support A similar height synchronization precondition SHALL exist for the transition from LOCKED_IN to ACTIVE. These synchronization conditions are expressed by the "mod(height, windowsize) = 0" clauses in the diagram, and have been added so that backward compatibility with BIP9's use of the 2016-block re-targeting periods can be configured for existing deployments (see above 'Optional full backward compatibility' section). A transition from LOCKED_IN to ACTIVE state SHALL only occur if the height synchronization criterion is met and two configurable 'grace period' conditions are fulfilled: # current height MUST be at least minlockedblocks above LOCKED_IN height # MTP must exceed LOCKED_IN time by at least minlockedtime seconds NOTE: If minlockedtime and minlockedblocks are both set to 0, then the fork will proceed directly to ACTIVE state once the chain height reaches a multiple of the windowsize. The ACTIVE and FAILED states are terminal; a deployment stays in these states once they are reached. Deployment states are maintained along block chain branches. They need re-computation when a reorganization happens. ===New consensus rules=== New consensus rules deployed by a fork SHALL be enforced for each block that has ACTIVE state. ===Optional operator notifications=== An implementation SHOULD notify the operator when a deployment transitions to STARTED, LOCKED_IN, ACTIVE or FAILED states. It is RECOMMENDED that an implementation provide finer-grained notifications to the operator which allow him/her to track the measured support level for defined deployments. An implementation SHOULD warn the operator if the configured (emitted) nVersion has been overridden to contain bits set to '1' in contravention of the above non-signaling recommendations for DEFINED forks. It is RECOMMENDED that an implementation warn the operator if no signal has been received for a given deployment during a full windowsize period after the deployment has STARTED. This could indicate that something may be wrong with the operator's configuration that is causing them not to receive the signal correctly. For undefined signals, it is RECOMMENDED that implementation track these and alert their operators with supportive upgrade notifications, e.g. * "warning: signaling started on unknown feature on version bit X" * "warning: signaling on unknown feature reached X% (over last N blocks)" * "info: signaling ceased on unknown feature (over last M blocks)" Since parameters of these deployments are unknown, it is RECOMMENDED that implementations allow the user to configure the emission of such notifications (e.g. suitable N and M parameters in the messages above, e.g. a best-guess window of 100 blocks). ===getblocktemplate changes=== The getblocktemplate features introduced in BIP9 remain in effect unmodified. ==Rationale== The timeout into FAILED state allows eventual reuse of bits if a fork was not successfully activated. A fallow period at the conclusion of a fork attempt allows some detection of buggy clients, and allows time for warnings and software upgrades for successful forks. The duration of a fallow period is not specified by this proposal, although a conventional fallow period of 3 months is RECOMMENDED. Due to the constraints set by BIP 34, BIP 66 and BIP 65, there are only 0x7FFFFFFB possible nVersion values available. This limits to at most 30 independent deployments. By restricting the top 3 bits to 001 we are left with 29 out of those for the purposes of this proposal, and support two future upgrades for different mechanisms (top bits 010 and 011). ==Guidelines== ===Parameter selection guidelines=== The following guidelines are suggested for selecting the parameters for a fork: # '''name''' SHOULD be selected such that no two forks, concurrent or otherwise, ever use the same name. # '''bit''' SHOULD be selected such that no two concurrent forks use the same bit. Implementers should make an effort to consult resources such as [2] to establish whether the bit they wish to use can reasonably be assumed to be unclaimed by a concurrent fork, and to announce their use ('claim') of a bit for a fork purpose on various project mailing lists, to reduce chance of collisions. # '''starttime''' SHOULD be set to some date in the future, approximately one month after a software release date which includes the fork signaling. This allows for some release delays, while preventing triggers as a result of parties running pre-release software. # '''timeout''' is RECOMMENDED to be 1 year (31536000 seconds) after starttime. # '''windowsize''' SHOULD be set large enough to allow reception of an adequately precise signal. A good high-resolution value would be 2016 blocks as used in BIP9. It is NOT RECOMMENDED to use a windowsize less than 100 blocks. # '''threshold''' SHOULD be set as high as possible to ensure a smooth activation based on the estimated support and the nature of the proposed changes. It is strongly RECOMMENDED that threshold >= windowsize / 2 (rounded up) to ensure that a proposal is only activated by majority support. # '''minlockedblocks''' is RECOMMENDED to be set >= windowsize, to ensure that a full window passes in LOCKED_IN state. Lower values will be ineffective as the transition from LOCKED_IN to ACTIVE is guarded by a synchronization based on the window size. # '''minlockedtime''' SHOULD only be set > 0 if a minimum LOCKED_IN time period needs be strictly enforced. It is permissible to set minlockedblocks to 0 and only specify minlockedtime, however the synchronization condition means the grace period can only expire once the time has passed AND the chain height is a multiple of the windowsize. NOTE: If minlockedtime and minlockedblocks are both set to 0, then the fork will proceed to ACTIVE state when the chain height reaches a multiple of the windowsize. A later deployment using the same bit is possible as long as the starttime is after the previous fork's timeout or activation, but it is discouraged until necessary, and even then recommended to have a pause in between to detect buggy software. ===Signaling guidelines=== An implementation SHOULD signal '0' on a bit if one of the following holds true: * the deployment parameters are not DEFINED (not configured or explicitly undefined) * the deployment is DEFINED and has not yet reached the STARTED state * the deployment has succeeded (it has become ACTIVE) * the deployment has FAILED An implementation SHOULD enable the operator to choose (override) whether to signal '0' or '1' on a bit, once its deployment has at least reached the STARTED state. An implementation SHOULD warn the operator if the configured (emitted) nVersion has been overridden to contain bits set to '1' in contravention of the above non-signaling recommendations. A supporting miner SHOULD signal '1' on a bit for which the deployment is LOCKED_IN state so that uptake is visible. However, this has no effect on consensus rules. Once LOCKED_IN, a deployment proceeds to ACTIVE solely based on the configured grace period parameters (see 'Fork deployment parameters' above). A miner SHOULD signal '0' on a bit if they wish to suspend signaling of support for a fork that is DEFINED in their software. It is NOT RECOMMENDED to signal '1' for bits where the meaning is undefined (i.e. bits which are unclaimed by proposals). ===Settings for BIP9 compatibility=== This section lists parameter values which can be used to effect compatibility with the existing BIP9 versionbits state machine. The following table describes mainnet compatibility options (95%, 2016 blocks): {| class="wikitable" !colspan=3 | |- ! Parameter !! BIP9 value !! BIP135 value |- | name || some_name || some_name |- | bit || b || b |- | starttime || T_start || T_start |- | timeout || T_timeout || T_timeout |- | windowsize || n/a || 2016 |- | threshold || n/a || 1916 |- | minlockedblocks || n/a || 2016 |- | minlockedtime || n/a || 0 |} The following table describes testnet compatibility options (75%, 2016 blocks): {| class="wikitable" !colspan=3 | |- ! Parameter !! BIP9 value !! BIP135 value |- | name || some_name || some_name |- | bit || b || b |- | starttime || T_start || T_start |- | timeout || T_timeout || T_timeout |- | windowsize || n/a || 2016 |- | threshold || n/a || 1512 |- | minlockedblocks || n/a || 2016 |- | minlockedtime || n/a || 0 |} ==Deployment== As this BIP is not itself consensus-relevant (Information like BIP9), it can be rolled out without the use of a BIP9 fork bit. Backward compatibility through judicious fork configuration parameters should ensure that it does not interfere with existing known deployments. By way of design it does not interfere with unknown (undefined) deployments. ==Reference implementation== A working reference implementation, including tests, can be found in these Pull Requests: * https://github.com/BitcoinUnlimited/BitcoinUnlimited/pull/458 * https://github.com/bitcoin/bitcoin/pull/10437 Existing unit tests and regression tests have been left active to demonstrate backward compatibility of the default settings with BIP9. ==References== [1] http://pubs.opengroup.org/onlinepubs/9699919799/xrat/V4_xbd_chap04.html#tag_21_04_16 [2] [[https://github.com/bitcoin/bips/blob/master/bip-0009/assignments.mediawiki|List of existing BIP9 deployment proposals]] ==Copyright== This BIP is dual-licensed under the Creative Commons CC0 1.0 Universal and FSF All Permissive licenses. ================================================ FILE: bip-0136.mediawiki ================================================
  BIP: 136
  Layer: Applications
  Title: Bech32 Encoded Tx Position References
  Authors: Велеслав 
           Jonas Schnelli 
           Daniel Pape 
  Status: Draft
  Type: Informational
  Assigned: 2017-07-09
  License: BSD-2-Clause
== Introduction == === Abstract === This document proposes a convenient, human usable encoding to refer to a '''confirmed transaction position''' within the Bitcoin blockchain--known as '''"TxRef"'''. The primary purpose of this encoding is to allow users to refer to a confirmed transaction (and optionally, a particular outpoint index within the transaction) in a standard, reliable, and concise way. ''Please note: Unlike a transaction ID, '''"TxID"''', where there is a strong cryptographic link between the ID and the actual transaction, a '''TxRef''' only provides a weak link to a particular transaction. A '''TxRef''' locates an offset within a blockchain for a transaction, that may - or may not - point to an actual transaction, which in fact may change with reorganisations. We recommend that '''TxRef'''s should be not used for positions within the blockchain having a maturity less than 100 blocks.'' The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED", "MAY", and "OPTIONAL" in this document are to be interpreted as described in [https://tools.ietf.org/html/rfc2119 RFC 2119]. === Copyright === This BIP is licensed under the 2-clause BSD license. === Motivation === Since the first version of Bitcoin, '''TxID'''s have been a core part of the consensus protocol and are routinely used to identify individual transactions between users. However, for many use-cases they have practical limitations: * '''TxID'''s are expensive for full nodes to lookup (requiring either a linear scan of the blockchain, or an expensive '''TxID''' index). * '''TxID'''s require third-party services for SPV wallets to lookup. * '''TxID'''s are 64 character HEX encoded values. It is possible to reference transactions not only by their '''TxID''', but by their location within the blockchain itself. Rather than use the 64 character '''TxID''', an encoding of the position coordinates can be made friendly for occasional human transcription. In this document, we propose a standard for doing this. === Examples === {| class="wikitable" |- ! Block # !! Transaction # !! Outpoint # !! TxRef !! TxID |- | 0 || 0 || 0 || tx1:rqqq‑qqqq‑qwtv‑vjr || 4a5e1e4baab89f3a32518a88c31bc87f618f76673e2cc77ab2127b7afdeda33b |- | 170 || 1 || 0 || tx1:r52q‑qqpq‑qpty‑cfg || f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16 |- | 456789 || 1234 || 1 || tx1:y29u‑mqjx‑ppqq‑sfp2‑tt || 6fb8960f70667dc9666329728a19917937896fc476dfc54a3e802e887ecb4e82 |} == Specification == A '''confirmed transaction position reference''', or '''TxRef''', is a reference to a particular location within the blockchain, specified by the block height and a transaction index within the block, and optionally, an outpoint index within the transaction. ''Please Note: All values in this specification are encoded in little-endian format.'' === TxRef Considerations === It is possible for a '''TxRef''' to reference a transaction that doesn't really exist because: * The specified block hasn't yet been mined. * The transaction index is greater than the total number of transactions included within the specified block. * The optional outpoint index is greater than the total outpoints contained within the transaction. Therefore, implementers must be careful not to display '''TxRef'''s to users prematurely: * Applications MUST NOT display '''TxRef'''s for transactions with less than 6 confirmations. * Application MUST show a warning for '''TxRef'''s for transactions with less than 100 confirmations. ** This warning SHOULD state that in the case of a large reorganisation, the '''TxRef'''s displayed may point to a different transaction, or to no transaction at all. === TxRef Format === '''TxRef''' MUST use the '''Bech32m''''''Why use Bech32 Encoding for Confirmed Transaction References?''' The error detection and correction properties of this encoding format make it very attractive. We expect that it will be reasonable for software to correct a maximum of two characters; however, we haven’t specified this yet. encoding as defined in [https://github.com/bitcoin/bips/blob/master/bip-0173.mediawiki BIP-0173] and later refined in [https://github.com/bitcoin/bips/blob/master/bip-0350.mediawiki BIP-0350]. The Bech32m encoding consists of: ==== Human-Readable Part ==== The '''HRP''' can be thought of as a label. We have chosen labels to distinguish between Main, Test, and Regtest networks: * Mainnet: '''"tx"'''. * Testnet: '''"txtest"'''. * Regtest: '''"txrt"'''. ==== Separator ==== The separator is the character '''"1"'''. ==== Data Part ==== The data part for a '''TxRef''' consists of the transaction's block height, transaction index within the block, and optionally, an outpoint index. Specific encoding details for the data are given below. ''Please note: other specifications, such as [https://w3c-ccg.github.io/did-spec/ the Decentralized Identifiers spec], have implicitly encoded the information contained within the HRP elsewhere. In this case they may choose to not include the HRP as specified here.'' ==== Readability ==== To increase portability and readability, additional separator characters SHOULD be added to the '''TxRef''': * A Colon'''Why add a colon here?''' This allows it to conform better with W3C URN/URL standards. '''":"''' added after the separator character '1'. * Hyphens'''Why hyphens within the TxRef?''' As '''TxRef'''s are short, we expect that they will be quoted via voice or written by hand. The inclusion of hyphens every 4 characters breaks up the string and means people don't lose their place so easily. '''"-"''' added after every 4 characters beyond the colon. === Encoding === Encoding a '''TxRef''' requires 4 or 5 pieces of data: a magic code denoting which network is being used; a version number (currently always 0); the block height of the block containing the transaction; the index of the transaction within the block; and optionally, the index of the outpoint within the transaction. Only a certain number of bits are supported for each of these values, see the following table for details. {| class="wikitable" ! !Description !Possible Data Type !'''# of Bits used''' !Values |- | style="background: #99DDFF; color: black; text-align : center;" | Magic Code |Chain Namespacing Code |uint8 | style="background: #99DDFF; color: black; text-align : center;" | 5 |'''3''': Mainnet
'''4''': Mainnet with Outpoint
'''6''': Testnet
'''7''': Testnet with Outpoint
'''0''': Regtest
'''1''': Regtest with Outpoint |- | style="background: #DDDDDD; color: black; text-align : center;" | Version |For Future Use |uint8 | style="background: #DDDDDD; color: black; text-align : center;" | 1 |Must be '''0''' |- | style="background: #EEDD88; color: black; text-align : center;" | Block
Height |The Block Height of the Tx |uint32 | style="background: #EEDD88; color: black; text-align : center;" | 24 |Block 0 to Block 16777215 |- | style="background: #FFAABB; color: black; text-align : center;" | Transaction
Index |The index of the Tx inside the block |uint16, uint32 | style="background: #FFAABB; color: black; text-align : center;" | 15 |Tx 0 to Tx 32767 |- | style="background: #BBCC33; color: black; text-align : center;" | Outpoint
Index |The index of the Outpoint inside the Tx |uint16, uint32 | style="background: #BBCC33; color: black; text-align : center;" | 15 |Outpoint 0 to Outpoint 32767 |} ==== Magic Notes ==== The magic code provides namespacing between chains: * For Mainnet the magic code is: '''0x3''', leading to an '''"r"''' character when encoded. * For Mainnet with Outpoint Encoded the magic code is: '''0x4''', leading to a '''"y"''' character when encoded. * For Testnet the magic code is: '''0x6''', leading to an '''"x"''' character when encoded. * For Testnet with Outpoint Encoded the magic code is: '''0x7''', leading to an '''"8"''' character when encoded. * For Regtest the magic code is: '''0x0''', leading to a '''"q"''' character when encoded. * For Regtest with Outpoint Encoded the magic code is: '''0x1''', leading to a '''"p"''' character when encoded. ==== Encoding Example ==== We want to encode a '''TxRef''' that refers to Transaction #1234 of Block #456789 on the Mainnet chain. We use this data in preparation for the Bech32 encoding algorithm: {| class="wikitable" ! !Decimal
Value !Binary
Value !'''# of Bits
used''' !Bit Indexes and Values |- | style="background: #99DDFF; color: black; text-align : center;" | Magic
Code | style="background: #99DDFF; color: black; text-align : center;" | 3 |00000011 | style="background: #99DDFF; color: black; text-align : center;" | 5 |(mc04, mc03, mc02, mc01, mc00) = (0, 0, 0, 1, 1) |- | style="background: #DDDDDD; color: black; text-align : center;" | Version | style="background: #DDDDDD; color: black; text-align : center;" | 0 |00000000 | style="background: #DDDDDD; color: black; text-align : center;" | 1 |(v0) = (0) |- | style="background: #EEDD88; color: black; text-align : center;" | Block
Height | style="background: #EEDD88; color: black; text-align : center;" | 456789 |00000110
11111000
01010101 | style="background: #EEDD88; color: black; text-align : center;" | 24 |(bh23, bh22, bh21, bh20, bh19, bh18, bh17, bh16) = (0, 0, 0, 0, 0, 1, 1, 0)
(bh15, bh14, bh13, bh12, bh11, bh10, bh09, bh08) = (1, 1, 1, 1, 1, 0, 0, 0)
(bh07, bh06, bh05, bh04, bh03, bh02, bh01, bh00) = (0, 1, 0, 1, 0, 1, 0, 1) |- | style="background: #FFAABB; color: black; text-align : center;" | Transaction
Index | style="background: #FFAABB; color: black; text-align : center;" | 1234 |00000100
11010010 | style="background: #FFAABB; color: black; text-align : center;" | 15 |(ti14, ti13, ti12, ti11, ti10, ti09, ti08) = (0, 0, 0, 0, 1, 0, 0)
(ti07, ti06, ti05, ti04, ti03, ti02, ti01, ti00) = (1, 1, 0, 1, 0, 0, 1, 0) |} As shown in the last column, we take the necessary bits of each binary value and copy them into nine unsigned chars illustrated in the next table. We only set the lower five bits of each unsigned char as the bech32 algorithm only uses those bits. {| class="wikitable" style="text-align: center" ! ! !style="width:2em"|7 !style="width:2em"|6 !style="width:2em"|5 !style="width:2em"|4 !style="width:2em"|3 !style="width:2em"|2 !style="width:2em"|1 !style="width:2em"|0 ! !Decimal
Value !Bech32
Character |- | || || || || || || || || || || || || |- | rowspan="2" | data[0] || Index |na |na |na | style="background: #99DDFF; color: black; text-align : center;" | mc04 | style="background: #99DDFF; color: black; text-align : center;" | mc03 | style="background: #99DDFF; color: black; text-align : center;" | mc02 | style="background: #99DDFF; color: black; text-align : center;" | mc01 | style="background: #99DDFF; color: black; text-align : center;" | mc00 | | | |- |Value |0 |0 |0 |0 |0 |0 |1 |1 | |3 |r |- | || || || || || || || || || || || |- | rowspan="2" | data[1] || Index |na |na |na | style="background: #EEDD88; color: black; text-align : center;" | bh03 | style="background: #EEDD88; color: black; text-align : center;" | bh02 | style="background: #EEDD88; color: black; text-align : center;" | bh01 | style="background: #EEDD88; color: black; text-align : center;" | bh00 | style="background: #DDDDDD; color: black; text-align : center;" | v0 | | | |- |Value |0 |0 |0 |0 |1 |0 |1 |0 | |10 |2 |- | || || || || || || || || || || || |- | rowspan="2" | data[2] || Index |na |na |na | style="background: #EEDD88; color: black; text-align : center;" | bh08 | style="background: #EEDD88; color: black; text-align : center;" | bh07 | style="background: #EEDD88; color: black; text-align : center;" | bh06 | style="background: #EEDD88; color: black; text-align : center;" | bh05 | style="background: #EEDD88; color: black; text-align : center;" | bh04 | | | |- |Value |0 |0 |0 |0 |0 |1 |0 |1 | |5 |9 |- | || || || || || || || || || || || |- | rowspan="2" | data[3] || Index |na |na |na | style="background: #EEDD88; color: black; text-align : center;" | bh13 | style="background: #EEDD88; color: black; text-align : center;" | bh12 | style="background: #EEDD88; color: black; text-align : center;" | bh11 | style="background: #EEDD88; color: black; text-align : center;" | bh10 | style="background: #EEDD88; color: black; text-align : center;" | bh09 | | | |- |Value |0 |0 |0 |1 |1 |1 |0 |0 | |28 |u |- | || || || || || || || || || || || |- | rowspan="2" | data[4] || Index |na |na |na | style="background: #EEDD88; color: black; text-align : center;" | bh18 | style="background: #EEDD88; color: black; text-align : center;" | bh17 | style="background: #EEDD88; color: black; text-align : center;" | bh16 | style="background: #EEDD88; color: black; text-align : center;" | bh15 | style="background: #EEDD88; color: black; text-align : center;" | bh14 | | | |- |Value |0 |0 |0 |1 |1 |0 |1 |1 | |27 |m |- | || || || || || || || || || || || |- | rowspan="2" | data[5] || Index |na |na |na | style="background: #EEDD88; color: black; text-align : center;" | bh23 | style="background: #EEDD88; color: black; text-align : center;" | bh22 | style="background: #EEDD88; color: black; text-align : center;" | bh21 | style="background: #EEDD88; color: black; text-align : center;" | bh20 | style="background: #EEDD88; color: black; text-align : center;" | bh19 | | | |- |Value |0 |0 |0 |0 |0 |0 |0 |0 | |0 |q |- | || || || || || || || || || || || |- | rowspan="2" | data[6] || Index |na |na |na | style="background: #FFAABB; color: black; text-align : center;" | ti04 | style="background: #FFAABB; color: black; text-align : center;" | ti03 | style="background: #FFAABB; color: black; text-align : center;" | ti02 | style="background: #FFAABB; color: black; text-align : center;" | ti01 | style="background: #FFAABB; color: black; text-align : center;" | ti00 | | | |- |Value |0 |0 |0 |1 |0 |0 |1 |0 | |18 |j |- | || || || || || || || || || || || |- | rowspan="2" | data[7] || Index |na |na |na | style="background: #FFAABB; color: black; text-align : center;" | ti09 | style="background: #FFAABB; color: black; text-align : center;" | ti08 | style="background: #FFAABB; color: black; text-align : center;" | ti07 | style="background: #FFAABB; color: black; text-align : center;" | ti06 | style="background: #FFAABB; color: black; text-align : center;" | ti05 | | | |- |Value |0 |0 |0 |0 |0 |1 |1 |0 | |6 |x |- | || || || || || || || || || || || |- | rowspan="2" | data[8] || Index |na |na |na | style="background: #FFAABB; color: black; text-align : center;" | ti14 | style="background: #FFAABB; color: black; text-align : center;" | ti13 | style="background: #FFAABB; color: black; text-align : center;" | ti12 | style="background: #FFAABB; color: black; text-align : center;" | ti11 | style="background: #FFAABB; color: black; text-align : center;" | ti10 | | | |- |Value |0 |0 |0 |0 |0 |0 |0 |1 | |1 |p |} The Bech32 algorithm encodes the nine unsigned chars above and computes a checksum of those chars and encodes that as well--this gives a six character checksum (in this case, '''utt3p0''') which is appended to the final '''TxRef'''. The final '''TxRef''' given is: '''tx1:r29u-mqjx-putt-3p0''' and is illustrated in the following table: TxRef character indexes and descriptions {| class="wikitable" style="text-align: top" !style="width:2em"|Index !style="width:2em"|0 !style="width:2em"|1 !style="width:2em"|2 !style="width:2em"|3 !style="width:2em"|4 !style="width:2em"|5 !style="width:2em"|6 !style="width:2em"|7 !style="width:2em"|8 !style="width:2em"|9 !style="width:2em"|10 !style="width:2em"|11 !style="width:2em"|12 !style="width:2em"|13 !style="width:2em"|14 !style="width:2em"|15 !style="width:2em"|16 !style="width:2em"|17 !style="width:2em"|18 !style="width:2em"|19 !style="width:2em"|20 !style="width:2em"|21 |- |Char: | style="background: #BBCCEE; color: black; text-align : center;" | t | style="background: #BBCCEE; color: black; text-align : center;" | x | style="background: #FFCCCC; color: black; text-align : center;" | 1 | style="background: #CCDDAA; color: black; text-align : center;" | : | style="background: #EEEEBB; color: black; text-align : center;" | r | style="background: #EEEEBB; color: black; text-align : center;" | 2 | style="background: #EEEEBB; color: black; text-align : center;" | 9 | style="background: #EEEEBB; color: black; text-align : center;" | u | style="background: #CCDDAA; color: black; text-align : center;" | - | style="background: #EEEEBB; color: black; text-align : center;" | m | style="background: #EEEEBB; color: black; text-align : center;" | q | style="background: #EEEEBB; color: black; text-align : center;" | j | style="background: #EEEEBB; color: black; text-align : center;" | x | style="background: #CCDDAA; color: black; text-align : center;" | - | style="background: #EEEEBB; color: black; text-align : center;" | p | style="background: #EEEEBB; color: black; text-align : center;" | u | style="background: #EEEEBB; color: black; text-align : center;" | t | style="background: #EEEEBB; color: black; text-align : center;" | t | style="background: #CCDDAA; color: black; text-align : center;" | - | style="background: #EEEEBB; color: black; text-align : center;" | 3 | style="background: #EEEEBB; color: black; text-align : center;" | p | style="background: #EEEEBB; color: black; text-align : center;" | 0 |} ==== Outpoint Index ==== Some uses of '''TxRef''' may want to refer to a specific outpoint of the transaction. In the previous example, since we did not specify the outpoint index, the '''TxRef''' '''tx1:r29u-mqjx-putt-3p0''' implicitly references the first (index 0) outpoint of the 1234th transaction in the 456789th block in the blockchain. If instead, for example, we want to reference the second (index 1) outpoint, we need to change the magic code from '''3''' to '''4''' and would include the following in the data to be encoded: {| class="wikitable" ! !Decimal
Value !Binary
Value !'''# of Bits
used''' !Bit Indexes and Values |- | style="background: #99DDFF; color: black; text-align : center;" | Magic
Code | style="background: #99DDFF; color: black; text-align : center;" | 4 |00000100 | style="background: #99DDFF; color: black; text-align : center;" | 5 |(mc04, mc03, mc02, mc01, mc00) = (0, 0, 1, 0, 0) |- | style="background: #BBCC33; color: black; text-align : center;" | Outpoint Index | style="background: #BBCC33; color: black; text-align : center;" | 1 |00000000 00000001 | style="background: #BBCC33; color: black; text-align : center;" | 15 |(op14, op13, op12, op11, op10, op09, op08) = (0, 0, 0, 0, 0, 0, 0)
(op07, op06, op05, op04, op03, op02, op01, op00) = (0, 0, 0, 0, 0, 0, 0, 1) |} {| class="wikitable" style="text-align: center" ! ! !style="width:2em"|7 !style="width:2em"|6 !style="width:2em"|5 !style="width:2em"|4 !style="width:2em"|3 !style="width:2em"|2 !style="width:2em"|1 !style="width:2em"|0 ! !Decimal
Value !Bech32
Character |- | || || || || || || || || || || || || |- | rowspan="2" | data[0] || Index |na |na |na | style="background: #99DDFF; color: black; text-align : center;" | mc04 | style="background: #99DDFF; color: black; text-align : center;" | mc03 | style="background: #99DDFF; color: black; text-align : center;" | mc02 | style="background: #99DDFF; color: black; text-align : center;" | mc01 | style="background: #99DDFF; color: black; text-align : center;" | mc00 | | | |- |Value |0 |0 |0 |0 |0 |1 |0 |0 | |4 |y |- | || || || || || || || || || || || |- | rowspan="2" | data[9] || Index |na |na |na | style="background: #BBCC33; color: black; text-align : center;" | op04 | style="background: #BBCC33; color: black; text-align : center;" | op03 | style="background: #BBCC33; color: black; text-align : center;" | op02 | style="background: #BBCC33; color: black; text-align : center;" | op01 | style="background: #BBCC33; color: black; text-align : center;" | op00 | | | |- |Value |0 |0 |0 |0 |0 |0 |0 |1 | |1 |p |- | || || || || || || || || || || || |- | rowspan="2" | data[10] || Index |na |na |na | style="background: #BBCC33; color: black; text-align : center;" | op09 | style="background: #BBCC33; color: black; text-align : center;" | op08 | style="background: #BBCC33; color: black; text-align : center;" | op07 | style="background: #BBCC33; color: black; text-align : center;" | op06 | style="background: #BBCC33; color: black; text-align : center;" | op05 | | | |- |Value |0 |0 |0 |0 |0 |0 |0 |0 | |0 |q |- | || || || || || || || || || || || |- | rowspan="2" | data[11] || Index |na |na |na | style="background: #BBCC33; color: black; text-align : center;" | op14 | style="background: #BBCC33; color: black; text-align : center;" | op13 | style="background: #BBCC33; color: black; text-align : center;" | op12 | style="background: #BBCC33; color: black; text-align : center;" | op11 | style="background: #BBCC33; color: black; text-align : center;" | op10 | | | |- | Value |0 |0 |0 |0 |0 |0 |0 |0 | |0 |q |} After Bech32 encoding all twelve unsigned chars above, we get the checksum: '''sfp2tt'''. The final '''TxRef''' given is: '''tx1:y29u-mqjx-ppqq-sfp2-tt''' and is illustrated in the following table: TxRef character indexes and descriptions {| class="wikitable" style="text-align: top" !style="width:2em"|Index !style="width:2em"|0 !style="width:2em"|1 !style="width:2em"|2 !style="width:2em"|3 !style="width:2em"|4 !style="width:2em"|5 !style="width:2em"|6 !style="width:2em"|7 !style="width:2em"|8 !style="width:2em"|9 !style="width:2em"|10 !style="width:2em"|11 !style="width:2em"|12 !style="width:2em"|13 !style="width:2em"|14 !style="width:2em"|15 !style="width:2em"|16 !style="width:2em"|17 !style="width:2em"|18 !style="width:2em"|19 !style="width:2em"|20 !style="width:2em"|21 !style="width:2em"|22 !style="width:2em"|23 !style="width:2em"|24 !style="width:2em"|25 |- |Char: | style="background: #BBCCEE; color: black; text-align : center;" | t | style="background: #BBCCEE; color: black; text-align : center;" | x | style="background: #FFCCCC; color: black; text-align : center;" | 1 | style="background: #CCDDAA; color: black; text-align : center;" | : | style="background: #EEEEBB; color: black; text-align : center;" | y | style="background: #EEEEBB; color: black; text-align : center;" | 2 | style="background: #EEEEBB; color: black; text-align : center;" | 9 | style="background: #EEEEBB; color: black; text-align : center;" | u | style="background: #CCDDAA; color: black; text-align : center;" | - | style="background: #EEEEBB; color: black; text-align : center;" | m | style="background: #EEEEBB; color: black; text-align : center;" | q | style="background: #EEEEBB; color: black; text-align : center;" | j | style="background: #EEEEBB; color: black; text-align : center;" | x | style="background: #CCDDAA; color: black; text-align : center;" | - | style="background: #EEEEBB; color: black; text-align : center;" | p | style="background: #EEEEBB; color: black; text-align : center;" | p | style="background: #EEEEBB; color: black; text-align : center;" | q | style="background: #EEEEBB; color: black; text-align : center;" | q | style="background: #CCDDAA; color: black; text-align : center;" | - | style="background: #EEEEBB; color: black; text-align : center;" | s | style="background: #EEEEBB; color: black; text-align : center;" | f | style="background: #EEEEBB; color: black; text-align : center;" | p | style="background: #EEEEBB; color: black; text-align : center;" | 2 | style="background: #CCDDAA; color: black; text-align : center;" | - | style="background: #EEEEBB; color: black; text-align : center;" | t | style="background: #EEEEBB; color: black; text-align : center;" | t |} === Decoding === The Bech32 spec defines 32 valid characters as its "alphabet". All non-Bech32-alphabet characters present in a '''TxRef''' after the Bech32 separator character MUST be ignored/removed when parsing (except for terminating characters). We do not wish to expect the users to keep their '''TxRef'''s in good form and '''TxRef'''s may contains hyphens, colons, invisible spaces, uppercase or random characters. We expect users to copy, paste, write by-hand, write in a mix of character sets, etc. Parsers SHOULD attempt to correct for these and other common errors, reporting to the user any '''TxRef'''s that violate a proper Bech32 encoding. As of early 2021, '''TxRef''' has been in limited use for a couple of years and it is possible that there are some '''TxRef'''s in use which were created with the original specification of Bech32 before the Bech32m refinement was codified. Due to this possibility, a '''TxRef''' parser SHOULD be able to decode both Bech32m and Bech32 encoded '''TxRef'''s. In such a case, a '''TxRef''' parser SHOULD display or somehow notify the user that they are using an obsolete '''TxRef''' and that they should upgrade it to the Bech32m version. Additionally, the parser MAY also display the Bech32m version. == Rationale == == Reference implementations == C Reference Implementation (supports magic codes 0x3 and 0x6): https://github.com/jonasschnelli/bitcoin_txref_code Go Reference Implementation (supports magic codes 0x3 and 0x6): https://github.com/kulpreet/txref C++ Reference Implementation (supports magic codes 0x3, 0x4, 0x6, 0x7, 0x0 and 0x1): https://github.com/dcdpr/libtxref/ Java Reference Implementation (supports magic codes 0x3, 0x4, 0x6, 0x7, 0x0 and 0x1): https://github.com/dcdpr/libtxref-java/ == Appendices == === Test Examples === The following examples show values for various combinations on mainnet and testnet; encoding block height, transaction index, and an optional output index. ==== TxRef ==== The following list gives properly encoded mainnet '''TxRef'''s and the decoded hex values (block height, transaction index) * tx1:rqqq-qqqq-qwtv-vjr: (0x0, 0x0) * tx1:rqqq-qqll-lj68-7n2: (0x0, 0x7FFF) * tx1:r7ll-llqq-qats-vx9: (0xFFFFFF, 0x0) * tx1:r7ll-llll-lp6m-78v: (0xFFFFFF, 0x7FFF) The following list gives properly encoded testnet '''TxRef'''s and the decoded hex values (block height, transaction index) * txtest1:xqqq-qqqq-qrrd-ksa: (0x0, 0x0) * txtest1:xqqq-qqll-lljx-y35: (0x0, 0x7FFF) * txtest1:x7ll-llqq-qsr3-kym: (0xFFFFFF, 0x0) * txtest1:x7ll-llll-lvj6-y9j: (0xFFFFFF, 0x7FFF) The following list gives valid (sometimes strangely formatted) '''TxRef'''s and the decoded values (block height, transaction index)* * tx1:r29u-mqjx-putt-3p0: (456789, 1234) * TX1R29UMQJXPUTT3P0: (456789, 1234) * tx1 r29u mqjx putt 3p0: (456789, 1234) * tx1!r29u/mqj*x-putt^^3p0: (456789, 1234) The following list gives invalid '''TxRef'''s and the reason for their invalidity. * tx1:t7ll-llll-lcq3-aj4: Magic 0xB instead of 0x3. * tx1:rlll-llll-lu9m-00x: Version 1 instead of 0. * tx1:r7ll-llll-lqfu-gss2: Valid Bech32, but ten 5 bit unsigned chars instead of nine. * tx1:r7ll-llll-rt5h-wz: Valid Bech32, but eight 5 bit unsigned chars instead of nine. * tx1:r7ll-LLLL-lp6m-78v: Invalid Bech32 due to mixed case. Would decode correctly otherwise. ==== TxRef with Outpoints ==== The following list gives properly encoded mainnet '''TxRef'''s with Outpoints and the decoded values (block height, transaction index, outpoint index) * tx1:yqqq-qqqq-qqqq-rvum-0c: (0x0, 0x0, 0x0) * tx1:yqqq-qqll-lqqq-en8x-05: (0x0, 0x7FFF, 0x0) * tx1:y7ll-llqq-qqqq-ggjg-w6: (0xFFFFFF, 0x0, 0x0) * tx1:y7ll-llll-lqqq-jhf4-wk: (0xFFFFFF, 0x7FFF, 0x0) * tx1:yqqq-qqqq-qpqq-pw4v-kq: (0x0, 0x0, 0x1) * tx1:yqqq-qqll-lpqq-m3w3-kv: (0x0, 0x7FFF, 0x1) * tx1:y7ll-llqq-qpqq-22ml-hz: (0xFFFFFF, 0x0, 0x1) * tx1:y7ll-llll-lpqq-s4qz-hw: (0xFFFFFF, 0x7FFF, 0x1) * tx1:y29u-mqjx-ppqq-sfp2-tt: (456789, 1234, 1) The following list gives properly encoded testnet '''TxRef'''s with Outpoints and the decoded values (block height, transaction index, outpoint index) * txtest1:8qqq-qqqq-qqqq-d5ns-vl: (0x0, 0x0, 0x0) * txtest1:8qqq-qqll-lqqq-htgd-vn: (0x0, 0x7FFF, 0x0) * txtest1:87ll-llqq-qqqq-xsar-da: (0xFFFFFF, 0x0, 0x0) * txtest1:87ll-llll-lqqq-u0x7-d3: (0xFFFFFF, 0x7FFF, 0x0) * txtest1:8qqq-qqqq-qpqq-0k68-48: (0x0, 0x0, 0x1) * txtest1:8qqq-qqll-lpqq-4fp6-4t: (0x0, 0x7FFF, 0x1) * txtest1:87ll-llqq-qpqq-yj55-59: (0xFFFFFF, 0x0, 0x1) * txtest1:87ll-llll-lpqq-7d0f-5f: (0xFFFFFF, 0x7FFF, 0x1) * txtest1:829u-mqjx-ppqq-73wp-gv: (456789, 1234, 1) === TxRef Payload Value Choices: === Some calculations showing why we chose these particular bit-length of the block height and transaction index. ==== Block Height Value: ==== 24 bits: value can be between 0, and 0xFFFFFF (16777216 blocks). * In early April, 2021, there have been 677700 blocks * There are roughly (365 days * 24 hours * 6 blocks / hour) = 52560 blocks every year, implying about (16777216 - 677700) / 52560 = 306 more years of addressable blocks. * Some time before year 2327 this specification should be extended. ==== Tx Position Value: ==== 15 bits: value can be between 0x0, and 0x7FFF (32768 transactions). *The ''realistic'' smallest Tx is 83 Bytes for maximum 12047 tx in a block. **4B version + 1B tx_in count + 36B previous_output + 1B script length + 0B signature script + 4B sequence + 1B tx_out count + 8B amount + 1B script length + 23B pubkey script + 4B lock_time = 83B *The ''extreme'' smallest Tx is 60 Bytes for maximum 16665 tx in a block. **4B version + 1B tx_in count + 36B previous_output + 1B script length + 0B signature script + 4B sequence + 1B tx_out count + 8B amount + 1B script length + 0B pubkey script + 4B lock_time = 60B == Acknowledgements == Special Thanks to Pieter Wuille and Greg Maxwell for Bech32, a wonderful user-facing data encoding. ================================================ FILE: bip-0137.mediawiki ================================================
  BIP: 137
  Layer: Applications
  Title: Signatures of Messages using Private Keys
  Authors: Christopher Gilliard 
  Status: Deployed
  Type: Specification
  Assigned: 2019-02-16
  License: BSD-2-Clause
==Abstract== This document describes a signature format for signing messages with Bitcoin private keys. The specification is intended to describe the standard for signatures of messages that can be signed and verified between different clients that exist in the field today. Note: that a new signature format has been defined which has a number of advantages over this BIP, but to be backwards compatible with existing implementations this BIP will be useful. See BIP 322 [1] for full details on the new signature scheme. One of the key problems in this area is that there are several different types of Bitcoin addresses and without introducing specific standards it is unclear which type of address format is being used. See [2]. This BIP will attempt to address these issues and define a clear and concise format for Bitcoin signatures. ==Copyright== This BIP is licensed under the 2-clause BSD license. ==Motivation== Since Bitcoin private keys can not only be used to sign Bitcoin transactions, but also any other message, it has become customary to use them to sign various messages for differing purposes. Some applications of signing messages with a Bitcoin private key are as follows: proof of funds for collateral, credit worthiness, entrance to events, airdrops, audits as well as other applications. While there was no BIP written for how to digitally sign messages with Bitcoin private keys with P2PKH addresses it is a fairly well understood process, however with the introduction of Segwit (both in the form of P2SH and bech32) addresses, it is unclear how to distinguish a P2PKH, P2SH, or bech32 address from one another. This BIP proposes a standard signature format that will allow clients to distinguish between the different address formats. ==Specification== ===Background on ECDSA Signatures=== (For readers who already understand how ECDSA signatures work, you can skip this section as this is only intended as background information.) Elliptic Curve Digital Signature Algorithm or ECDSA is a cryptographic algorithm used by Bitcoin to ensure that funds can only be spent by their rightful owners. A few concepts related to ECDSA: private key: A secret number, known only to the person that generated it. A private key is essentially a randomly generated number. In Bitcoin, someone with the private key that corresponds to funds on the block chain can spend the funds. In Bitcoin, a private key is a single unsigned 256 bit integer (32 bytes). public key: A number that corresponds to a private key, but does not need to be kept secret. A public key can be calculated from a private key, but not vice versa. A public key can be used to determine if a signature is genuine (in other words, produced with the proper key) without requiring the private key to be divulged. In Bitcoin, public keys are either compressed or uncompressed. Compressed public keys are 33 bytes, consisting of a prefix either 0x02 or 0x03, and a 256-bit integer called x. The older uncompressed keys are 65 bytes, consisting of constant prefix (0x04), followed by two 256-bit integers called x and y (2 * 32 bytes). The prefix of a compressed key allows for the y value to be derived from the x value. signature: A number that proves that a signing operation took place. A signature is mathematically generated from a hash of something to be signed, plus a private key. The signature itself is two numbers known as r and s. With the public key, a mathematical algorithm can be used on the signature to determine that it was originally produced from the hash and the private key, without needing to know the private key. Signatures are either 73, 72, or 71 bytes long, with probabilities approximately 25%, 50% and 25% respectively, although sizes even smaller than that are possible with exponentially decreasing probability. Source [3]. ===Conventions with signatures used in Bitcoin=== Bitcoin signatures have the r and s values mentioned above, and a header. The header is a single byte and the r and s are each 32 bytes so a signature's size is 65 bytes. The header is used to specify information about the signature. It can be thought of as a bitmask with each bit in this byte having a meaning. The serialization format of a Bitcoin signature is as follows: [1 byte of header data][32 bytes for r value][32 bytes for s value] The header byte has a few components to it. First, it stores something known as the recId. This value is stored in the least significant 2 bits of the header. If the header is between a value of 31 and 34, this indicates that it is a compressed address. If the header value is between 35 and 38 inclusive, it is a p2sh segwit address. If the header value is between 39 and 42, it is a bech32 address. ===Procedure for signing/verifying a signature=== As noted above the signature is composed of three components, the header, r and s values. r/s can be computed with standard ECDSA library functions. Part of the header includes something called a recId. This is part of every ECDSA signature and should be generated by the ECDSA library. The recId is a number between 0 and 3 inclusive. The header is the recId plus a constant which indicates what type of Bitcoin address this is. For P2PKH address using an uncompressed public key this value is 27. For P2PKH address using compressed public key this value is 31. For P2SH-P2WPKH this value is 35 and for P2WPKH (version 0 witness) address this value is 39. So, you have the following ranges: * 27-30: P2PKH uncompressed * 31-34: P2PKH compressed * 35-38: Segwit P2SH * 39-42: Segwit Bech32 To verify a signature, the recId is obtained by subtracting this constant from the header value. ===Sample Code for processing a signature=== Note: this code is a modification of the BitcoinJ code which is written in java. public static ECKey signedMessageToKey(String message, String signatureBase64) throws SignatureException { byte[] signatureEncoded; try { signatureEncoded = Base64.decode(signatureBase64); } catch (RuntimeException e) { // This is what you get back from Bouncy Castle if base64 doesn't decode :( throw new SignatureException("Could not decode base64", e); } // Parse the signature bytes into r/s and the selector value. if (signatureEncoded.length < 65) throw new SignatureException("Signature truncated, expected 65 bytes and got " + signatureEncoded.length); int header = signatureEncoded[0] & 0xFF; // The header byte: 0x1B = first key with even y, 0x1C = first key with odd y, // 0x1D = second key with even y, 0x1E = second key with odd y if (header < 27 || header > 42) throw new SignatureException("Header byte out of range: " + header); BigInteger r = new BigInteger(1, Arrays.copyOfRange(signatureEncoded, 1, 33)); BigInteger s = new BigInteger(1, Arrays.copyOfRange(signatureEncoded, 33, 65)); ECDSASignature sig = new ECDSASignature(r, s); byte[] messageBytes = formatMessageForSigning(message); // Note that the C++ code doesn't actually seem to specify any character encoding. Presumably it's whatever // JSON-SPIRIT hands back. Assume UTF-8 for now. Sha256Hash messageHash = Sha256Hash.twiceOf(messageBytes); boolean compressed = false; // this section is added to support new signature types if(header>= 39) // this is a bech32 signature { header -= 12; compressed = true; } // this is a segwit p2sh signature else if(header >= 35) { header -= 8; compressed = true; } // this is a compressed key signature else if (header >= 31) { compressed = true; header -= 4; } int recId = header - 27; ECKey key = ECKey.recoverFromSignature(recId, sig, messageHash, compressed); if (key == null) throw new SignatureException("Could not recover public key from signature"); return key; } ==Backwards Compatibility== Since this format includes P2PKH keys, it is backwards compatible, but keep in mind some software has checks for ranges of headers and will report the newer segwit header types as errors. ==Implications== Message signing is an important use case and potentially underused due to the fact that, up until now, there has not been a formal specification for how wallets can sign messages using Bitcoin private keys. Bitcoin wallets should be interoperable and use the same conventions for determining a signature's validity. This BIP can also be updated as new signature formats emerge. ==Acknowledgements== * Konstantin Bay - review * Holly Casaletto - review * James Bryrer - review Note that the background on ECDSA signatures was taken from en.bitcoin.it and code sample modified from BitcoinJ. ==References== [1] - https://github.com/bitcoin/bips/blob/master/bip-0322.mediawiki [2] - https://github.com/bitcoin/bitcoin/issues/10542 [3] - https://en.bitcoin.it/wiki/Elliptic_Curve_Digital_Signature_Algorithm ================================================ FILE: bip-0140.mediawiki ================================================
  BIP: 140
  Layer: Consensus (soft fork)
  Title: Normalized TXID
  Authors: Christian Decker 
  Status: Closed
  Type: Specification
  Assigned: 2015-10-14
  License: PD
== Abstract == This BIP describes the use of normalized transaction IDs (NTXIDs) in order to eliminate transaction malleability, both in the third-party modification scenario as well as the participant modification scenario. The transaction ID is normalized by removing the signature scripts from transactions before computing its hash. The normalized transaction hashes are then used during the signature creation and signature verification of dependent transactions. == Motivation == Transaction malleability refers to the fact that transactions can be modified, either by one of the signers by re-signing the transaction or a third-party by modifying the signature representation. This is a problem since any modification to the serialized representation also changes the hash of the transaction, which is used by spending transaction to reference the funds that are being transferred. If a transaction is modified and later confirmed by ending up in the blockchain all transactions that depended on the original transaction are no longer valid, and thus orphaned. BIPs 62[[https://github.com/bitcoin/bips/blob/master/bip-0062.mediawiki|BIP 62 - Dealing with malleability]] and 66[[https://github.com/bitcoin/bips/blob/master/bip-0066.mediawiki|BIP 66 - Strict DER signatures]] alleviate the problem of third-party modification by defining a canonical representation of the signatures. However, checking the canonical representation is complex and may not eliminate all sources of third-party malleability. Furthermore, these BIPs do not address modifications by one of the signers, i.e., re-signing the transaction, because signers can produce any number of signatures due to the random parameter in ECDSA. This proposal eliminates malleability by removing the malleable signatures from the hash used to reference the outputs spent by a transaction. The new hash used to reference an output is called the ''normalized transaction ID''. The integrity of all data that is used to reference the output is guaranteed by the signature itself, and any modification that would change the normalized transaction ID would also invalidate the signature itself. Besides eliminating transaction malleability as a source of problems it also allows the use of transaction templates. Transaction templates simplify higher level protocols and allows new uses. They allow an unsigned template transaction to be used as a basis for a sequence of transaction and only once the sequence matches the signers' expectations they provide the necessary signatures for the template to become valid, thus opting in to the sequence. == Specification == The use of normalized transaction IDs is introduced as a softfork. The specification is divided into three parts: * Computation of the normalized transaction ID * Introduction of a new extensible signature verification opcode to enable softfork deployment * Changes to the UTXO tracking to enable normalized transaction ID lookup === Normalized Transaction ID computation === In order to calculate the normalized transaction ID, the signature script is stripped from each input of the transaction of non-coinbase transactions and each input is normalized. Stripping the signature script is achieved by setting the script's length to 0 and removing the uchar[] array from the TxIn.[[https://en.bitcoin.it/wiki/Protocol_Specification#tx|Protocol Specification: TX]] Inputs are then normalized by replacing the hash of each previous transaction with its normalized version if available, i.e., the normalized hash of the previous transaction that created the output being spent in the current transaction. Version 1 transactions do not have a normalized transaction ID hence the non-normalized transaction ID is used for input normalization. The normalized transaction ID is then computed as the double SHA 256 hash of the normalized transaction matching the existing transaction ID computation. The normalized transaction ID remains unchanged even if the signatures of the transaction are replaced/malleated and describe a class of semantically identical transactions. In the following we use ''transaction instance ID'' to refer to the transaction ID computed on the transaction including signatures. Normalized transaction IDs for coinbase transactions are computed with the signature script in the coinbase input, in order to avoid hash collisions. === OP_CHECKSIGEX === This BIP introduces a new opcode OP_CHECKSIGEX which replaces OP_NOP4. OP_CHECKSIGEX subsumes OP_CHECKSIGVERIFY and OP_CHECKMULTISIGVERIFY, and extends them by accepting a new VERSION parameter. The version parameter is a single integer pushed onto the stack before invoking OP_CHECKSIGEX and is used to group and evolve future versions of signature checking opcodes. When executed OP_CHECKSIGEX pops the version from the stack and then performs the signature check according to the specified version. If the verifying client does not support the specified version, i.e., the version was defined after the release of the client, the client must treat the OP_CHECKSIGEX as an OP_NOP. ==== Version 1 ==== The first version of OP_CHECKSIGEX (VERSION=1) implements normalized transaction IDs and uses Schnorr signatures instead of the current ECDSA signatures. Version 1 introduces the following new standard script format: m {pubkey}...{pubkey} n v OP_CHECKSIGEX with matching scriptSig format: {signature}...{signature} This is the standard ''m-of-n'' script defined in [https://github.com/bitcoin/bips/blob/master/bip-0011.mediawiki BIP 11] with an additional version parameter v and the new opcode. Singlesig transactions are encoded as ''1-of-1'' transactions. The existing OP_CHECKMULTISIG and OP_CHECKMULTISIGVERIFY have a bug[[https://bitcoin.org/en/developer-guide#multisig|Developer Documentation - Multisig]] that pops one argument too many from the stack. This bug is not reproduced in the implementation of OP_CHECKSIGEX, so the canonical solution of pushing a dummy value onto the stack is not necessary. The normalization is achieved by normalizing the transaction before computing the signaturehash, i.e., the hash that is signed. The transaction must be normalized by replacing all transaction IDs in the inputs by their normalized variants and stripping the signature scripts. The normalized transaction IDs are computed as described in the previous section. This normalization step is performed both when creating the signatures as well as when checking the signatures. === Tracking Normalized Transaction IDs === The transaction version is bumped to 2. The new version signals to clients receiving the transaction that they should track the normalized transaction ID along with the transaction instance ID in the unspent transaction output (UTXO) set. Upon receiving a version 2 transaction the client computes the normalized transaction ID, annotates the outputs with it, and adds them into the UTXO set indexed by the transaction instance ID as before. Transactions continue using the transaction instance ID to reference the outputs, but while checking the signature they may get normalized. All network messages continue to use the transaction instance ID to reference the transaction, specifically inv, getdata, tx and block messages still use transaction instance IDs, not the normalized transaction IDs. Outputs created by version 1 transactions are not annotated with the normalized transaction ID, and when normalizing the hashes in transaction inputs referencing version 1 outputs are not modified. == Rationale == === Normalization === Normalized transaction IDs are provably non-malleable since no data is included in the signaturehash whose integrity is not also proven in the signature, thus any modification causing the hash to change will also invalidate the signature. Normalized transactions are secure as they still use cryptographic hashes over all the semantic information of the transaction, i.e., the inputs, outputs and metadata, thus it is still computationally infeasible to cause a hash collision between transactions. There are a number of advantages to using normalized transaction IDs: * Like BIP 62 and BIP 66 it solves the problem of third-parties picking transactions out of the network, modifying them and reinjecting them. * ''m-of-n'' multisig outputs are often used in higher level protocols[[http://www.tik.ee.ethz.ch/file/716b955c130e6c703fac336ea17b1670/duplex-micropayment-channels.pdf|A Fast and Scalable Payment Network with Bitcoin Duplex Micropayment Channels ]][[http://lightning.network/lightning-network-paper.pdf|The Bitcoin Lightning Network: Scalable Off-Chain Instant Payments]] in which several parties sign a transaction. Without normalized transaction IDs it is trivial for one party to re-sign a transaction, hence changing the transaction hash and invalidating any transaction built on top of its outputs. Normalized transaction IDs force the ID not to change, even if a party replaces its signature. * Many higher level protocols build structures of transactions on top of multisig outputs that are not completely signed. This is currently not possible without one party holding a fully signed transaction and then calculating the ID. It is desirable to be able to build successive transactions without one party collecting all signatures, and thus possibly lock in funds unilaterally. Normalized transaction IDs allow the use of transaction templates, i.e., completely unsigned transactions upon which further transactions can be built, and only once every party is assured the structure matches its expectations it signs the template, thus validating the template. The only occurrence in which transactions can still be modified unilaterally is in the case SIGHASH_NONE, SIGHASH_SINGLE or SIGHASH_ANYONECANPAY is used. This however is not problematic since in these cases the creator of the transaction explicitly allows modification. In case of a transaction becoming invalid due to one of the inputs being malleated it is necessary to modify the spending transaction to reference the modified transaction ID. However, the signatures, which only use the normalized IDs, remain valid as long as the semantics of the funding transaction remain unchanged. An observer in the network may fix the transaction and reinject a corrected version. Using version 2 for transactions is an explicit opt-in to the normalized ID tracking and a simple upgrade for existing clients. It avoids having to reprocess the entire blockchain and computing the normalized transaction IDs for existing outputs in the UTXO. This would be further complicated by having to recursively compute normalized transaction IDs down to the coinbase transactions which created the coins. Tracking the normalized transaction IDs in the UTXO requires the storage of an additional hash per transaction whose outputs are not completely spent, which at 7,000,000 transactions with unspent outputs amounts to 224MB additional storage on disk. The coinbase transactions have been checked for hash-collisions and no collisions were found except for the coinbase transactions in blocks at heights 91842 and 91880, which are known to be identical[[https://github.com/bitcoin/bips/blob/master/bip-0030.mediawiki|BIP 30 - Duplicate transactions]], and motivated the introduction of BIP 34.[[https://github.com/bitcoin/bips/blob/master/bip-0034.mediawiki|Block v2, Height in Coinbase]] Since coinbase transactions are invalid if transmitted outside of a block it is not possible to modify them on the fly and since they only mature after being included for a long time in the blockchain they are considered safe. === OP_CHECKSIGEX === The new opcode OP_CHECKSIGEX was introduced in order to allow the use of normalized transaction IDs as a softfork and in order to keep the number of OP_NOPs needed to a bare minimum, while enabling future soft-fork updates to the signing algorithms. The additional argument containing the version can be pushed on the stack using a single byte up to version 16 (OP_1 - OP_16), resulting in one byte overhead for this script type. Using the standard multisig format also for 1-of-1 transactions add an additional 2 bytes, however it also removes the bug requiring a dummy push, resulting in a single byte overhead. Furthermore, using Schnorr signatures instead of ECDSA brings a number of improvements that reduce the size of transactions (''m-of-m'' is the same size as ''1-of-1'') and increase verification speed (batch signature validation by summing up keys and signatures). The code is already in bitcoin/secp256k1 and can be merged in. We limited the description of this BIP to re-using BIP 11 style ''m-of-n'' scripts to keep it short, however Schnorr also allows a number of more complex applications which we defer to future BIPs. Version 0 was intentionally skipped in order to guarantee that the top-most element before OP_CHECKSIGEX is non-zero. This is necessary to guarantee that non-upgraded clients, which interpret OP_CHECKSIGEX as OP_NOP4, do not end up with a zero value on top of the stack after execution, which would be interpreted as script failure. === Impact === This is a softfork which replaces OP_NOP4 with the new implementation of OP_CHECKSIGEX, as such the impact on the network is minimal. Wallets that do not implement this opcode will not be able to verify the validity of the scripts, however if transactions using OP_CHECKSIGEX are included in blocks they will accept them and track the inputs correctly. This is guaranteed since the transaction inputs still use the non-normalized transaction ID to reference the outputs to be claimed, hence non-upgraded wallets can still lookup the outputs and mark them as spent. Furthermore, clients that do not implement this BIP are unable to identify outputs using this script as their own, however upgrading and rescanning the blockchain will make them available. == See also == * [[bip-0062.mediawiki|BIP 62: Dealing with malleability]] * [[bip-0066.mediawiki|BIP 66: Strict DER Signatures]] == References == ==Copyright== This document is placed in the public domain. ================================================ FILE: bip-0141.mediawiki ================================================
  BIP: 141
  Layer: Consensus (soft fork)
  Title: Segregated Witness (Consensus layer)
  Authors: Eric Lombrozo 
           Johnson Lau 
           Pieter Wuille 
  Status: Deployed
  Type: Specification
  Assigned: 2015-12-21
  License: PD
==Abstract== This BIP defines a new structure called a "witness" that is committed to blocks separately from the transaction merkle tree. This structure contains data required to check transaction validity but not required to determine transaction effects. In particular, scripts and signatures are moved into this new structure. The witness is committed in a tree that is nested into the block's existing merkle root via the coinbase transaction for the purpose of making this BIP soft fork compatible. A future hard fork can place this tree in its own branch. ==Motivation== The entirety of the transaction's effects are determined by output consumption (spends) and new output creation. Other transaction data, and signatures in particular, are only required to validate the blockchain state, not to determine it. By removing this data from the transaction structure committed to the transaction merkle tree, several problems are fixed: # '''Nonintentional malleability becomes impossible'''. Since signature data is no longer part of the transaction hash, changes to how the transaction was signed are no longer relevant to transaction identification. As a solution of transaction malleability, this is superior to the canonical signature approach ([https://github.com/bitcoin/bips/blob/master/bip-0062.mediawiki BIP62]): #* It prevents involuntary transaction malleability for any type of scripts, as long as all inputs are signed (with at least one CHECKSIG or CHECKMULTISIG operation) #* In the case of an m-of-n CHECKMULTISIG script, a transaction is malleable only with agreement of m private key holders (as opposed to only 1 private key holder with BIP62) #* It prevents involuntary transaction malleability due to unknown ECDSA signature malleability #* It allows creation of unconfirmed transaction dependency chains without counterparty risk, an important feature for offchain protocols such as the Lightning Network # '''Transmission of signature data becomes optional'''. It is needed only if a peer is trying to validate a transaction instead of just checking its existence. This reduces the size of SPV proofs and potentially improves the privacy of SPV clients as they can download more transactions using the same bandwidth. # '''Some constraints could be bypassed with a soft fork''' by moving part of the transaction data to a structure unknown to current protocol, for example: #* Size of witness could be ignored / discounted when calculating the block size, effectively increasing the block size to some extent #* Hard coded constants, such as maximum data push size (520 bytes) or sigops limit could be reevaluated or removed #* New script system could be introduced without any limitation from the existing script semantic. For example, a new transaction digest algorithm for transaction signature verification is described in [https://github.com/bitcoin/bips/blob/master/bip-0143.mediawiki BIP143] ==Specification== === Transaction ID === A new data structure, witness, is defined. Each transaction will have 2 IDs. Definition of txid remains unchanged: the double SHA256 of the traditional serialization format: [nVersion][txins][txouts][nLockTime] A new wtxid is defined: the double SHA256 of the new serialization with witness data: [nVersion][marker][flag][txins][txouts][witness][nLockTime] Format of nVersion, txins, txouts, and nLockTime are same as traditional serialization. The marker MUST be a 1-byte zero value: 0x00. The flag MUST be a 1-byte non-zero value. Currently, 0x01 MUST be used. The witness is a serialization of all witness fields of the transaction. Each txin is associated with a witness field. A witness field starts with a var_int to indicate the number of stack items for the txin. It is followed by stack items, with each item starts with a var_int to indicate the length. Witness data is NOT script. A non-witness program (defined hereinafter) txin MUST be associated with an empty witness field, represented by a 0x00. If all txins are not witness program, a transaction's wtxid is equal to its txid. === Commitment structure === A new block rule is added which requires a commitment to the wtxid. The wtxid of coinbase transaction is assumed to be 0x0000....0000. A witness root hash is calculated with all those wtxid as leaves, in a way similar to the hashMerkleRoot in the block header. The commitment is recorded in a scriptPubKey of the coinbase transaction. It must be at least 38 bytes, with the first 6-byte of 0x6a24aa21a9ed, that is: 1-byte - OP_RETURN (0x6a) 1-byte - Push the following 36 bytes (0x24) 4-byte - Commitment header (0xaa21a9ed) 32-byte - Commitment hash: Double-SHA256(witness root hash|witness reserved value) 39th byte onwards: Optional data with no consensus meaning and the coinbase's input's witness must consist of a single 32-byte array for the witness reserved value. If there are more than one scriptPubKey matching the pattern, the one with highest output index is assumed to be the commitment. If all transactions in a block do not have witness data, the commitment is optional. === Witness program === A scriptPubKey (or redeemScript as defined in BIP16/P2SH) that consists of a 1-byte push opcode (one of OP_0,OP_1,OP_2,...,OP_16) followed by a direct data push between 2 and 40 bytes gets a new special meaning. The value of the first push is called the "version byte". The following byte vector pushed is called the "witness program". In more detail, this means a scriptPubKey or redeemScript which consists of (in order): * First, byte 0x00 (OP_0) or any byte between 0x51 (OP_1) and 0x60 (OP_16) inclusive (the version byte). * Then, a byte ''L'' between 0x02 (push of 2 bytes) and 0x28 (push of 40 bytes) inclusive. * Finally, ''L'' arbitrary bytes (the witness program). There are two cases in which witness validation logic are triggered. Each case determines the location of the witness version byte and program, as well as the form of the scriptSig: # Triggered by a scriptPubKey that is exactly a push of a version byte, plus a push of a witness program. The scriptSig must be exactly empty or validation fails. (''"native witness program"'') # Triggered when a scriptPubKey is a P2SH script, and the BIP16 redeemScript pushed in the scriptSig is exactly a push of a version byte plus a push of a witness program. The scriptSig must be exactly a push of the BIP16 redeemScript or validation fails. (''"P2SH witness program"'') If the version byte is 0, and the witness program is 20 bytes (''L = 20''): * It is interpreted as a pay-to-witness-public-key-hash (P2WPKH) program. * The witness must consist of exactly 2 items (≤ 520 bytes each). The first one a signature, and the second one a public key. * The HASH160 of the public key must match the 20-byte witness program. * After normal script evaluation, the signature is verified against the public key with CHECKSIG operation. The verification must result in a single TRUE on the stack. If the version byte is 0, and the witness program is 32 bytes (''L = 32''): * It is interpreted as a pay-to-witness-script-hash (P2WSH) program. * The witness must consist of an input stack to feed to the script, followed by a serialized script (witnessScript). * The witnessScript (≤ 10,000 bytes) is popped off the initial witness stack. SHA256 of the witnessScript must match the 32-byte witness program. * The witnessScript is deserialized, and executed after normal script evaluation with the remaining witness stack (≤ 520 bytes for each stack item). * The script must not fail, and result in exactly a single TRUE on the stack. If the version byte is 0, but the witness program is neither 20 nor 32 bytes, the script must fail.For example, a scriptPubKey with OP_0 followed by a 40-byte non-zero data push will fail due to incorrect program size. However, a scriptPubKey with OP_0 followed by a 41-byte non-zero data push will pass, since it is not considered to be a witness program If the version byte is 1 to 16, no further interpretation of the witness program or witness stack happens, and there is no size restriction for the witness stack. These versions are reserved for future extensions.For backward compatibility, for any version byte from 0 to 16, the script must fail if the witness program has a CastToBool value of zero. However, having a hash like this is a successful preimage attack against the hash function, and the risk is negligible. === Other consensus critical limits === ==== Block size ==== Blocks are currently limited to 1,000,000 bytes (1MB) total size. We change this restriction as follows: ''Block weight'' is defined as ''Base size'' * 3 + ''Total size''. (rationaleRationale of using a single composite constraint, instead of two separate limits such as 1MB base data and 3MB witness data: Using two separate limits would make mining and fee estimation nearly impossible. Miners would need to solve a complex non-linear optimization problem to find the set of transactions that maximize fees given both constraints, and wallets would not be able to know what to pay as it depends on which of the two conditions is most constrained by the time miners try to produce blocks with their transactions in. Another problem with such an approach is freeloading. Once a set of transactions hit the base data 1MB constraint, up to 3MB extra data could be added to the witness by just minimally increasing the fee. The marginal cost for extra witness space effectively becomes zero in that case.) ''Base size'' is the block size in bytes with the original transaction serialization without any witness-related data, as seen by a non-upgraded node. ''Total size'' is the block size in bytes with transactions serialized as described in [[bip-0144.mediawiki|BIP144]], including base data and witness data. The new rule is ''block weight'' ≤ 4,000,000. ==== Sigops ==== Sigops per block is currently limited to 20,000. We change this restriction as follows: Sigops in the current pubkey script, signature script, and P2SH check script are counted at 4 times their previous value. The sigop limit is likewise quadrupled to ≤ 80,000. Each P2WPKH input is counted as 1 sigop. In addition, opcodes within a P2WSH witnessScript are counted identically as previously within the P2SH redeemScript. That is, CHECKSIG is counted as only 1 sigop. When preceded by OP_1 to OP_16 CHECKMULTISIG is counted as 1 to 16 sigops respectively, otherwise it is counted as 20 sigops. This rule applies to both native witness program and P2SH witness program. === Additional definitions === The following definitions are not used for consensus limits, but are suggested to provide language consistent with the terminology introduced above. ==== Transaction size calculations ==== ''Transaction weight'' is defined as ''Base transaction size'' * 3 + ''Total transaction size'' (ie. the same method as calculating ''Block weight'' from ''Base size'' and ''Total size''). ''Virtual transaction size'' is defined as ''Transaction weight'' / 4 (rounded up to the next integer). ''Base transaction size'' is the size of the transaction serialised with the witness data stripped. ''Total transaction size'' is the transaction size in bytes serialized as described in [[bip-0144.mediawiki|BIP144]], including base data and witness data. === New script semantics === Despite that the script language for P2WPKH and P2WSH looks very similar to pre-segregated witness script, there are several notable differences. Users MUST NOT assume that a script spendable in pre-segregated witness system would also be spendable as a P2WPKH or P2WSH script. Before large-scale deployment in the production network, developers should test the scripts on testnet with the default relay policy turned on, and with a small amount of money after BIP141 is activated on mainnet. A major difference at consensus level is described in [https://github.com/bitcoin/bips/blob/master/bip-0143.mediawiki BIP143], as a new transaction digest algorithm for signature verification in version 0 witness program. Three relay and mining policies are also included in the first release of segregated witness at reference implementation version 0.13.1. Softforks based on these policies are likely to be proposed in the near future. To avoid indefinite delay in transaction confirmation and permanent fund loss in a potential softfork, users MUST observe the new semantics carefully: # Only compressed public keys are accepted in P2WPKH and P2WSH (See [https://github.com/bitcoin/bips/blob/master/bip-0143.mediawiki#Restrictions_on_public_key_type BIP143]) # The argument of OP_IF/NOTIF in P2WSH must be minimalhttps://lists.linuxfoundation.org/pipermail/bitcoin-dev/2016-August/013014.html # Signature(s) must be null vector(s) if an OP_CHECKSIG or OP_CHECKMULTISIG is failed (for both pre-segregated witness script and P2WSH. See [https://github.com/bitcoin/bips/blob/master/bip-0146.mediawiki BIP146]) == Examples == === P2WPKH === The following example is a version 0 pay-to-witness-public-key-hash (P2WPKH): witness: scriptSig: (empty) scriptPubKey: 0 <20-byte-key-hash> (0x0014{20-byte-key-hash}) The '0' in scriptPubKey indicates the following push is a version 0 witness program. The length of the witness program indicates that it is a P2WPKH type. The witness must consist of exactly 2 items. The HASH160 of the pubkey in witness must match the witness program. The signature is verified as CHECKSIG Comparing with a traditional P2PKH output, the P2WPKH equivalent occupies 3 less bytes in the scriptPubKey, and moves the signature and public key from scriptSig to witness. === P2WPKH nested in BIP16 P2SH === The following example is the same P2WPKH, but nested in a BIP16 P2SH output. witness: scriptSig: <0 <20-byte-key-hash>> (0x160014{20-byte-key-hash}) scriptPubKey: HASH160 <20-byte-script-hash> EQUAL (0xA914{20-byte-script-hash}87) The only item in scriptSig is hashed with HASH160, compared against the 20-byte-script-hash in scriptPubKey, and interpreted as: 0 <20-byte-key-hash> The public key and signature are then verified as described in the previous example. Comparing with the previous example, the scriptPubKey is 1 byte bigger and the scriptSig is 23 bytes bigger. Although a nested witness program is less efficient, its payment address is fully transparent and backward compatible for all Bitcoin reference client since version 0.6.0. === P2WSH === The following example is an 1-of-2 multi-signature version 0 pay-to-witness-script-hash (P2WSH). witness: 0 <1 2 CHECKMULTISIG> scriptSig: (empty) scriptPubKey: 0 <32-byte-hash> (0x0020{32-byte-hash}) The '0' in scriptPubKey indicates the following push is a version 0 witness program. The length of the witness program indicates that it is a P2WSH type. The last item in the witness (the "witnessScript") is popped off, hashed with SHA256, compared against the 32-byte-hash in scriptPubKey, and deserialized: 1 2 CHECKMULTISIG The script is executed with the remaining data from witness: 0 1 2 CHECKMULTISIG P2WSH allows maximum script size of 10,000 bytes, as the 520-byte push limit is bypassed. The scriptPubKey occupies 34 bytes, as opposed to 23 bytes of BIP16 P2SH. The increased size improves security against possible collision attacks, as 280 work is not infeasible anymore (By the end of 2015, 284 hashes have been calculated in Bitcoin mining since the creation of Bitcoin). The spending script is same as the one for an equivalent BIP16 P2SH output but is moved to witness. === P2WSH nested in BIP16 P2SH === The following example is the same 1-of-2 multi-signature P2WSH script, but nested in a BIP16 P2SH output. witness: 0 <1 2 CHECKMULTISIG> scriptSig: <0 <32-byte-hash>> (0x220020{32-byte-hash}) scriptPubKey: HASH160 <20-byte-hash> EQUAL (0xA914{20-byte-hash}87) The only item in scriptSig is hashed with HASH160, compared against the 20-byte-hash in scriptPubKey, and interpreted as: 0 <32-byte-hash> The P2WSH witnessScript is then executed as described in the previous example. Comparing with the previous example, the scriptPubKey is 11 bytes smaller (with reduced security) while witness is the same. However, it also requires 35 bytes in scriptSig. === Extensible commitment structure === The new commitment in coinbase transaction is a hash of the witness root hash and a witness reserved value. The witness reserved value currently has no consensus meaning, but in the future allows new commitment values for future softforks. For example, if a new consensus-critical commitment is required in the future, the commitment in coinbase becomes: Double-SHA256(Witness root hash|Hash(new commitment|witness reserved value)) For backward compatibility, the Hash(new commitment|witness reserved value) will go to the coinbase witness, and the witness reserved value will be recorded in another location specified by the future softfork. Any number of new commitment could be added in this way. Any commitments that are not consensus-critical to Bitcoin, such as merge-mining, MUST NOT use the witness reserved value to preserve the ability to do upgrades of the Bitcoin consensus protocol. The optional data space following the commitment also leaves room for metadata of future softforks, and MUST NOT be used for other purpose. === Trust-free unconfirmed transaction dependency chain === Segregated witness fixes the problem of transaction malleability fundamentally, which enables the building of unconfirmed transaction dependency chains in a trust-free manner. Two parties, Alice and Bob, may agree to send certain amount of Bitcoin to a 2-of-2 multisig output (the "funding transaction"). Without signing the funding transaction, they may create another transaction, time-locked in the future, spending the 2-of-2 multisig output to third account(s) (the "spending transaction"). Alice and Bob will sign the spending transaction and exchange the signatures. After examining the signatures, they will sign and commit the funding transaction to the blockchain. Without further action, the spending transaction will be confirmed after the lock-time and release the funding according to the original contract. It also retains the flexibility of revoking the original contract before the lock-time, by another spending transaction with shorter lock-time, but only with mutual-agreement of both parties. Such setups are not possible with BIP62 as the malleability fix, since the spending transaction could not be created without both parties first signing the funding transaction. If Alice reveals the funding transaction signature before Bob does, Bob is able to lock up the funding indefinitely without ever signing the spending transaction. Unconfirmed transaction dependency chain is a fundamental building block of more sophisticated payment networks, such as duplex micropayment channel and the Lightning Network, which have the potential to greatly improve the scalability and efficiency of the Bitcoin system. == Future extensions == === Compact fraud proof for SPV nodes === Bitcoin right now only has two real security models. A user either runs a full-node which validates every block with all rules in the system, or a SPV (Simple Payment Verification) client which only validates the headers as a proof of publication of some transactions. The Bitcoin whitepaper suggested that SPV nodes may accept alerts from full nodes when they detect an invalid block, prompting the SPV node to download the questioned blocks and transactions for validation. This approach, however, could become a DoS attack vector as there is virtually no cost to generate a false alarm. An alarm must come with a compact, yet deterministic fraud proof. In the current Bitcoin protocol, it is possible to generate compact fraud proof for almost all rules except a few: # It is not possible to prove a miner has introduced too many Bitcoins in the coinbase transaction outputs without showing the whole block itself and all input transactions. # It is not possible to prove the violation of any block specific constraints, such as size and sigop limits, without showing the whole block (and all input transactions in the case of sigop limit) # It is not possible to prove the spending of a non-existing input without showing all transaction IDs in the blockchain way back to the genesis block. Extra witness data can be committed that allows short proofs of block invalidity that SPV nodes can quickly verify: # Sum trees for transaction fee can be committed making it possible to construct short proofs that the miner does not add excessive fees to the coinbase transaction. Similar for the block size and sigop count limit. # Backlinks for the outputs spent by the transaction's inputs can be provided. These backlinks consist of a block hash and an offset that thin clients can easily query and check to verify that the outputs exist. These commitments could be included in the extensible commitment structure through a soft fork and will be transparent to nodes that do not understand such new rules. === New script system === Since a version byte is pushed before a witness program, and programs with unknown versions are always considered as anyone-can-spend script, it is possible to introduce any new script system with a soft fork. The witness as a structure is not restricted by any existing script semantics and constraints, the 520-byte push limit in particular, and therefore allows arbitrarily large scripts and signatures. Examples of new script systems include Schnorr signatures, which reduce the size of multisig transactions dramatically; Lamport signatures, which are quantum computing resistant; and Merklized abstract syntax trees, which allow very compact witnesses for conditional scripts with extreme complexity. === Per-input lock-time and relative-lock-time === Currently there is only one nLockTime field in a transaction and all inputs must share the same value. [https://github.com/bitcoin/bips/blob/master/bip-0068.mediawiki BIP68] enables per-input relative-lock-time using the nSequence field, however, with a limited lock-time period and resolution. With a soft fork, it is possible to introduce a separate witness structure to allow per-input lock-time and relative-lock-time, and a new script system that could sign and manipulate the new data (like [https://github.com/bitcoin/bips/blob/master/bip-0065.mediawiki BIP65] and [https://github.com/bitcoin/bips/blob/master/bip-0112.mediawiki BIP112]). == Backward compatibility == As a soft fork, older software will continue to operate without modification. Non-upgraded nodes, however, will not see nor validate the witness data and will consider all witness programs as anyone-can-spend scripts (except a few edge cases where the witness programs are equal to 0, which the script must fail). Wallets should always be wary of anyone-can-spend scripts and treat them with suspicion. Non-upgraded nodes are strongly encouraged to upgrade in order to take advantage of the new features. '''What a non-upgraded wallet can do''' * Receiving bitcoin from non-upgraded and upgraded wallets * Sending bitcoin to non-upgraded and upgraded wallets with traditional P2PKH address (without any benefit of segregated witness) * Sending bitcoin to upgraded wallets using a P2SH address * Sending bitcoin to upgraded wallets using a native witness program through [https://github.com/bitcoin/bips/blob/master/bip-0070.mediawiki BIP70] payment protocol '''What a non-upgraded wallet cannot do''' * Validating segregated witness transaction. It assumes such a transaction is always valid == Deployment == This BIP will be deployed by "version bits" BIP9 with the name "segwit" and using bit 1. For Bitcoin mainnet, the BIP9 starttime will be midnight 15 November 2016 UTC (Epoch timestamp 1479168000) and BIP9 timeout will be midnight 15 November 2017 UTC (Epoch timestamp 1510704000). For Bitcoin testnet, the BIP9 starttime will be midnight 1 May 2016 UTC (Epoch timestamp 1462060800) and BIP9 timeout will be midnight 1 May 2017 UTC (Epoch timestamp 1493596800). == Credits == Special thanks to Gregory Maxwell for originating many of the ideas in this BIP and Luke-Jr for figuring out how to deploy this as a soft fork. == Footnotes == == Reference Implementation == https://github.com/bitcoin/bitcoin/pull/8149 == References == *[[bip-0016.mediawiki|BIP16 Pay to Script Hash]] *[[bip-0143.mediawiki|BIP143 Transaction Signature Verification for Version 0 Witness Program]] *[[bip-0144.mediawiki|BIP144 Segregated Witness (Peer Services)]] *[[bip-0173.mediawiki|BIP173 Base32 address format for native v0-16 witness outputs]] == Copyright == This document is placed in the public domain. ================================================ FILE: bip-0142.mediawiki ================================================
  BIP: 142
  Layer: Applications
  Title: Address Format for Segregated Witness
  Authors: Johnson Lau 
  Status: Closed
  Type: Specification
  Assigned: 2015-12-24
  License: PD
== Abstract == This BIP describes new types of Bitcoin address to support native segregated witness transactions with 20-byte and 32-byte program. == Motivation == To define standard payment address for native segregated witness (segwit) transactions to promote early adoption of the more efficient transaction method. == Specification == The new Bitcoin address format defined is for the Pay-to-Witness-Public-Key-Hash (P2WPKH) and Pay-to-Witness-Script-Hash (P2WSH) transaction described in segregated witness soft fork (BIP141). The scriptPubKey is an OP_0 followed by a push of 20-byte-hash (P2WPKH) or 32-byte hash (P2WSH). The new address is encoded in a way similar to existing address formats: base58-encode: [1-byte address version] [1-byte witness program version] [0x00] [20/32-byte-hash] [4-byte checksum] For P2WPKH address, the address version is 6 (0x06) for a main-network address or 3 (0x03) for a testnet address. For P2WSH address, the address version is 10 (0x0A) for a main-network address or 40 (0x28) for a testnet address. The witness program version is a 1-byte value between 0 (0x00) and 16 (0x10). Only version 0 is defined in BIP141. Versions 1 to 16 are reserved for future extensions. Following the witness program version is a 0x00 padding to make sure that each witness program version will have a unique prefix. Following the padding is the program hash, 20 byte for a P2WPKH address and 32 byte for a P2WSH address. The 4-byte checksum is the first four bytes of the double SHA256 hash of the serialization of the previous items. All addresses generated with this scheme will have a constant length, with 36 digits for 20-byte and 53 digits for 32-byte. Different witness program versions will have a unique prefix, as shown in the following table: {|class="wikitable" style="text-align: center;" |- !rowspan=3 style=""|Witness program version !colspan=4 style=""|Hash size |- !colspan=2 style=""|20-byte (36 characters) !colspan=2 style=""|32-byte (53 characters) |- !Mainnet !Testnet !Mainnet !Testnet |- |0||p2||QW||7Xh||T7n |- |1||p4||QY||7Xq||T7w |- |2||p6||Qa||7Xz||T85 |- |3||p7||Qc||7Y9||T8E |- |4||pA||Qe||7YH||T8N |- |5||pB||Qf||7YS||T8X |- |6||pD||Qh||7Ya||T8g |- |7||pF||Qj||7Yj||T8p |- |8||pG||Qm||7Yt||T8y |- |9||pJ||Qn||7Z2||T97 |- |10||pL||Qp||7ZB||T9G |- |11||pN||Qr||7ZK||T9Q |- |12||pQ||Qt||7ZU||T9Z |- |13||pS||Qv||7Zc||T9i |- |14||pT||Qw||7Zm||T9r |- |15||pV||Qy||7Zv||TA1 |- |16||pX||R1||7a4||TA9 |- |} == Rationale == BIP141 defines 2 ways of encoding a "witness program", a data push of 2 to 32 bytes: * A native witness program output is a scriptPubKey with a push of version byte followed by a push of witness program, and nothing else; * Segwit-in-P2SH is a BIP16 P2SH redeemScript with a push of version byte followed by a push of witness program, while the scriptPubKey looks like a normal P2SH output. Considering the BIP13 P2SH address has been defined in 2012, using segwit-in-P2SH allows most existing wallets to pay a segwit-compatible wallet without any upgrade. However, this method requires more block space and is only a short-term solution to make the transition smoother. Eventually, all users are expected to use the more efficient native witness program as the primary method of payment. The drawbacks of Bitcoin addresses have been extensively discussed in BIP13. Since then, better payment methods have been proposed or deployed, for example: *BIP47 Reusable Payment Codes for Hierarchical Deterministic Wallets *BIP63 Stealth Addresses *BIP70 Payment protocol However, none of these are as widely adopted as the suboptimal base-58 scriptPubKey template addresses, which is still a standard for the whole eco-system, from wallets, block explorers, merchants, exchanges, to end users. It is believed that the proposed P2WPKH and P2WSH address format is the easiest way for wallets and services to adopt native witness program, which is particularly important in the context of scaling the capacity of the blockchain. While P2WPKH address is specific for simple payment to a single public key, P2WSH address allows arbitrarily complex segwit transactions, similar to the BIP13 P2SH address. == Compatibility == This proposal is not backward-compatible. However, an older implementation will report the new address type as invalid, and refuse to create a transaction. This proposal is forward-compatible with future versions of witness programs of 20 and 32 bytes. == Example == The following public key, 0450863AD64A87AE8A2FE83C1AF1A8403CB53F53E486D8511DAD8A04887E5B23522CD470243453A299FA9E77237716103ABC11A1DF38855ED6F2EE187E9C582BA6 when encoded as a P2PKH template, would become: DUP HASH160 <010966776006953D5567439E5E39F86A0D273BEE> EQUALVERIFY CHECKSIG With the corresponding version 1 Bitcoin address being: 16UwLL9Risc3QfPqBUvKofHmBQ7wMtjvM When the same public key is encoded as P2WPKH, the scriptPubKey becomes: OP_0 <010966776006953D5567439E5E39F86A0D273BEE> Using 0x06 as address version, followed by 0x00 as witness program version, and a 0x00 padding, the equivalent P2WPKH address is: p2xtZoXeX5X8BP8JfFhQK2nD3emtjch7UeFm == Reference implementation == https://github.com/theuni/bitcoin/commit/ede1b57058ac8efdefe61f67395affb48f2c0d80 == References == * [[bip-0013.mediawiki|BIP 13: Address Format for pay-to-script-hash]] * [[bip-0016.mediawiki|BIP 16: Pay to Script Hash]] * [[bip-0070.mediawiki|BIP 70: Payment Protocol]] * [[bip-0141.mediawiki|BIP 141: Segregated Witness]] == Copyright == This work is placed in the public domain. ================================================ FILE: bip-0143.mediawiki ================================================
  BIP: 143
  Layer: Consensus (soft fork)
  Title: Transaction Signature Verification for Version 0 Witness Program
  Authors: Johnson Lau 
           Pieter Wuille 
  Status: Deployed
  Type: Specification
  Assigned: 2016-01-03
  License: PD
== Abstract == This proposal defines a new transaction digest algorithm for signature verification in version 0 witness program, in order to minimize redundant data hashing in verification, and to cover the input value by the signature. == Motivation == There are 4 ECDSA signature verification codes in the original Bitcoin script system: CHECKSIG, CHECKSIGVERIFY, CHECKMULTISIG, CHECKMULTISIGVERIFY (“sigops”). According to the sighash type (ALL, NONE, SINGLE, ANYONECANPAY), a transaction digest is generated with a double SHA256 of a serialized subset of the transaction, and the signature is verified against this digest with a given public key. The detailed procedure is described in a Bitcoin Wiki article. [https://en.bitcoin.it/wiki/OP_CHECKSIG] Unfortunately, there are at least 2 weaknesses in the original SignatureHash transaction digest algorithm: * For the verification of each signature, the amount of data hashing is proportional to the size of the transaction. Therefore, data hashing grows in O(n2) as the number of sigops in a transaction increases. While a 1 MB block would normally take 2 seconds to verify with an average computer in 2015, a 1MB transaction with 5569 sigops may take 25 seconds to verify. This could be fixed by optimizing the digest algorithm by introducing some reusable “midstate”, so the time complexity becomes O(n). [https://web.nvd.nist.gov/view/vuln/detail?vulnId=CVE-2013-2292 CVE-2013-2292][https://bitcointalk.org/?topic=140078 New Bitcoin vulnerability: A transaction that takes at least 3 minutes to verify][http://rusty.ozlabs.org/?p=522 The Megatransaction: Why Does It Take 25 Seconds?] * The algorithm does not involve the amount of Bitcoin being spent by the input. This is usually not a problem for online network nodes as they could request for the specified transaction to acquire the output value. For an offline transaction signing device ("cold wallet"), however, the unknowing of input amount makes it impossible to calculate the exact amount being spent and the transaction fee. To cope with this problem a cold wallet must also acquire the full transaction being spent, which could be a big obstacle in the implementation of lightweight, air-gapped wallet. By including the input value of part of the transaction digest, a cold wallet may safely sign a transaction by learning the value from an untrusted source. In the case that a wrong value is provided and signed, the signature would be invalid and no funding might be lost. [https://bitcointalk.org/index.php?topic=181734.0 SIGHASH_WITHINPUTVALUE: Super-lightweight HW wallets and offline data] Deploying the aforementioned fixes in the original script system is not a simple task. That would be either a hardfork, or a softfork for new sigops without the ability to remove or insert stack items. However, the introduction of segregated witness softfork offers an opportunity to define a different set of script semantics without disrupting the original system, as the unupgraded nodes would always consider such a transaction output is spendable by arbitrary signature or no signature at all. [https://github.com/bitcoin/bips/blob/master/bip-0141.mediawiki BIP141: Segregated Witness (Consensus layer)] == Specification == A new transaction digest algorithm is defined, but only applicable to sigops in version 0 witness program: Double SHA256 of the serialization of: 1. nVersion of the transaction (4-byte little endian) 2. hashPrevouts (32-byte hash) 3. hashSequence (32-byte hash) 4. outpoint (32-byte hash + 4-byte little endian) 5. scriptCode of the input (serialized as scripts inside CTxOuts) 6. value of the output spent by this input (8-byte little endian) 7. nSequence of the input (4-byte little endian) 8. hashOutputs (32-byte hash) 9. nLocktime of the transaction (4-byte little endian) 10. sighash type of the signature (4-byte little endian) Semantics of the original sighash types remain unchanged, except the following: # The way of serialization is changed; # All sighash types commit to the amount being spent by the signed input; # FindAndDelete of the signature is not applied to the scriptCode; # OP_CODESEPARATOR(s) after the last executed OP_CODESEPARATOR are not removed from the scriptCode (the last executed OP_CODESEPARATOR and any script before it are always removed); # SINGLE does not commit to the input index. When ANYONECANPAY is not set, the semantics are unchanged since hashPrevouts and outpoint together implicitly commit to the input index. When SINGLE is used with ANYONECANPAY, omission of the index commitment allows permutation of the input-output pairs, as long as each pair is located at an equivalent index. The items 1, 4, 7, 9, 10 have the same meaning as the original algorithm. The item 5: *For P2WPKH witness program, the scriptCode is 0x1976a914{20-byte-pubkey-hash}88ac. *For P2WSH witness program, **if the witnessScript does not contain any OP_CODESEPARATOR, the scriptCode is the witnessScript serialized as scripts inside CTxOut. **if the witnessScript contains any OP_CODESEPARATOR, the scriptCode is the witnessScript but removing everything up to and including the last executed OP_CODESEPARATOR before the signature checking opcode being executed, serialized as scripts inside CTxOut. (The exact semantics is demonstrated in the examples below) The item 6 is a 8-byte value of the amount of bitcoin spent in this input. hashPrevouts: *If the ANYONECANPAY flag is not set, hashPrevouts is the double SHA256 of the serialization of all input outpoints; *Otherwise, hashPrevouts is a uint256 of 0x0000......0000. hashSequence: *If none of the ANYONECANPAY, SINGLE, NONE sighash type is set, hashSequence is the double SHA256 of the serialization of nSequence of all inputs; *Otherwise, hashSequence is a uint256 of 0x0000......0000. hashOutputs: *If the sighash type is neither SINGLE nor NONE, hashOutputs is the double SHA256 of the serialization of all output amount (8-byte little endian) with scriptPubKey (serialized as scripts inside CTxOuts); *If sighash type is SINGLE and the input index is smaller than the number of outputs, hashOutputs is the double SHA256 of the output amount with scriptPubKey of the same index as the input; *Otherwise, hashOutputs is a uint256 of 0x0000......0000.In the original algorithm, a uint256 of 0x0000......0001 is committed if the input index for a SINGLE signature is greater than or equal to the number of outputs. In this BIP a 0x0000......0000 is committed, without changing the semantics. The hashPrevouts, hashSequence, and hashOutputs calculated in an earlier verification may be reused in other inputs of the same transaction, so that the time complexity of the whole hashing process reduces from O(n2) to O(n). Refer to the reference implementation, reproduced below, for the precise algorithm: uint256 hashPrevouts; uint256 hashSequence; uint256 hashOutputs; if (!(nHashType & SIGHASH_ANYONECANPAY)) { CHashWriter ss(SER_GETHASH, 0); for (unsigned int n = 0; n < txTo.vin.size(); n++) { ss << txTo.vin[n].prevout; } hashPrevouts = ss.GetHash(); } if (!(nHashType & SIGHASH_ANYONECANPAY) && (nHashType & 0x1f) != SIGHASH_SINGLE && (nHashType & 0x1f) != SIGHASH_NONE) { CHashWriter ss(SER_GETHASH, 0); for (unsigned int n = 0; n < txTo.vin.size(); n++) { ss << txTo.vin[n].nSequence; } hashSequence = ss.GetHash(); } if ((nHashType & 0x1f) != SIGHASH_SINGLE && (nHashType & 0x1f) != SIGHASH_NONE) { CHashWriter ss(SER_GETHASH, 0); for (unsigned int n = 0; n < txTo.vout.size(); n++) { ss << txTo.vout[n]; } hashOutputs = ss.GetHash(); } else if ((nHashType & 0x1f) == SIGHASH_SINGLE && nIn < txTo.vout.size()) { CHashWriter ss(SER_GETHASH, 0); ss << txTo.vout[nIn]; hashOutputs = ss.GetHash(); } CHashWriter ss(SER_GETHASH, 0); // Version ss << txTo.nVersion; // Input prevouts/nSequence (none/all, depending on flags) ss << hashPrevouts; ss << hashSequence; // The input being signed (replacing the scriptSig with scriptCode + amount) // The prevout may already be contained in hashPrevout, and the nSequence // may already be contained in hashSequence. ss << txTo.vin[nIn].prevout; ss << static_cast(scriptCode); ss << amount; ss << txTo.vin[nIn].nSequence; // Outputs (none/one/all, depending on flags) ss << hashOutputs; // Locktime ss << txTo.nLockTime; // Sighash type ss << nHashType; return ss.GetHash(); == Restrictions on public key type == As a default policy, only compressed public keys are accepted in P2WPKH and P2WSH. Each public key passed to a sigop inside version 0 witness program must be a compressed key: the first byte MUST be either 0x02 or 0x03, and the size MUST be 33 bytes. Transactions that break this rule will not be relayed or mined by default. Since this policy is preparation for a future softfork proposal, to avoid potential future funds loss, users MUST NOT use uncompressed keys in version 0 witness programs. == Example == To ensure consistency in consensus-critical behaviour, developers should test their implementations against all the tests below. More tests related to this proposal could be found under https://github.com/bitcoin/bitcoin/tree/master/src/test/data . === Native P2WPKH === The following is an unsigned transaction: 0100000002fff7f7881a8099afa6940d42d1e7f6362bec38171ea3edf433541db4e4ad969f0000000000eeffffffef51e1b804cc89d182d279655c3aa89e815b1b309fe287d9b2b55d57b90ec68a0100000000ffffffff02202cb206000000001976a9148280b37df378db99f66f85c95a783a76ac7a6d5988ac9093510d000000001976a9143bde42dbee7e4dbe6a21b2d50ce2f0167faa815988ac11000000 nVersion: 01000000 txin: 02 fff7f7881a8099afa6940d42d1e7f6362bec38171ea3edf433541db4e4ad969f 00000000 00 eeffffff ef51e1b804cc89d182d279655c3aa89e815b1b309fe287d9b2b55d57b90ec68a 01000000 00 ffffffff txout: 02 202cb20600000000 1976a9148280b37df378db99f66f85c95a783a76ac7a6d5988ac 9093510d00000000 1976a9143bde42dbee7e4dbe6a21b2d50ce2f0167faa815988ac nLockTime: 11000000 The first input comes from an ordinary P2PK: scriptPubKey : 2103c9f4836b9a4f77fc0d81f7bcb01b7f1b35916864b9476c241ce9fc198bd25432ac value: 6.25 private key : bbc27228ddcb9209d7fd6f36b02f7dfa6252af40bb2f1cbc7a557da8027ff866 The second input comes from a P2WPKH witness program: scriptPubKey : 00141d0f172a0ecb48aee1be1f2687d2963ae33f71a1, value: 6 private key : 619c335025c7f4012e556c2a58b2506e30b8511b53ade95ea316fd8c3286feb9 public key : 025476c2e83188368da1ff3e292e7acafcdb3566bb0ad253f62fc70f07aeee6357 To sign it with a nHashType of 1 (SIGHASH_ALL): hashPrevouts: dSHA256(fff7f7881a8099afa6940d42d1e7f6362bec38171ea3edf433541db4e4ad969f00000000ef51e1b804cc89d182d279655c3aa89e815b1b309fe287d9b2b55d57b90ec68a01000000) = 96b827c8483d4e9b96712b6713a7b68d6e8003a781feba36c31143470b4efd37 hashSequence: dSHA256(eeffffffffffffff) = 52b0a642eea2fb7ae638c36f6252b6750293dbe574a806984b8e4d8548339a3b hashOutputs: dSHA256(202cb206000000001976a9148280b37df378db99f66f85c95a783a76ac7a6d5988ac9093510d000000001976a9143bde42dbee7e4dbe6a21b2d50ce2f0167faa815988ac) = 863ef3e1a92afbfdb97f31ad0fc7683ee943e9abcf2501590ff8f6551f47e5e5 hash preimage: 0100000096b827c8483d4e9b96712b6713a7b68d6e8003a781feba36c31143470b4efd3752b0a642eea2fb7ae638c36f6252b6750293dbe574a806984b8e4d8548339a3bef51e1b804cc89d182d279655c3aa89e815b1b309fe287d9b2b55d57b90ec68a010000001976a9141d0f172a0ecb48aee1be1f2687d2963ae33f71a188ac0046c32300000000ffffffff863ef3e1a92afbfdb97f31ad0fc7683ee943e9abcf2501590ff8f6551f47e5e51100000001000000 nVersion: 01000000 hashPrevouts: 96b827c8483d4e9b96712b6713a7b68d6e8003a781feba36c31143470b4efd37 hashSequence: 52b0a642eea2fb7ae638c36f6252b6750293dbe574a806984b8e4d8548339a3b outpoint: ef51e1b804cc89d182d279655c3aa89e815b1b309fe287d9b2b55d57b90ec68a01000000 scriptCode: 1976a9141d0f172a0ecb48aee1be1f2687d2963ae33f71a188ac amount: 0046c32300000000 nSequence: ffffffff hashOutputs: 863ef3e1a92afbfdb97f31ad0fc7683ee943e9abcf2501590ff8f6551f47e5e5 nLockTime: 11000000 nHashType: 01000000 sigHash: c37af31116d1b27caf68aae9e3ac82f1477929014d5b917657d0eb49478cb670 signature: 304402203609e17b84f6a7d30c80bfa610b5b4542f32a8a0d5447a12fb1366d7f01cc44a0220573a954c4518331561406f90300e8f3358f51928d43c212a8caed02de67eebee01 The serialized signed transaction is: 01000000000102fff7f7881a8099afa6940d42d1e7f6362bec38171ea3edf433541db4e4ad969f00000000494830450221008b9d1dc26ba6a9cb62127b02742fa9d754cd3bebf337f7a55d114c8e5cdd30be022040529b194ba3f9281a99f2b1c0a19c0489bc22ede944ccf4ecbab4cc618ef3ed01eeffffffef51e1b804cc89d182d279655c3aa89e815b1b309fe287d9b2b55d57b90ec68a0100000000ffffffff02202cb206000000001976a9148280b37df378db99f66f85c95a783a76ac7a6d5988ac9093510d000000001976a9143bde42dbee7e4dbe6a21b2d50ce2f0167faa815988ac000247304402203609e17b84f6a7d30c80bfa610b5b4542f32a8a0d5447a12fb1366d7f01cc44a0220573a954c4518331561406f90300e8f3358f51928d43c212a8caed02de67eebee0121025476c2e83188368da1ff3e292e7acafcdb3566bb0ad253f62fc70f07aeee635711000000 nVersion: 01000000 marker: 00 flag: 01 txin: 02 fff7f7881a8099afa6940d42d1e7f6362bec38171ea3edf433541db4e4ad969f 00000000 494830450221008b9d1dc26ba6a9cb62127b02742fa9d754cd3bebf337f7a55d114c8e5cdd30be022040529b194ba3f9281a99f2b1c0a19c0489bc22ede944ccf4ecbab4cc618ef3ed01 eeffffff ef51e1b804cc89d182d279655c3aa89e815b1b309fe287d9b2b55d57b90ec68a 01000000 00 ffffffff txout: 02 202cb20600000000 1976a9148280b37df378db99f66f85c95a783a76ac7a6d5988ac 9093510d00000000 1976a9143bde42dbee7e4dbe6a21b2d50ce2f0167faa815988ac witness 00 02 47304402203609e17b84f6a7d30c80bfa610b5b4542f32a8a0d5447a12fb1366d7f01cc44a0220573a954c4518331561406f90300e8f3358f51928d43c212a8caed02de67eebee01 21025476c2e83188368da1ff3e292e7acafcdb3566bb0ad253f62fc70f07aeee6357 nLockTime: 11000000 === P2SH-P2WPKH === The following is an unsigned transaction: 0100000001db6b1b20aa0fd7b23880be2ecbd4a98130974cf4748fb66092ac4d3ceb1a54770100000000feffffff02b8b4eb0b000000001976a914a457b684d7f0d539a46a45bbc043f35b59d0d96388ac0008af2f000000001976a914fd270b1ee6abcaea97fea7ad0402e8bd8ad6d77c88ac92040000 nVersion: 01000000 txin: 01 db6b1b20aa0fd7b23880be2ecbd4a98130974cf4748fb66092ac4d3ceb1a5477 01000000 00 feffffff txout: 02 b8b4eb0b00000000 1976a914a457b684d7f0d539a46a45bbc043f35b59d0d96388ac 0008af2f00000000 1976a914fd270b1ee6abcaea97fea7ad0402e8bd8ad6d77c88ac nLockTime: 92040000 The input comes from a P2SH-P2WPKH witness program: scriptPubKey : a9144733f37cf4db86fbc2efed2500b4f4e49f31202387, value: 10 redeemScript : 001479091972186c449eb1ded22b78e40d009bdf0089 private key : eb696a065ef48a2192da5b28b694f87544b30fae8327c4510137a922f32c6dcf public key : 03ad1d8e89212f0b92c74d23bb710c00662ad1470198ac48c43f7d6f93a2a26873 To sign it with a nHashType of 1 (SIGHASH_ALL): hashPrevouts: dSHA256(db6b1b20aa0fd7b23880be2ecbd4a98130974cf4748fb66092ac4d3ceb1a547701000000) = b0287b4a252ac05af83d2dcef00ba313af78a3e9c329afa216eb3aa2a7b4613a hashSequence: dSHA256(feffffff) = 18606b350cd8bf565266bc352f0caddcf01e8fa789dd8a15386327cf8cabe198 hashOutputs: dSHA256(b8b4eb0b000000001976a914a457b684d7f0d539a46a45bbc043f35b59d0d96388ac0008af2f000000001976a914fd270b1ee6abcaea97fea7ad0402e8bd8ad6d77c88ac) = de984f44532e2173ca0d64314fcefe6d30da6f8cf27bafa706da61df8a226c83 hash preimage: 01000000b0287b4a252ac05af83d2dcef00ba313af78a3e9c329afa216eb3aa2a7b4613a18606b350cd8bf565266bc352f0caddcf01e8fa789dd8a15386327cf8cabe198db6b1b20aa0fd7b23880be2ecbd4a98130974cf4748fb66092ac4d3ceb1a5477010000001976a91479091972186c449eb1ded22b78e40d009bdf008988ac00ca9a3b00000000feffffffde984f44532e2173ca0d64314fcefe6d30da6f8cf27bafa706da61df8a226c839204000001000000 nVersion: 01000000 hashPrevouts: b0287b4a252ac05af83d2dcef00ba313af78a3e9c329afa216eb3aa2a7b4613a hashSequence: 18606b350cd8bf565266bc352f0caddcf01e8fa789dd8a15386327cf8cabe198 outpoint: db6b1b20aa0fd7b23880be2ecbd4a98130974cf4748fb66092ac4d3ceb1a547701000000 scriptCode: 1976a91479091972186c449eb1ded22b78e40d009bdf008988ac amount: 00ca9a3b00000000 nSequence: feffffff hashOutputs: de984f44532e2173ca0d64314fcefe6d30da6f8cf27bafa706da61df8a226c83 nLockTime: 92040000 nHashType: 01000000 sigHash: 64f3b0f4dd2bb3aa1ce8566d220cc74dda9df97d8490cc81d89d735c92e59fb6 signature: 3044022047ac8e878352d3ebbde1c94ce3a10d057c24175747116f8288e5d794d12d482f0220217f36a485cae903c713331d877c1f64677e3622ad4010726870540656fe9dcb01 The serialized signed transaction is: 01000000000101db6b1b20aa0fd7b23880be2ecbd4a98130974cf4748fb66092ac4d3ceb1a5477010000001716001479091972186c449eb1ded22b78e40d009bdf0089feffffff02b8b4eb0b000000001976a914a457b684d7f0d539a46a45bbc043f35b59d0d96388ac0008af2f000000001976a914fd270b1ee6abcaea97fea7ad0402e8bd8ad6d77c88ac02473044022047ac8e878352d3ebbde1c94ce3a10d057c24175747116f8288e5d794d12d482f0220217f36a485cae903c713331d877c1f64677e3622ad4010726870540656fe9dcb012103ad1d8e89212f0b92c74d23bb710c00662ad1470198ac48c43f7d6f93a2a2687392040000 nVersion: 01000000 marker: 00 flag: 01 txin: 01 db6b1b20aa0fd7b23880be2ecbd4a98130974cf4748fb66092ac4d3ceb1a5477 01000000 1716001479091972186c449eb1ded22b78e40d009bdf0089 feffffff txout: 02 b8b4eb0b00000000 1976a914a457b684d7f0d539a46a45bbc043f35b59d0d96388ac 0008af2f00000000 1976a914fd270b1ee6abcaea97fea7ad0402e8bd8ad6d77c88ac witness 02 473044022047ac8e878352d3ebbde1c94ce3a10d057c24175747116f8288e5d794d12d482f0220217f36a485cae903c713331d877c1f64677e3622ad4010726870540656fe9dcb01 2103ad1d8e89212f0b92c74d23bb710c00662ad1470198ac48c43f7d6f93a2a26873 nLockTime: 92040000 === Native P2WSH === This example shows how OP_CODESEPARATOR and out-of-range SIGHASH_SINGLE are processed: The following is an unsigned transaction: 0100000002fe3dc9208094f3ffd12645477b3dc56f60ec4fa8e6f5d67c565d1c6b9216b36e0000000000ffffffff0815cf020f013ed6cf91d29f4202e8a58726b1ac6c79da47c23d1bee0a6925f80000000000ffffffff0100f2052a010000001976a914a30741f8145e5acadf23f751864167f32e0963f788ac00000000 nVersion: 01000000 txin: 02 fe3dc9208094f3ffd12645477b3dc56f60ec4fa8e6f5d67c565d1c6b9216b36e 00000000 00 ffffffff 0815cf020f013ed6cf91d29f4202e8a58726b1ac6c79da47c23d1bee0a6925f8 00000000 00 ffffffff txout: 01 00f2052a01000000 1976a914a30741f8145e5acadf23f751864167f32e0963f788ac nLockTime: 00000000 The first input comes from an ordinary P2PK: scriptPubKey: 21036d5c20fa14fb2f635474c1dc4ef5909d4568e5569b79fc94d3448486e14685f8ac value: 1.5625 private key: b8f28a772fccbf9b4f58a4f027e07dc2e35e7cd80529975e292ea34f84c4580c signature: 304402200af4e47c9b9629dbecc21f73af989bdaa911f7e6f6c2e9394588a3aa68f81e9902204f3fcf6ade7e5abb1295b6774c8e0abd94ae62217367096bc02ee5e435b67da201 (SIGHASH_ALL) The second input comes from a native P2WSH witness program: scriptPubKey : 00205d1b56b63d714eebe542309525f484b7e9d6f686b3781b6f61ef925d66d6f6a0, value: 49 witnessScript: 21026dccc749adc2a9d0d89497ac511f760f45c47dc5ed9cf352a58ac706453880aeadab210255a9626aebf5e29c0e6538428ba0d1dcf6ca98ffdf086aa8ced5e0d0215ea465ac <026dccc749adc2a9d0d89497ac511f760f45c47dc5ed9cf352a58ac706453880ae> CHECKSIGVERIFY CODESEPARATOR <0255a9626aebf5e29c0e6538428ba0d1dcf6ca98ffdf086aa8ced5e0d0215ea465> CHECKSIG To sign it with a nHashType of 3 (SIGHASH_SINGLE): hashPrevouts: dSHA256(fe3dc9208094f3ffd12645477b3dc56f60ec4fa8e6f5d67c565d1c6b9216b36e000000000815cf020f013ed6cf91d29f4202e8a58726b1ac6c79da47c23d1bee0a6925f800000000) = ef546acf4a020de3898d1b8956176bb507e6211b5ed3619cd08b6ea7e2a09d41 nVersion: 01000000 hashPrevouts: ef546acf4a020de3898d1b8956176bb507e6211b5ed3619cd08b6ea7e2a09d41 hashSequence: 0000000000000000000000000000000000000000000000000000000000000000 outpoint: 0815cf020f013ed6cf91d29f4202e8a58726b1ac6c79da47c23d1bee0a6925f800000000 scriptCode: (see below) amount: 0011102401000000 nSequence: ffffffff hashOutputs: 0000000000000000000000000000000000000000000000000000000000000000 (this is the second input but there is only one output) nLockTime: 00000000 nHashType: 03000000 scriptCode: 4721026dccc749adc2a9d0d89497ac511f760f45c47dc5ed9cf352a58ac706453880aeadab210255a9626aebf5e29c0e6538428ba0d1dcf6ca98ffdf086aa8ced5e0d0215ea465ac ^^ (please note that the not-yet-executed OP_CODESEPARATOR is not removed from the scriptCode) preimage: 01000000ef546acf4a020de3898d1b8956176bb507e6211b5ed3619cd08b6ea7e2a09d4100000000000000000000000000000000000000000000000000000000000000000815cf020f013ed6cf91d29f4202e8a58726b1ac6c79da47c23d1bee0a6925f8000000004721026dccc749adc2a9d0d89497ac511f760f45c47dc5ed9cf352a58ac706453880aeadab210255a9626aebf5e29c0e6538428ba0d1dcf6ca98ffdf086aa8ced5e0d0215ea465ac0011102401000000ffffffff00000000000000000000000000000000000000000000000000000000000000000000000003000000 sigHash: 82dde6e4f1e94d02c2b7ad03d2115d691f48d064e9d52f58194a6637e4194391 public key: 026dccc749adc2a9d0d89497ac511f760f45c47dc5ed9cf352a58ac706453880ae private key: 8e02b539b1500aa7c81cf3fed177448a546f19d2be416c0c61ff28e577d8d0cd signature: 3044022027dc95ad6b740fe5129e7e62a75dd00f291a2aeb1200b84b09d9e3789406b6c002201a9ecd315dd6a0e632ab20bbb98948bc0c6fb204f2c286963bb48517a7058e2703 scriptCode: 23210255a9626aebf5e29c0e6538428ba0d1dcf6ca98ffdf086aa8ced5e0d0215ea465ac (everything up to the last executed OP_CODESEPARATOR, including that OP_CODESEPARATOR, are removed) preimage: 01000000ef546acf4a020de3898d1b8956176bb507e6211b5ed3619cd08b6ea7e2a09d4100000000000000000000000000000000000000000000000000000000000000000815cf020f013ed6cf91d29f4202e8a58726b1ac6c79da47c23d1bee0a6925f80000000023210255a9626aebf5e29c0e6538428ba0d1dcf6ca98ffdf086aa8ced5e0d0215ea465ac0011102401000000ffffffff00000000000000000000000000000000000000000000000000000000000000000000000003000000 sigHash: fef7bd749cce710c5c052bd796df1af0d935e59cea63736268bcbe2d2134fc47 public key: 0255a9626aebf5e29c0e6538428ba0d1dcf6ca98ffdf086aa8ced5e0d0215ea465 private key: 86bf2ed75935a0cbef03b89d72034bb4c189d381037a5ac121a70016db8896ec signature: 304402200de66acf4527789bfda55fc5459e214fa6083f936b430a762c629656216805ac0220396f550692cd347171cbc1ef1f51e15282e837bb2b30860dc77c8f78bc8501e503 The serialized signed transaction is: 01000000000102fe3dc9208094f3ffd12645477b3dc56f60ec4fa8e6f5d67c565d1c6b9216b36e000000004847304402200af4e47c9b9629dbecc21f73af989bdaa911f7e6f6c2e9394588a3aa68f81e9902204f3fcf6ade7e5abb1295b6774c8e0abd94ae62217367096bc02ee5e435b67da201ffffffff0815cf020f013ed6cf91d29f4202e8a58726b1ac6c79da47c23d1bee0a6925f80000000000ffffffff0100f2052a010000001976a914a30741f8145e5acadf23f751864167f32e0963f788ac000347304402200de66acf4527789bfda55fc5459e214fa6083f936b430a762c629656216805ac0220396f550692cd347171cbc1ef1f51e15282e837bb2b30860dc77c8f78bc8501e503473044022027dc95ad6b740fe5129e7e62a75dd00f291a2aeb1200b84b09d9e3789406b6c002201a9ecd315dd6a0e632ab20bbb98948bc0c6fb204f2c286963bb48517a7058e27034721026dccc749adc2a9d0d89497ac511f760f45c47dc5ed9cf352a58ac706453880aeadab210255a9626aebf5e29c0e6538428ba0d1dcf6ca98ffdf086aa8ced5e0d0215ea465ac00000000 This example shows how unexecuted OP_CODESEPARATOR is processed, and SINGLE|ANYONECANPAY does not commit to the input index: The following is an unsigned transaction: 0100000002e9b542c5176808107ff1df906f46bb1f2583b16112b95ee5380665ba7fcfc0010000000000ffffffff80e68831516392fcd100d186b3c2c7b95c80b53c77e77c35ba03a66b429a2a1b0000000000ffffffff0280969800000000001976a914de4b231626ef508c9a74a8517e6783c0546d6b2888ac80969800000000001976a9146648a8cd4531e1ec47f35916de8e259237294d1e88ac00000000 nVersion: 01000000 txin: 02 e9b542c5176808107ff1df906f46bb1f2583b16112b95ee5380665ba7fcfc001 00000000 00 ffffffff 80e68831516392fcd100d186b3c2c7b95c80b53c77e77c35ba03a66b429a2a1b 00000000 00 ffffffff txout: 02 8096980000000000 1976a914de4b231626ef508c9a74a8517e6783c0546d6b2888ac 8096980000000000 1976a9146648a8cd4531e1ec47f35916de8e259237294d1e88ac nLockTime: 00000000 The first input comes from a native P2WSH witness program: scriptPubKey: 0020ba468eea561b26301e4cf69fa34bde4ad60c81e70f059f045ca9a79931004a4d value: 0.16777215 witnessScript:0063ab68210392972e2eb617b2388771abe27235fd5ac44af8e61693261550447a4c3e39da98ac 0 IF CODESEPARATOR ENDIF <0392972e2eb617b2388771abe27235fd5ac44af8e61693261550447a4c3e39da98> CHECKSIG The second input comes from a native P2WSH witness program: scriptPubKey: 0020d9bbfbe56af7c4b7f960a70d7ea107156913d9e5a26b0a71429df5e097ca6537 value: 0.16777215 witnessScript:5163ab68210392972e2eb617b2388771abe27235fd5ac44af8e61693261550447a4c3e39da98ac 1 IF CODESEPARATOR ENDIF <0392972e2eb617b2388771abe27235fd5ac44af8e61693261550447a4c3e39da98> CHECKSIG To sign it with a nHashType of 0x83 (SINGLE|ANYONECANPAY): nVersion: 01000000 hashPrevouts: 0000000000000000000000000000000000000000000000000000000000000000 hashSequence: 0000000000000000000000000000000000000000000000000000000000000000 outpoint: (see below) scriptCode: (see below) amount: ffffff0000000000 nSequence: ffffffff hashOutputs: (see below) nLockTime: 00000000 nHashType: 83000000 outpoint: e9b542c5176808107ff1df906f46bb1f2583b16112b95ee5380665ba7fcfc00100000000 scriptCode: 270063ab68210392972e2eb617b2388771abe27235fd5ac44af8e61693261550447a4c3e39da98ac (since the OP_CODESEPARATOR is not executed, nothing is removed from the scriptCode) hashOutputs: b258eaf08c39fbe9fbac97c15c7e7adeb8df142b0df6f83e017f349c2b6fe3d2 preimage: 0100000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000e9b542c5176808107ff1df906f46bb1f2583b16112b95ee5380665ba7fcfc00100000000270063ab68210392972e2eb617b2388771abe27235fd5ac44af8e61693261550447a4c3e39da98acffffff0000000000ffffffffb258eaf08c39fbe9fbac97c15c7e7adeb8df142b0df6f83e017f349c2b6fe3d20000000083000000 sigHash: e9071e75e25b8a1e298a72f0d2e9f4f95a0f5cdf86a533cda597eb402ed13b3a public key: 0392972e2eb617b2388771abe27235fd5ac44af8e61693261550447a4c3e39da98 private key: f52b3484edd96598e02a9c89c4492e9c1e2031f471c49fd721fe68b3ce37780d signature: 3045022100f6a10b8604e6dc910194b79ccfc93e1bc0ec7c03453caaa8987f7d6c3413566002206216229ede9b4d6ec2d325be245c5b508ff0339bf1794078e20bfe0babc7ffe683 outpoint: 80e68831516392fcd100d186b3c2c7b95c80b53c77e77c35ba03a66b429a2a1b00000000 scriptCode: 2468210392972e2eb617b2388771abe27235fd5ac44af8e61693261550447a4c3e39da98ac (everything up to the last executed OP_CODESEPARATOR, including that OP_CODESEPARATOR, are removed) hashOutputs: 91ea93dd77f702b738ebdbf3048940a98310e869a7bb8fa2c6cb3312916947ca preimage: 010000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000080e68831516392fcd100d186b3c2c7b95c80b53c77e77c35ba03a66b429a2a1b000000002468210392972e2eb617b2388771abe27235fd5ac44af8e61693261550447a4c3e39da98acffffff0000000000ffffffff91ea93dd77f702b738ebdbf3048940a98310e869a7bb8fa2c6cb3312916947ca0000000083000000 sigHash: cd72f1f1a433ee9df816857fad88d8ebd97e09a75cd481583eb841c330275e54 public key: 0392972e2eb617b2388771abe27235fd5ac44af8e61693261550447a4c3e39da98 private key: f52b3484edd96598e02a9c89c4492e9c1e2031f471c49fd721fe68b3ce37780d signature: 30440220032521802a76ad7bf74d0e2c218b72cf0cbc867066e2e53db905ba37f130397e02207709e2188ed7f08f4c952d9d13986da504502b8c3be59617e043552f506c46ff83 The serialized signed transaction is: 01000000000102e9b542c5176808107ff1df906f46bb1f2583b16112b95ee5380665ba7fcfc0010000000000ffffffff80e68831516392fcd100d186b3c2c7b95c80b53c77e77c35ba03a66b429a2a1b0000000000ffffffff0280969800000000001976a914de4b231626ef508c9a74a8517e6783c0546d6b2888ac80969800000000001976a9146648a8cd4531e1ec47f35916de8e259237294d1e88ac02483045022100f6a10b8604e6dc910194b79ccfc93e1bc0ec7c03453caaa8987f7d6c3413566002206216229ede9b4d6ec2d325be245c5b508ff0339bf1794078e20bfe0babc7ffe683270063ab68210392972e2eb617b2388771abe27235fd5ac44af8e61693261550447a4c3e39da98ac024730440220032521802a76ad7bf74d0e2c218b72cf0cbc867066e2e53db905ba37f130397e02207709e2188ed7f08f4c952d9d13986da504502b8c3be59617e043552f506c46ff83275163ab68210392972e2eb617b2388771abe27235fd5ac44af8e61693261550447a4c3e39da98ac00000000 nVersion: 01000000 marker: 00 flag: 01 txin: 02 e9b542c5176808107ff1df906f46bb1f2583b16112b95ee5380665ba7fcfc001 00000000 00 ffffffff 80e68831516392fcd100d186b3c2c7b95c80b53c77e77c35ba03a66b429a2a1b 00000000 00 ffffffff txout: 02 8096980000000000 1976a914de4b231626ef508c9a74a8517e6783c0546d6b2888ac 8096980000000000 1976a9146648a8cd4531e1ec47f35916de8e259237294d1e88ac witness 02 483045022100f6a10b8604e6dc910194b79ccfc93e1bc0ec7c03453caaa8987f7d6c3413566002206216229ede9b4d6ec2d325be245c5b508ff0339bf1794078e20bfe0babc7ffe683 270063ab68210392972e2eb617b2388771abe27235fd5ac44af8e61693261550447a4c3e39da98ac 02 4730440220032521802a76ad7bf74d0e2c218b72cf0cbc867066e2e53db905ba37f130397e02207709e2188ed7f08f4c952d9d13986da504502b8c3be59617e043552f506c46ff83 275163ab68210392972e2eb617b2388771abe27235fd5ac44af8e61693261550447a4c3e39da98ac nLockTime: 00000000 Since SINGLE|ANYONECANPAY does not commit to the input index, the signatures are still valid when the input-output pairs are swapped: 0100000000010280e68831516392fcd100d186b3c2c7b95c80b53c77e77c35ba03a66b429a2a1b0000000000ffffffffe9b542c5176808107ff1df906f46bb1f2583b16112b95ee5380665ba7fcfc0010000000000ffffffff0280969800000000001976a9146648a8cd4531e1ec47f35916de8e259237294d1e88ac80969800000000001976a914de4b231626ef508c9a74a8517e6783c0546d6b2888ac024730440220032521802a76ad7bf74d0e2c218b72cf0cbc867066e2e53db905ba37f130397e02207709e2188ed7f08f4c952d9d13986da504502b8c3be59617e043552f506c46ff83275163ab68210392972e2eb617b2388771abe27235fd5ac44af8e61693261550447a4c3e39da98ac02483045022100f6a10b8604e6dc910194b79ccfc93e1bc0ec7c03453caaa8987f7d6c3413566002206216229ede9b4d6ec2d325be245c5b508ff0339bf1794078e20bfe0babc7ffe683270063ab68210392972e2eb617b2388771abe27235fd5ac44af8e61693261550447a4c3e39da98ac00000000 nVersion: 01000000 marker: 00 flag: 01 txin: 02 80e68831516392fcd100d186b3c2c7b95c80b53c77e77c35ba03a66b429a2a1b 00000000 00 ffffffff e9b542c5176808107ff1df906f46bb1f2583b16112b95ee5380665ba7fcfc001 00000000 00 ffffffff txout: 02 8096980000000000 1976a9146648a8cd4531e1ec47f35916de8e259237294d1e88ac 8096980000000000 1976a914de4b231626ef508c9a74a8517e6783c0546d6b2888ac witness 02 4730440220032521802a76ad7bf74d0e2c218b72cf0cbc867066e2e53db905ba37f130397e02207709e2188ed7f08f4c952d9d13986da504502b8c3be59617e043552f506c46ff83 275163ab68210392972e2eb617b2388771abe27235fd5ac44af8e61693261550447a4c3e39da98ac 02 483045022100f6a10b8604e6dc910194b79ccfc93e1bc0ec7c03453caaa8987f7d6c3413566002206216229ede9b4d6ec2d325be245c5b508ff0339bf1794078e20bfe0babc7ffe683 270063ab68210392972e2eb617b2388771abe27235fd5ac44af8e61693261550447a4c3e39da98ac nLockTime: 00000000 === P2SH-P2WSH === This example is a P2SH-P2WSH 6-of-6 multisig witness program signed with 6 different SIGHASH types. The following is an unsigned transaction: 010000000136641869ca081e70f394c6948e8af409e18b619df2ed74aa106c1ca29787b96e0100000000ffffffff0200e9a435000000001976a914389ffce9cd9ae88dcc0631e88a821ffdbe9bfe2688acc0832f05000000001976a9147480a33f950689af511e6e84c138dbbd3c3ee41588ac00000000 nVersion: 01000000 txin: 01 36641869ca081e70f394c6948e8af409e18b619df2ed74aa106c1ca29787b96e 01000000 00 ffffffff txout: 02 00e9a43500000000 1976a914389ffce9cd9ae88dcc0631e88a821ffdbe9bfe2688ac c0832f0500000000 1976a9147480a33f950689af511e6e84c138dbbd3c3ee41588ac nLockTime: 00000000 The input comes from a P2SH-P2WSH 6-of-6 multisig witness program: scriptPubKey : a9149993a429037b5d912407a71c252019287b8d27a587, value: 9.87654321 redeemScript : 0020a16b5755f7f6f96dbd65f5f0d6ab9418b89af4b1f14a1bb8a09062c35f0dcb54 witnessScript: 56210307b8ae49ac90a048e9b53357a2354b3334e9c8bee813ecb98e99a7e07e8c3ba32103b28f0c28bfab54554ae8c658ac5c3e0ce6e79ad336331f78c428dd43eea8449b21034b8113d703413d57761b8b9781957b8c0ac1dfe69f492580ca4195f50376ba4a21033400f6afecb833092a9a21cfdf1ed1376e58c5d1f47de74683123987e967a8f42103a6d48b1131e94ba04d9737d61acdaa1322008af9602b3b14862c07a1789aac162102d8b661b0b3302ee2f162b09e07a55ad5dfbe673a9f01d9f0c19617681024306b56ae hashPrevouts: dSHA256(36641869ca081e70f394c6948e8af409e18b619df2ed74aa106c1ca29787b96e01000000) = 74afdc312af5183c4198a40ca3c1a275b485496dd3929bca388c4b5e31f7aaa0 hashSequence: dSHA256(ffffffff) = 3bb13029ce7b1f559ef5e747fcac439f1455a2ec7c5f09b72290795e70665044 hashOutputs for ALL: dSHA256(00e9a435000000001976a914389ffce9cd9ae88dcc0631e88a821ffdbe9bfe2688acc0832f05000000001976a9147480a33f950689af511e6e84c138dbbd3c3ee41588ac) = bc4d309071414bed932f98832b27b4d76dad7e6c1346f487a8fdbb8eb90307cc hashOutputs for SINGLE: dSHA256(00e9a435000000001976a914389ffce9cd9ae88dcc0631e88a821ffdbe9bfe2688ac) = 9efe0c13a6b16c14a41b04ebe6a63f419bdacb2f8705b494a43063ca3cd4f708 hash preimage for ALL: 0100000074afdc312af5183c4198a40ca3c1a275b485496dd3929bca388c4b5e31f7aaa03bb13029ce7b1f559ef5e747fcac439f1455a2ec7c5f09b72290795e7066504436641869ca081e70f394c6948e8af409e18b619df2ed74aa106c1ca29787b96e01000000cf56210307b8ae49ac90a048e9b53357a2354b3334e9c8bee813ecb98e99a7e07e8c3ba32103b28f0c28bfab54554ae8c658ac5c3e0ce6e79ad336331f78c428dd43eea8449b21034b8113d703413d57761b8b9781957b8c0ac1dfe69f492580ca4195f50376ba4a21033400f6afecb833092a9a21cfdf1ed1376e58c5d1f47de74683123987e967a8f42103a6d48b1131e94ba04d9737d61acdaa1322008af9602b3b14862c07a1789aac162102d8b661b0b3302ee2f162b09e07a55ad5dfbe673a9f01d9f0c19617681024306b56aeb168de3a00000000ffffffffbc4d309071414bed932f98832b27b4d76dad7e6c1346f487a8fdbb8eb90307cc0000000001000000 nVersion: 01000000 hashPrevouts: 74afdc312af5183c4198a40ca3c1a275b485496dd3929bca388c4b5e31f7aaa0 hashSequence: 3bb13029ce7b1f559ef5e747fcac439f1455a2ec7c5f09b72290795e70665044 outpoint: 36641869ca081e70f394c6948e8af409e18b619df2ed74aa106c1ca29787b96e01000000 scriptCode: cf56210307b8ae49ac90a048e9b53357a2354b3334e9c8bee813ecb98e99a7e07e8c3ba32103b28f0c28bfab54554ae8c658ac5c3e0ce6e79ad336331f78c428dd43eea8449b21034b8113d703413d57761b8b9781957b8c0ac1dfe69f492580ca4195f50376ba4a21033400f6afecb833092a9a21cfdf1ed1376e58c5d1f47de74683123987e967a8f42103a6d48b1131e94ba04d9737d61acdaa1322008af9602b3b14862c07a1789aac162102d8b661b0b3302ee2f162b09e07a55ad5dfbe673a9f01d9f0c19617681024306b56ae amount: b168de3a00000000 nSequence: ffffffff hashOutputs: bc4d309071414bed932f98832b27b4d76dad7e6c1346f487a8fdbb8eb90307cc nLockTime: 00000000 nHashType: 01000000 sigHash: 185c0be5263dce5b4bb50a047973c1b6272bfbd0103a89444597dc40b248ee7c public key: 0307b8ae49ac90a048e9b53357a2354b3334e9c8bee813ecb98e99a7e07e8c3ba3 private key: 730fff80e1413068a05b57d6a58261f07551163369787f349438ea38ca80fac6 signature: 304402206ac44d672dac41f9b00e28f4df20c52eeb087207e8d758d76d92c6fab3b73e2b0220367750dbbe19290069cba53d096f44530e4f98acaa594810388cf7409a1870ce01 hash preimage for NONE: 0100000074afdc312af5183c4198a40ca3c1a275b485496dd3929bca388c4b5e31f7aaa0000000000000000000000000000000000000000000000000000000000000000036641869ca081e70f394c6948e8af409e18b619df2ed74aa106c1ca29787b96e01000000cf56210307b8ae49ac90a048e9b53357a2354b3334e9c8bee813ecb98e99a7e07e8c3ba32103b28f0c28bfab54554ae8c658ac5c3e0ce6e79ad336331f78c428dd43eea8449b21034b8113d703413d57761b8b9781957b8c0ac1dfe69f492580ca4195f50376ba4a21033400f6afecb833092a9a21cfdf1ed1376e58c5d1f47de74683123987e967a8f42103a6d48b1131e94ba04d9737d61acdaa1322008af9602b3b14862c07a1789aac162102d8b661b0b3302ee2f162b09e07a55ad5dfbe673a9f01d9f0c19617681024306b56aeb168de3a00000000ffffffff00000000000000000000000000000000000000000000000000000000000000000000000002000000 nVersion: 01000000 hashPrevouts: 74afdc312af5183c4198a40ca3c1a275b485496dd3929bca388c4b5e31f7aaa0 hashSequence: 0000000000000000000000000000000000000000000000000000000000000000 outpoint: 36641869ca081e70f394c6948e8af409e18b619df2ed74aa106c1ca29787b96e01000000 scriptCode: cf56210307b8ae49ac90a048e9b53357a2354b3334e9c8bee813ecb98e99a7e07e8c3ba32103b28f0c28bfab54554ae8c658ac5c3e0ce6e79ad336331f78c428dd43eea8449b21034b8113d703413d57761b8b9781957b8c0ac1dfe69f492580ca4195f50376ba4a21033400f6afecb833092a9a21cfdf1ed1376e58c5d1f47de74683123987e967a8f42103a6d48b1131e94ba04d9737d61acdaa1322008af9602b3b14862c07a1789aac162102d8b661b0b3302ee2f162b09e07a55ad5dfbe673a9f01d9f0c19617681024306b56ae amount: b168de3a00000000 nSequence: ffffffff hashOutputs: 0000000000000000000000000000000000000000000000000000000000000000 nLockTime: 00000000 nHashType: 02000000 sigHash: e9733bc60ea13c95c6527066bb975a2ff29a925e80aa14c213f686cbae5d2f36 public key: 03b28f0c28bfab54554ae8c658ac5c3e0ce6e79ad336331f78c428dd43eea8449b private key: 11fa3d25a17cbc22b29c44a484ba552b5a53149d106d3d853e22fdd05a2d8bb3 signature: 3044022068c7946a43232757cbdf9176f009a928e1cd9a1a8c212f15c1e11ac9f2925d9002205b75f937ff2f9f3c1246e547e54f62e027f64eefa2695578cc6432cdabce271502 hash preimage for SINGLE: 0100000074afdc312af5183c4198a40ca3c1a275b485496dd3929bca388c4b5e31f7aaa0000000000000000000000000000000000000000000000000000000000000000036641869ca081e70f394c6948e8af409e18b619df2ed74aa106c1ca29787b96e01000000cf56210307b8ae49ac90a048e9b53357a2354b3334e9c8bee813ecb98e99a7e07e8c3ba32103b28f0c28bfab54554ae8c658ac5c3e0ce6e79ad336331f78c428dd43eea8449b21034b8113d703413d57761b8b9781957b8c0ac1dfe69f492580ca4195f50376ba4a21033400f6afecb833092a9a21cfdf1ed1376e58c5d1f47de74683123987e967a8f42103a6d48b1131e94ba04d9737d61acdaa1322008af9602b3b14862c07a1789aac162102d8b661b0b3302ee2f162b09e07a55ad5dfbe673a9f01d9f0c19617681024306b56aeb168de3a00000000ffffffff9efe0c13a6b16c14a41b04ebe6a63f419bdacb2f8705b494a43063ca3cd4f7080000000003000000 nVersion: 01000000 hashPrevouts: 74afdc312af5183c4198a40ca3c1a275b485496dd3929bca388c4b5e31f7aaa0 hashSequence: 0000000000000000000000000000000000000000000000000000000000000000 outpoint: 36641869ca081e70f394c6948e8af409e18b619df2ed74aa106c1ca29787b96e01000000 scriptCode: cf56210307b8ae49ac90a048e9b53357a2354b3334e9c8bee813ecb98e99a7e07e8c3ba32103b28f0c28bfab54554ae8c658ac5c3e0ce6e79ad336331f78c428dd43eea8449b21034b8113d703413d57761b8b9781957b8c0ac1dfe69f492580ca4195f50376ba4a21033400f6afecb833092a9a21cfdf1ed1376e58c5d1f47de74683123987e967a8f42103a6d48b1131e94ba04d9737d61acdaa1322008af9602b3b14862c07a1789aac162102d8b661b0b3302ee2f162b09e07a55ad5dfbe673a9f01d9f0c19617681024306b56ae amount: b168de3a00000000 nSequence: ffffffff hashOutputs: 9efe0c13a6b16c14a41b04ebe6a63f419bdacb2f8705b494a43063ca3cd4f708 nLockTime: 00000000 nHashType: 03000000 sigHash: 1e1f1c303dc025bd664acb72e583e933fae4cff9148bf78c157d1e8f78530aea public key: 034b8113d703413d57761b8b9781957b8c0ac1dfe69f492580ca4195f50376ba4a private key: 77bf4141a87d55bdd7f3cd0bdccf6e9e642935fec45f2f30047be7b799120661 signature: 3044022059ebf56d98010a932cf8ecfec54c48e6139ed6adb0728c09cbe1e4fa0915302e022007cd986c8fa870ff5d2b3a89139c9fe7e499259875357e20fcbb15571c76795403 hash preimage for ALL|ANYONECANPAY: 010000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000036641869ca081e70f394c6948e8af409e18b619df2ed74aa106c1ca29787b96e01000000cf56210307b8ae49ac90a048e9b53357a2354b3334e9c8bee813ecb98e99a7e07e8c3ba32103b28f0c28bfab54554ae8c658ac5c3e0ce6e79ad336331f78c428dd43eea8449b21034b8113d703413d57761b8b9781957b8c0ac1dfe69f492580ca4195f50376ba4a21033400f6afecb833092a9a21cfdf1ed1376e58c5d1f47de74683123987e967a8f42103a6d48b1131e94ba04d9737d61acdaa1322008af9602b3b14862c07a1789aac162102d8b661b0b3302ee2f162b09e07a55ad5dfbe673a9f01d9f0c19617681024306b56aeb168de3a00000000ffffffffbc4d309071414bed932f98832b27b4d76dad7e6c1346f487a8fdbb8eb90307cc0000000081000000 nVersion: 01000000 hashPrevouts: 0000000000000000000000000000000000000000000000000000000000000000 hashSequence: 0000000000000000000000000000000000000000000000000000000000000000 outpoint: 36641869ca081e70f394c6948e8af409e18b619df2ed74aa106c1ca29787b96e01000000 scriptCode: cf56210307b8ae49ac90a048e9b53357a2354b3334e9c8bee813ecb98e99a7e07e8c3ba32103b28f0c28bfab54554ae8c658ac5c3e0ce6e79ad336331f78c428dd43eea8449b21034b8113d703413d57761b8b9781957b8c0ac1dfe69f492580ca4195f50376ba4a21033400f6afecb833092a9a21cfdf1ed1376e58c5d1f47de74683123987e967a8f42103a6d48b1131e94ba04d9737d61acdaa1322008af9602b3b14862c07a1789aac162102d8b661b0b3302ee2f162b09e07a55ad5dfbe673a9f01d9f0c19617681024306b56ae amount: b168de3a00000000 nSequence: ffffffff hashOutputs: bc4d309071414bed932f98832b27b4d76dad7e6c1346f487a8fdbb8eb90307cc nLockTime: 00000000 nHashType: 81000000 sigHash: 2a67f03e63a6a422125878b40b82da593be8d4efaafe88ee528af6e5a9955c6e public key: 033400f6afecb833092a9a21cfdf1ed1376e58c5d1f47de74683123987e967a8f4 private key: 14af36970f5025ea3e8b5542c0f8ebe7763e674838d08808896b63c3351ffe49 signature: 3045022100fbefd94bd0a488d50b79102b5dad4ab6ced30c4069f1eaa69a4b5a763414067e02203156c6a5c9cf88f91265f5a942e96213afae16d83321c8b31bb342142a14d16381 hash preimage for NONE|ANYONECANPAY: 010000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000036641869ca081e70f394c6948e8af409e18b619df2ed74aa106c1ca29787b96e01000000cf56210307b8ae49ac90a048e9b53357a2354b3334e9c8bee813ecb98e99a7e07e8c3ba32103b28f0c28bfab54554ae8c658ac5c3e0ce6e79ad336331f78c428dd43eea8449b21034b8113d703413d57761b8b9781957b8c0ac1dfe69f492580ca4195f50376ba4a21033400f6afecb833092a9a21cfdf1ed1376e58c5d1f47de74683123987e967a8f42103a6d48b1131e94ba04d9737d61acdaa1322008af9602b3b14862c07a1789aac162102d8b661b0b3302ee2f162b09e07a55ad5dfbe673a9f01d9f0c19617681024306b56aeb168de3a00000000ffffffff00000000000000000000000000000000000000000000000000000000000000000000000082000000 nVersion: 01000000 hashPrevouts: 0000000000000000000000000000000000000000000000000000000000000000 hashSequence: 0000000000000000000000000000000000000000000000000000000000000000 outpoint: 36641869ca081e70f394c6948e8af409e18b619df2ed74aa106c1ca29787b96e01000000 scriptCode: cf56210307b8ae49ac90a048e9b53357a2354b3334e9c8bee813ecb98e99a7e07e8c3ba32103b28f0c28bfab54554ae8c658ac5c3e0ce6e79ad336331f78c428dd43eea8449b21034b8113d703413d57761b8b9781957b8c0ac1dfe69f492580ca4195f50376ba4a21033400f6afecb833092a9a21cfdf1ed1376e58c5d1f47de74683123987e967a8f42103a6d48b1131e94ba04d9737d61acdaa1322008af9602b3b14862c07a1789aac162102d8b661b0b3302ee2f162b09e07a55ad5dfbe673a9f01d9f0c19617681024306b56ae amount: b168de3a00000000 nSequence: ffffffff hashOutputs: 0000000000000000000000000000000000000000000000000000000000000000 nLockTime: 00000000 nHashType: 82000000 sigHash: 781ba15f3779d5542ce8ecb5c18716733a5ee42a6f51488ec96154934e2c890a public key: 03a6d48b1131e94ba04d9737d61acdaa1322008af9602b3b14862c07a1789aac16 private key: fe9a95c19eef81dde2b95c1284ef39be497d128e2aa46916fb02d552485e0323 signature: 3045022100a5263ea0553ba89221984bd7f0b13613db16e7a70c549a86de0cc0444141a407022005c360ef0ae5a5d4f9f2f87a56c1546cc8268cab08c73501d6b3be2e1e1a8a0882 hash preimage for SINGLE|ANYONECANPAY: 010000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000036641869ca081e70f394c6948e8af409e18b619df2ed74aa106c1ca29787b96e01000000cf56210307b8ae49ac90a048e9b53357a2354b3334e9c8bee813ecb98e99a7e07e8c3ba32103b28f0c28bfab54554ae8c658ac5c3e0ce6e79ad336331f78c428dd43eea8449b21034b8113d703413d57761b8b9781957b8c0ac1dfe69f492580ca4195f50376ba4a21033400f6afecb833092a9a21cfdf1ed1376e58c5d1f47de74683123987e967a8f42103a6d48b1131e94ba04d9737d61acdaa1322008af9602b3b14862c07a1789aac162102d8b661b0b3302ee2f162b09e07a55ad5dfbe673a9f01d9f0c19617681024306b56aeb168de3a00000000ffffffff9efe0c13a6b16c14a41b04ebe6a63f419bdacb2f8705b494a43063ca3cd4f7080000000083000000 nVersion: 01000000 hashPrevouts: 0000000000000000000000000000000000000000000000000000000000000000 hashSequence: 0000000000000000000000000000000000000000000000000000000000000000 outpoint: 36641869ca081e70f394c6948e8af409e18b619df2ed74aa106c1ca29787b96e01000000 scriptCode: cf56210307b8ae49ac90a048e9b53357a2354b3334e9c8bee813ecb98e99a7e07e8c3ba32103b28f0c28bfab54554ae8c658ac5c3e0ce6e79ad336331f78c428dd43eea8449b21034b8113d703413d57761b8b9781957b8c0ac1dfe69f492580ca4195f50376ba4a21033400f6afecb833092a9a21cfdf1ed1376e58c5d1f47de74683123987e967a8f42103a6d48b1131e94ba04d9737d61acdaa1322008af9602b3b14862c07a1789aac162102d8b661b0b3302ee2f162b09e07a55ad5dfbe673a9f01d9f0c19617681024306b56ae amount: b168de3a00000000 nSequence: ffffffff hashOutputs: 9efe0c13a6b16c14a41b04ebe6a63f419bdacb2f8705b494a43063ca3cd4f708 nLockTime: 00000000 nHashType: 83000000 sigHash: 511e8e52ed574121fc1b654970395502128263f62662e076dc6baf05c2e6a99b public key: 02d8b661b0b3302ee2f162b09e07a55ad5dfbe673a9f01d9f0c19617681024306b private key: 428a7aee9f0c2af0cd19af3cf1c78149951ea528726989b2e83e4778d2c3f890 signature: 30440220525406a1482936d5a21888260dc165497a90a15669636d8edca6b9fe490d309c022032af0c646a34a44d1f4576bf6a4a74b67940f8faa84c7df9abe12a01a11e2b4783 The serialized signed transaction is: 0100000000010136641869ca081e70f394c6948e8af409e18b619df2ed74aa106c1ca29787b96e0100000023220020a16b5755f7f6f96dbd65f5f0d6ab9418b89af4b1f14a1bb8a09062c35f0dcb54ffffffff0200e9a435000000001976a914389ffce9cd9ae88dcc0631e88a821ffdbe9bfe2688acc0832f05000000001976a9147480a33f950689af511e6e84c138dbbd3c3ee41588ac080047304402206ac44d672dac41f9b00e28f4df20c52eeb087207e8d758d76d92c6fab3b73e2b0220367750dbbe19290069cba53d096f44530e4f98acaa594810388cf7409a1870ce01473044022068c7946a43232757cbdf9176f009a928e1cd9a1a8c212f15c1e11ac9f2925d9002205b75f937ff2f9f3c1246e547e54f62e027f64eefa2695578cc6432cdabce271502473044022059ebf56d98010a932cf8ecfec54c48e6139ed6adb0728c09cbe1e4fa0915302e022007cd986c8fa870ff5d2b3a89139c9fe7e499259875357e20fcbb15571c76795403483045022100fbefd94bd0a488d50b79102b5dad4ab6ced30c4069f1eaa69a4b5a763414067e02203156c6a5c9cf88f91265f5a942e96213afae16d83321c8b31bb342142a14d16381483045022100a5263ea0553ba89221984bd7f0b13613db16e7a70c549a86de0cc0444141a407022005c360ef0ae5a5d4f9f2f87a56c1546cc8268cab08c73501d6b3be2e1e1a8a08824730440220525406a1482936d5a21888260dc165497a90a15669636d8edca6b9fe490d309c022032af0c646a34a44d1f4576bf6a4a74b67940f8faa84c7df9abe12a01a11e2b4783cf56210307b8ae49ac90a048e9b53357a2354b3334e9c8bee813ecb98e99a7e07e8c3ba32103b28f0c28bfab54554ae8c658ac5c3e0ce6e79ad336331f78c428dd43eea8449b21034b8113d703413d57761b8b9781957b8c0ac1dfe69f492580ca4195f50376ba4a21033400f6afecb833092a9a21cfdf1ed1376e58c5d1f47de74683123987e967a8f42103a6d48b1131e94ba04d9737d61acdaa1322008af9602b3b14862c07a1789aac162102d8b661b0b3302ee2f162b09e07a55ad5dfbe673a9f01d9f0c19617681024306b56ae00000000 === No FindAndDelete === These examples show that FindAndDelete for the signature is not applied. The transactions are generated in an unconventional way. Instead of signing using a private key, the signatures are pre-determined as part of witnessScript. The public keys are generated with key recovery, using the fixed signatures and the sighash defined in this proposal. Therefore, the private keys are unknown. The following is an unsigned transaction: 010000000169c12106097dc2e0526493ef67f21269fe888ef05c7a3a5dacab38e1ac8387f14c1d000000ffffffff0101000000000000000000000000 nVersion: 01000000 txin: 01 69c12106097dc2e0526493ef67f21269fe888ef05c7a3a5dacab38e1ac8387f1 4c1d0000 00 ffffffff txout: 01 0100000000000000 00 nLockTime: 00000000 The input comes from a P2WSH witness program: scriptPubKey : 00209e1be07558ea5cc8e02ed1d80c0911048afad949affa36d5c3951e3159dbea19, value: 0.00200000 redeemScript : OP_CHECKSIGVERIFY <0x30450220487fb382c4974de3f7d834c1b617fe15860828c7f96454490edd6d891556dcc9022100baf95feb48f845d5bfc9882eb6aeefa1bc3790e39f59eaa46ff7f15ae626c53e01> ad4830450220487fb382c4974de3f7d834c1b617fe15860828c7f96454490edd6d891556dcc9022100baf95feb48f845d5bfc9882eb6aeefa1bc3790e39f59eaa46ff7f15ae626c53e01 To sign it with a nHashType of 1 (SIGHASH_ALL): hashPrevouts: dSHA256(69c12106097dc2e0526493ef67f21269fe888ef05c7a3a5dacab38e1ac8387f14c1d0000) = b67c76d200c6ce72962d919dc107884b9d5d0e26f2aea7474b46a1904c53359f hashSequence: dSHA256(ffffffff) = 3bb13029ce7b1f559ef5e747fcac439f1455a2ec7c5f09b72290795e70665044 hashOutputs: dSHA256(010000000000000000) = e5d196bfb21caca9dbd654cafb3b4dc0c4882c8927d2eb300d9539dd0b934228 hash preimage: 01000000b67c76d200c6ce72962d919dc107884b9d5d0e26f2aea7474b46a1904c53359f3bb13029ce7b1f559ef5e747fcac439f1455a2ec7c5f09b72290795e7066504469c12106097dc2e0526493ef67f21269fe888ef05c7a3a5dacab38e1ac8387f14c1d00004aad4830450220487fb382c4974de3f7d834c1b617fe15860828c7f96454490edd6d891556dcc9022100baf95feb48f845d5bfc9882eb6aeefa1bc3790e39f59eaa46ff7f15ae626c53e01400d030000000000ffffffffe5d196bfb21caca9dbd654cafb3b4dc0c4882c8927d2eb300d9539dd0b9342280000000001000000 nVersion: 01000000 hashPrevouts: b67c76d200c6ce72962d919dc107884b9d5d0e26f2aea7474b46a1904c53359f hashSequence: 3bb13029ce7b1f559ef5e747fcac439f1455a2ec7c5f09b72290795e70665044 outpoint: 69c12106097dc2e0526493ef67f21269fe888ef05c7a3a5dacab38e1ac8387f14c1d0000 scriptCode: 4aad4830450220487fb382c4974de3f7d834c1b617fe15860828c7f96454490edd6d891556dcc9022100baf95feb48f845d5bfc9882eb6aeefa1bc3790e39f59eaa46ff7f15ae626c53e01 amount: 400d030000000000 nSequence: ffffffff hashOutputs: e5d196bfb21caca9dbd654cafb3b4dc0c4882c8927d2eb300d9539dd0b934228 nLockTime: 00000000 nHashType: 01000000 sigHash: 71c9cd9b2869b9c70b01b1f0360c148f42dee72297db312638df136f43311f23 signature: 30450220487fb382c4974de3f7d834c1b617fe15860828c7f96454490edd6d891556dcc9022100baf95feb48f845d5bfc9882eb6aeefa1bc3790e39f59eaa46ff7f15ae626c53e 01 pubkey: 02a9781d66b61fb5a7ef00ac5ad5bc6ffc78be7b44a566e3c87870e1079368df4c The serialized signed transaction is: 0100000000010169c12106097dc2e0526493ef67f21269fe888ef05c7a3a5dacab38e1ac8387f14c1d000000ffffffff01010000000000000000034830450220487fb382c4974de3f7d834c1b617fe15860828c7f96454490edd6d891556dcc9022100baf95feb48f845d5bfc9882eb6aeefa1bc3790e39f59eaa46ff7f15ae626c53e012102a9781d66b61fb5a7ef00ac5ad5bc6ffc78be7b44a566e3c87870e1079368df4c4aad4830450220487fb382c4974de3f7d834c1b617fe15860828c7f96454490edd6d891556dcc9022100baf95feb48f845d5bfc9882eb6aeefa1bc3790e39f59eaa46ff7f15ae626c53e0100000000 nVersion: 01000000 marker: 00 flag: 01 txin: 01 69c12106097dc2e0526493ef67f21269fe888ef05c7a3a5dacab38e1ac8387f1 4c1d0000 00 ffffffff txout: 01 0100000000000000 00 witness: 03 4830450220487fb382c4974de3f7d834c1b617fe15860828c7f96454490edd6d891556dcc9022100baf95feb48f845d5bfc9882eb6aeefa1bc3790e39f59eaa46ff7f15ae626c53e01 2102a9781d66b61fb5a7ef00ac5ad5bc6ffc78be7b44a566e3c87870e1079368df4c 4aad4830450220487fb382c4974de3f7d834c1b617fe15860828c7f96454490edd6d891556dcc9022100baf95feb48f845d5bfc9882eb6aeefa1bc3790e39f59eaa46ff7f15ae626c53e01 nLockTime: 00000000 The following transaction is a OP_CHECKMULTISIGVERIFY version of the FindAndDelete examples: 010000000001019275cb8d4a485ce95741c013f7c0d28722160008021bb469a11982d47a6628964c1d000000ffffffff0101000000000000000007004830450220487fb382c4974de3f7d834c1b617fe15860828c7f96454490edd6d891556dcc9022100baf95feb48f845d5bfc9882eb6aeefa1bc3790e39f59eaa46ff7f15ae626c53e0148304502205286f726690b2e9b0207f0345711e63fa7012045b9eb0f19c2458ce1db90cf43022100e89f17f86abc5b149eba4115d4f128bcf45d77fb3ecdd34f594091340c0395960101022102966f109c54e85d3aee8321301136cedeb9fc710fdef58a9de8a73942f8e567c021034ffc99dd9a79dd3cb31e2ab3e0b09e0e67db41ac068c625cd1f491576016c84e9552af4830450220487fb382c4974de3f7d834c1b617fe15860828c7f96454490edd6d891556dcc9022100baf95feb48f845d5bfc9882eb6aeefa1bc3790e39f59eaa46ff7f15ae626c53e0148304502205286f726690b2e9b0207f0345711e63fa7012045b9eb0f19c2458ce1db90cf43022100e89f17f86abc5b149eba4115d4f128bcf45d77fb3ecdd34f594091340c039596017500000000 redeemScript: OP_2 OP_CHECKMULTISIGVERIFY <30450220487fb382c4974de3f7d834c1b617fe15860828c7f96454490edd6d891556dcc9022100baf95feb48f845d5bfc9882eb6aeefa1bc3790e39f59eaa46ff7f15ae626c53e01> <304502205286f726690b2e9b0207f0345711e63fa7012045b9eb0f19c2458ce1db90cf43022100e89f17f86abc5b149eba4115d4f128bcf45d77fb3ecdd34f594091340c03959601> hash preimage: 0100000039283953eb1e26994dde57b7f9362a79a8c523e2f8deba943c27e826a005f1e63bb13029ce7b1f559ef5e747fcac439f1455a2ec7c5f09b72290795e706650449275cb8d4a485ce95741c013f7c0d28722160008021bb469a11982d47a6628964c1d00009552af4830450220487fb382c4974de3f7d834c1b617fe15860828c7f96454490edd6d891556dcc9022100baf95feb48f845d5bfc9882eb6aeefa1bc3790e39f59eaa46ff7f15ae626c53e0148304502205286f726690b2e9b0207f0345711e63fa7012045b9eb0f19c2458ce1db90cf43022100e89f17f86abc5b149eba4115d4f128bcf45d77fb3ecdd34f594091340c0395960175400d030000000000ffffffffe5d196bfb21caca9dbd654cafb3b4dc0c4882c8927d2eb300d9539dd0b9342280000000001000000 sighash: c1628a1e7c67f14ca0c27c06e4fdeec2e6d1a73c7a91d7c046ff83e835aebb72 witness: 07 00 4830450220487fb382c4974de3f7d834c1b617fe15860828c7f96454490edd6d891556dcc9022100baf95feb48f845d5bfc9882eb6aeefa1bc3790e39f59eaa46ff7f15ae626c53e01 48304502205286f726690b2e9b0207f0345711e63fa7012045b9eb0f19c2458ce1db90cf43022100e89f17f86abc5b149eba4115d4f128bcf45d77fb3ecdd34f594091340c03959601 0102 2102966f109c54e85d3aee8321301136cedeb9fc710fdef58a9de8a73942f8e567c0 21034ffc99dd9a79dd3cb31e2ab3e0b09e0e67db41ac068c625cd1f491576016c84e 9552af4830450220487fb382c4974de3f7d834c1b617fe15860828c7f96454490edd6d891556dcc9022100baf95feb48f845d5bfc9882eb6aeefa1bc3790e39f59eaa46ff7f15ae626c53e0148304502205286f726690b2e9b0207f0345711e63fa7012045b9eb0f19c2458ce1db90cf43022100e89f17f86abc5b149eba4115d4f128bcf45d77fb3ecdd34f594091340c0395960175 The new serialization format is described in BIP144 [[bip-0144.mediawiki|BIP144: Segregated Witness (Peer Services)]] == Deployment == This proposal is deployed with Segregated Witness softfork (BIP 141) == Backward compatibility == As a soft fork, older software will continue to operate without modification. Non-upgraded nodes, however, will not see nor validate the witness data and will consider all witness programs, including the redefined sigops, as anyone-can-spend scripts. == Reference Implementation == https://github.com/bitcoin/bitcoin/pull/8149 == References == == Copyright == This document is placed in the public domain. ================================================ FILE: bip-0144.mediawiki ================================================
  BIP: 144
  Layer: Peer Services
  Title: Segregated Witness (Peer Services)
  Authors: Eric Lombrozo 
           Pieter Wuille 
  Status: Deployed
  Type: Specification
  Assigned: 2016-01-08
  License: PD
==Abstract== This BIP defines new messages and serialization formats for propagation of transactions and blocks committing to segregated witness structures. ==Motivation== In addition to defining witness structures and requiring commitments in future blocks ([https://github.com/bitcoin/bips/blob/master/bip-0141.mediawiki BIP141] - Consensus segwit BIP), new mechanisms must be defined to allow peers to advertise support for segregated witness and to relay the witness structures and request them from other peers without breaking compatibility with older nodes. ==Specification== === Serialization === A new serialization format for tx messages is added to the peer-to-peer protocol. The serialization has the following structure: {| class="wikitable" style="width: auto; text-align: center; font-size: smaller; table-layout: fixed;" !Field Size !Name !Type !Description |- | 4 | version | int32_t | Transaction data format version |- | 1 | marker | char | Must be zero |- | 1 | flag | char | Must be nonzero |- | 1+ | txin_count | var_int | Number of transaction inputs |- | 41+ | txins | txin[] | A list of one or more transaction inputs |- | 1+ | txout_count | var_int | Number of transaction outputs |- | 9+ | txouts | txouts[] | A list of one or more transaction outputs |- | 1+ | script_witnesses | script_witnesses[] | The witness structure as a serialized byte array |- | 4 | lock_time | uint32_t | The block number or timestamp until which the transaction is locked |} Parsers supporting this BIP will be able to distinguish between the old serialization format (without the witness) and this one. The marker byte is set to zero so that this structure will never parse as a valid transaction in a parser that does not support this BIP. If parsing were to succeed, such a transaction would contain no inputs and a single output. If the witness is empty, the old serialization format must be used. Currently, the only witness objects type supported are script witnesses which consist of a stack of byte arrays. It is encoded as a var_int item count followed by each item encoded as a var_int length followed by a string of bytes. Each txin has its own script witness. The number of script witnesses is not explicitly encoded as it is implied by txin_count. Empty script witnesses are encoded as a zero byte. The order of the script witnesses follows the same order as the associated txins. * '''Rationale for not having an independent message type with its own serialization''': this would require separate "tx" and "block" messages, and all RPC calls operating on raw transactions would need to be duplicated, or need inefficient or nondeterministic guesswork to know which type is to be used. * '''Rationale for not using just a single 0x00 byte as marker''': that would lead to empty transactions (no inputs, no outputs, which are used in some tests) to be interpreted as new serialized data. * '''Rationale for the 0x01 flag byte in between''': this will allow us to easily add more extra non-committed data to transactions (like txouts being spent, ...). It can be interpreted as a bitvector. === Handshake === A node will signal that it can provide witnesses using the following service bit NODE_WITNESS = (1 << 3) === Hashes === Transaction hashes used in the transaction merkle tree and txin outpoints are always computed using the old non-witness serialization. Support for a new hash including the witness data is added that is computed from the new witness serialization. (Note that transactions with an empty witness always use the old serialization, and therefore, they have witness hash equal to normal hash.) === Relay === New inv types MSG_WITNESS_TX (0x40000001, or (1<<30)+MSG_TX) and MSG_WITNESS_BLOCK (0x40000002, or (1<<30)+MSG_BLOCK) are added, only for use in getdata. Inventory messages themselves still use just MSG_TX and MSG_BLOCK, similar to MSG_FILTERED_BLOCK. A further inv type MSG_FILTERED_WITNESS_BLOCK (0x40000003, or (1<<30)+MSG_FILTERED_BLOCK) is reserved for future use. * '''Rationale for not advertizing witnessness in invs''': we don't always use invs anymore (with 'sendheaders' BIP 130), plus it's not useful: implicitly, every transaction and block have a witness, old ones just have empty ones. MSG_WITNESS_TX getdata requests should use the non-witness serialized hash. The peer shall respond with a tx message, and if the witness structure is nonempty, the witness serialization shall be used. MSG_WITNESS_BLOCK requests will return a block message with transactions that have a witness using witness serialization. == Credits == Special thanks to Gregory Maxwell for originating many of the ideas in this BIP and Luke-Jr for figuring out how to deploy this as a soft fork. == Reference Implementation == https://github.com/bitcoin/bitcoin/pull/8149 == Copyright == This document is placed in the public domain. ================================================ FILE: bip-0145.mediawiki ================================================
  BIP: 145
  Layer: API/RPC
  Title: getblocktemplate Updates for Segregated Witness
  Authors: Luke Dashjr 
  Status: Deployed
  Type: Specification
  Assigned: 2016-01-30
  License: BSD-2-Clause OR OPUBL-1.0
==Abstract== This BIP describes modifications to the getblocktemplate JSON-RPC call ([[bip-0022.mediawiki|BIP 22]]) to support segregated witness as defined by [[bip-0141.mediawiki|BIP 141]]. ==Specification== ===Block Template=== The template Object is revised to include a new key: {| class="wikitable" !colspan=4| template |- ! Key !! Required !! Type !! Description |- | weightlimit || No || Number || total weight allowed in blocks |} The '!' rule prefix MUST be enabled on the "segwit" rule for templates including transactions with witness data. In particular, note that even if the client's "rules" list lacks "segwit", server MAY support old miners by producing a witness-free template and omitting the '!' rule prefix for "segwit" in the template's "rules" list. If the GBT server does not support producing witness-free templates after its activation, it must also use the '!' rule prefix in the "vbavailable" list prior to activation. ====Transactions Object Format==== The Objects listed in the response's "transactions" key is revised to include these keys: {| class="wikitable" !colspan=3|template "transactions" element |- ! Key !! Type !! Description |- | txid || String || transaction id encoded in hexadecimal; required for transactions with witness data |- | weight || Number || numeric weight of the transaction, as counted for purposes of the block's weightlimit; if key is not present, weight is unknown and clients MUST NOT assume it is zero, although they MAY choose to calculate it themselves |- | hash || String || reversed hash of complete transaction (with witness data included) encoded in hexadecimal |} Transactions with witness data may only be included if the template's "rules" list (see [[bip-0009.mediawiki#getblocktemplate_changes|BIP 9]]) includes "segwit". ===Sigops=== For templates with "segwit" enabled as a rule, the "sigoplimit" and "sigops" keys must use the new values as calculated in [[bip-0141.mediawiki#Sigops|BIP 141]]. ===Block Assembly with Witness Transactions=== When block assembly is done without witness transactions, no changes are made by this BIP, and it should be assembled as previously. When witness transactions are included in the block, the primary merkle root MUST be calculated with those transactions' "txid" field instead of "hash". A secondary merkle root MUST be calculated as per [[bip-0141.mediawiki#Commitment_structure|BIP 141's commitment structure specification]] to be inserted into the generation (coinbase) transaction. Servers MUST NOT include a commitment in the "coinbasetxn" key on the template. Clients MUST insert the commitment as an additional output at the end of the final generation (coinbase) transaction. Only if the template includes a "mutable" key (see [[bip-0023.mediawiki#Mutations|BIP 23 Mutations]]) including "generation", the client MAY in that case place the commitment output in any position it chooses, provided that no later output matches the commitment pattern. ==Motivation== Segregated witness substantially changes the structure of blocks, so the previous getblocktemplate specification is no longer sufficient. It additionally also adds a new way of counting resource limits, and so GBT must be extended to convey this information correctly as well. ==Rationale== Why doesn't "weightlimit" simply redefine the existing "sizelimit"? * "sizelimit" is already enforced by clients by counting the sum of bytes in transactions' "data" keys. * Servers may wish to limit the overall size of a block, independently from the "weight" of the block. Why is "sigoplimit" redefined instead of a new "sigopweightlimit" being added? * The old limit was already arbitrarily defined, and could not be counted by clients on their own anyway. The concept of "sigop weight" is merely a change in the arbitrary formula used. Why is "sigoplimit" divided by 4? * To resemble the previous values. (FIXME: is this a good reason? maybe we shouldn't divide it?) Why is the witness commitment required to be added to the end of the generation transaction rather than anywhere else? * Servers which do not allow modification of the generation outputs ought to be checking this as part of the validity of submissions. By requiring a specific placement, they can simply strip the commitment and do a byte-for-byte comparison of the outputs. Placing it at the end avoids the possibility of a later output matching the pattern and overriding it. Why shouldn't the server simply add the commitment upfront in the "coinbasetxn", and simply send the client stripped transaction data? * It would become impossible for servers to specify only "coinbasevalue", since clients would no longer have the information required to construct the commitment. * getblocktemplate is intended to be a *decentralised* mining protocol, and allowing clients to be blinded to the content of the block works contrary to that purpose. * BIP 23's "transactions" mutations allow the client to modify the transaction-set on their own, which is impossible without the complete transaction data. ==Reference Implementation== * [https://github.com/bitcoin/libblkmaker/tree/segwit libblkmaker] * [https://github.com/luke-jr/eloipool/tree/segwit Eloipool] * [https://github.com/bitcoin/bitcoin/pull/7404/files Bitcoin Core] ==See Also== * [[bip-0009.mediawiki|BIP 9: Version bits with timeout and delay]] * [[bip-0022.mediawiki|BIP 22: getblocktemplate - Fundamentals]] * [[bip-0023.mediawiki|BIP 23: getblocktemplate - Pooled Mining]] * [[bip-0141.mediawiki|BIP 141: Segregated Witness (Consensus layer)]] ==Copyright== This BIP is dual-licensed under the Open Publication License and BSD 2-clause license. ================================================ FILE: bip-0146.mediawiki ================================================
  BIP: 146
  Layer: Consensus (soft fork)
  Title: Dealing with signature encoding malleability
  Authors: Johnson Lau 
           Pieter Wuille 
  Status: Closed
  Type: Specification
  Assigned: 2016-08-16
  License: PD
==Abstract== This document specifies proposed changes to the Bitcoin transaction validity rules to fix signature malleability related to ECDSA signature encoding. ==Motivation== Signature malleability refers to the ability of any relay node on the network to transform the signature in transactions, with no access to the relevant private keys required. For non-segregated witness transactions, signature malleability will change the txid and invalidate any unconfirmed child transactions. Although the txid of segregated witness ([https://github.com/bitcoin/bips/blob/master/bip-0141.mediawiki BIP141]) transactions is not third party malleable, this malleability vector will change the wtxid and may reduce the efficiency of compact block relay ([https://github.com/bitcoin/bips/blob/master/bip-0152.mediawiki BIP152]). Since the enforcement of Strict DER signatures ([https://github.com/bitcoin/bips/blob/master/bip-0066.mediawiki BIP66]), there are 2 remaining known sources of malleability in ECDSA signatures: # '''Inherent ECDSA signature malleability''': ECDSA signatures are inherently malleable as taking the negative of the number S inside (modulo the curve order) does not invalidate it. # '''Malleability of failing signature''': If a signature failed to validate in OP_CHECKSIG or OP_CHECKMULTISIG, a FALSE would be returned to the stack and the script evaluation would continue. The failing signature may take any value, as long as it follows all the rules described in BIP66. This document specifies new rules to fix the aforesaid signature malleability. ==Specification== To fix signature encoding malleability, the following new rules are applied to pre-segregated witness and segregated witness scripts: ===LOW_S=== We require that the S value inside ECDSA signatures is at most the curve order divided by 2 (essentially restricting this value to its lower half range). Every signature passed to OP_CHECKSIGIncluding pay-to-witness-public-key-hash (P2WPKH) described in BIP141, OP_CHECKSIGVERIFY, OP_CHECKMULTISIG, or OP_CHECKMULTISIGVERIFY, to which ECDSA verification is applied, MUST use a S value between 0x1 and 0x7FFFFFFF FFFFFFFF FFFFFFFF FFFFFFFF 5D576E73 57A4501D DFE92F46 681B20A0 (inclusive) with strict DER encoding (see [https://github.com/bitcoin/bips/blob/master/bip-0066.mediawiki BIP66]). If a signature passing to ECDSA verification does not pass the Low S value check and is not an empty byte array, the entire script evaluates to false immediately. A high S value in signature could be trivially replaced by S' = 0xFFFFFFFF FFFFFFFF FFFFFFFF FFFFFFFE BAAEDCE6 AF48A03B BFD25E8C D0364141 - S. ===NULLFAIL=== If an OP_CHECKSIG is trying to return a FALSE value to the stack, we require that the relevant signature must be an empty byte array. If an OP_CHECKMULTISIG is trying to return a FALSE value to the stack, we require that all signatures passing to this OP_CHECKMULTISIG must be empty byte arrays, even the processing of some signatures might have been skipped due to early termination of the signature verification. Otherwise, the entire script evaluates to false immediately. ==Examples== The following examples are the combined results of the LOW_S and NULLFAIL rules.Please note that due to implementation details in reference client v0.13.1, some signatures with S value higher than the half curve order might pass the LOW_S test. However, such signatures are certainly invalid, and will fail later due to NULLFAIL test. Notation: CO : curve order = 0xFFFFFFFF FFFFFFFF FFFFFFFF FFFFFFFE BAAEDCE6 AF48A03B BFD25E8C D0364141 HCO : half curve order = CO / 2 = 0x7FFFFFFF FFFFFFFF FFFFFFFF FFFFFFFF 5D576E73 57A4501D DFE92F46 681B20A0 P1, P2 : valid, serialized, public keys S1L, S2L : valid low S value signatures using respective keys P1 and P2 (1 ≤ S ≤ HCO) S1H, S2H : signatures with high S value (otherwise valid) using respective keys P1 and P2 (HCO < S < CO) F : any BIP66-compliant non-empty byte array but not a valid signature These scripts will return a TRUE to the stack as before: S1L P1 CHECKSIG 0 S1L S2L 2 P1 P2 2 CHECKMULTISIG These scripts will return a FALSE to the stack as before: 0 P1 CHECKSIG 0 0 0 2 P1 P2 2 CHECKMULTISIG These previously TRUE scripts will fail immediately under the new rules: S1H P1 CHECKSIG 0 S1H S2L 2 P1 P2 2 CHECKMULTISIG 0 S1L S2H 2 P1 P2 2 CHECKMULTISIG 0 S1H S2H 2 P1 P2 2 CHECKMULTISIG These previously FALSE scripts will fail immediately under the new rules: F P1 CHECKSIG 0 S2L S1L 2 P1 P2 2 CHECKMULTISIG 0 S1L F 2 P1 P2 2 CHECKMULTISIG 0 F S2L 2 P1 P2 2 CHECKMULTISIG 0 S1L 0 2 P1 P2 2 CHECKMULTISIG 0 0 S2L 2 P1 P2 2 CHECKMULTISIG 0 F 0 2 P1 P2 2 CHECKMULTISIG 0 0 F 2 P1 P2 2 CHECKMULTISIG ==Deployment== This BIP will be deployed by "version bits" [https://github.com/bitcoin/bips/blob/master/bip-0009.mediawiki BIP9]. Details TBD. For Bitcoin mainnet, the BIP9 starttime will be midnight TBD UTC (Epoch timestamp TBD) and BIP9 timeout will be midnight TBD UTC (Epoch timestamp TBD). For Bitcoin testnet, the BIP9 starttime will be midnight TBD UTC (Epoch timestamp TBD) and BIP9 timeout will be midnight TBD UTC (Epoch timestamp TBD). ==Compatibility== The reference client has produced LOW_S compatible signatures since v0.9.0, and the LOW_S rule has been enforced as relay policy by the reference client since v0.11.1. As of August 2016, very few transactions violating the requirement are being added to the chain. For all scriptPubKey types in actual use, non-compliant signatures can trivially be converted into compliant ones, so there is no loss of functionality by these requirements. Scripts with failing OP_CHECKSIG or OP_CHECKMULTISIG rarely happen on the chain. The NULLFAIL rule has been enforced as relay policy by the reference client since v0.13.1. Users MUST pay extra attention to these new rules when designing exotic scripts. ==Implementation== Implementations for the reference client is available at: https://github.com/bitcoin/bitcoin/blob/35fe0393f216aa6020fc929272118eade5628636/src/script/interpreter.cpp#L185 and https://github.com/bitcoin/bitcoin/pull/8634 ==Footnotes== ==Acknowledgements== This document is extracted from the previous [https://github.com/bitcoin/bips/blob/master/bip-0062.mediawiki BIP62] proposal which had input from various people. ==Copyright== This document is placed in the public domain. ================================================ FILE: bip-0147.mediawiki ================================================
  BIP: 147
  Layer: Consensus (soft fork)
  Title: Dealing with dummy stack element malleability
  Authors: Johnson Lau 
  Status: Deployed
  Type: Specification
  Assigned: 2016-09-02
  License: PD
==Abstract== This document specifies proposed changes to the Bitcoin transaction validity rules to fix a malleability vector in the extra stack element consumed by OP_CHECKMULTISIG and OP_CHECKMULTISIGVERIFY. ==Motivation== Signature malleability refers to the ability of any relay node on the network to transform the signature in transactions, with no access to the relevant private keys required. For non-segregated witness transactions, signature malleability will change the txid and invalidate any unconfirmed child transactions. Although the txid of segregated witness ([https://github.com/bitcoin/bips/blob/master/bip-0141.mediawiki BIP141]) transactions is not third party malleable, this malleability vector will change the wtxid and may reduce the efficiency of compact block relay ([https://github.com/bitcoin/bips/blob/master/bip-0152.mediawiki BIP152]). A design flaw in OP_CHECKMULTISIG and OP_CHECKMULTISIGVERIFY causes them to consume an extra stack element ("dummy element") after signature validation. The dummy element is not inspected in any manner, and could be replaced by any value without invalidating the script. This document specifies a new rule to fix this signature malleability. ==Specification== To fix the dummy element malleability, a new consensus rule ("NULLDUMMY") is deployed to require that the dummy element MUST be the empty byte array. Anything else makes the script evaluate to false immediately. The NULLDUMMY rule applies to OP_CHECKMULTISIG and OP_CHECKMULTISIGVERIFY in pre-segregated scripts, and also pay-to-witness-script-hash scripts described in BIP141. ==Deployment== This BIP will be deployed by "version bits" [https://github.com/bitcoin/bips/blob/master/bip-0009.mediawiki BIP9] using the same parameters for BIP141 and BIP143, with the name "segwit" and using bit 1. For Bitcoin mainnet, the BIP9 starttime is midnight 15 November 2016 UTC (Epoch timestamp 1479168000) and BIP9 timeout is midnight 15 November 2017 UTC (Epoch timestamp 1510704000). For Bitcoin testnet, the BIP9 starttime is midnight 1 May 2016 UTC (Epoch timestamp 1462060800) and BIP9 timeout is midnight 1 May 2017 UTC (Epoch timestamp 1493596800). ==Compatibility== The reference client has produced compatible signatures from the beginning, and the NULLDUMMY rule has been enforced as relay policy by the reference client since v0.10.0. There has been no transactions violating the requirement being added to the chain since at least August 2015. For all scriptPubKey types in actual use, non-compliant signatures can trivially be converted into compliant ones, so there is no loss of functionality by this requirement. Users MUST pay extra attention to this new rule when designing exotic scripts. ==Implementation== An implementation for the reference client is available at https://github.com/bitcoin/bitcoin/pull/8636 ==Acknowledgements== Peter Todd is the original author of NULLDUMMY. This document is extracted from the previous [https://github.com/bitcoin/bips/blob/master/bip-0062.mediawiki BIP62] proposal, which was composed by Pieter Wuille and had input from various people. ==Copyright== This document is placed in the public domain. ================================================ FILE: bip-0148.mediawiki ================================================
  BIP: 148
  Layer: Consensus (soft fork)
  Title: Mandatory activation of segwit deployment
  Authors: Shaolin Fry 
  Status: Deployed
  Type: Specification
  Assigned: 2017-03-12
  License: BSD-3-Clause OR CC0-1.0
==Abstract== This document specifies a BIP16 like soft fork flag day activation of the segregated witness BIP9 deployment known as "segwit". ==Definitions== "existing segwit deployment" refer to the BIP9 "segwit" deployment using bit 1, between November 15th 2016 and November 15th 2017 to activate BIP141, BIP143 and BIP147. ==Motivation== Segwit increases the blocksize, fixes transaction malleability, and makes scripting easier to upgrade as well as bringing many other [https://bitcoincore.org/en/2016/01/26/segwit-benefits/ benefits]. It is hoped that miners will respond to this BIP by activating segwit early, before this BIP takes effect. Otherwise this BIP will cause the mandatory activation of the existing segwit deployment before the end of midnight November 15th 2017. ==Specification== All times are specified according to median past time. This BIP will be active between midnight August 1st 2017 (epoch time 1501545600) and midnight November 15th 2017 (epoch time 1510704000) if the existing segwit deployment is not locked-in or activated before epoch time 1501545600. This BIP will cease to be active when segwit is locked-in. While this BIP is active, all blocks must set the nVersion header top 3 bits to 001 together with bit field (1<<1) (according to the existing segwit deployment). Blocks that do not signal as required will be rejected. === Reference implementation ===
// Check if Segregated Witness is Locked In
bool IsWitnessLockedIn(const CBlockIndex* pindexPrev, const Consensus::Params& params)
{
    LOCK(cs_main);
    return (VersionBitsState(pindexPrev, params, Consensus::DEPLOYMENT_SEGWIT, versionbitscache) == THRESHOLD_LOCKED_IN);
}

// BIP148 mandatory segwit signalling.
int64_t nMedianTimePast = pindex->GetMedianTimePast();
if ( (nMedianTimePast >= 1501545600) &&  // Tue 01 Aug 2017 00:00:00 UTC
     (nMedianTimePast <= 1510704000) &&  // Wed 15 Nov 2017 00:00:00 UTC
     (!IsWitnessLockedIn(pindex->pprev, chainparams.GetConsensus()) &&  // Segwit is not locked in
      !IsWitnessEnabled(pindex->pprev, chainparams.GetConsensus())) )   // and is not active.
{
    bool fVersionBits = (pindex->nVersion & VERSIONBITS_TOP_MASK) == VERSIONBITS_TOP_BITS;
    bool fSegbit = (pindex->nVersion & VersionBitsMask(chainparams.GetConsensus(), Consensus::DEPLOYMENT_SEGWIT)) != 0;
    if (!(fVersionBits && fSegbit)) {
        return state.DoS(0, error("ConnectBlock(): relayed block must signal for segwit, please upgrade"), REJECT_INVALID, "bad-no-segwit");
    }
}
https://github.com/bitcoin/bitcoin/compare/master...shaolinfry:bip-segwit-flagday ==Backwards Compatibility== This deployment is compatible with the existing "segwit" bit 1 deployment scheduled between midnight November 15th, 2016 and midnight November 15th, 2017. ==Rationale== Historically, the P2SH soft fork (BIP16) was activated using a predetermined flag day where nodes began enforcing the new rules. P2SH was successfully activated with relatively few issues By orphaning non-signalling blocks during the last month of the BIP9 bit 1 "segwit" deployment, this BIP can cause the existing "segwit" deployment to activate without needing to release a new deployment. ==References== *[https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2017-March/013714.html Mailing list discussion] *[https://github.com/bitcoin/bitcoin/blob/v0.6.0/src/main.cpp#L1281-L1283 P2SH flag day activation] *[[bip-0009.mediawiki|BIP9 Version bits with timeout and delay]] *[[bip-0016.mediawiki|BIP16 Pay to Script Hash]] *[[bip-0141.mediawiki|BIP141 Segregated Witness (Consensus layer)]] *[[bip-0143.mediawiki|BIP143 Transaction Signature Verification for Version 0 Witness Program]] *[[bip-0147.mediawiki|BIP147 Dealing with dummy stack element malleability]] *[https://bitcoincore.org/en/2016/01/26/segwit-benefits/ Segwit benefits] ==Copyright== This document is dual licensed as BSD 3-clause, and Creative Commons CC0 1.0 Universal. ================================================ FILE: bip-0149.mediawiki ================================================
  BIP: 149
  Layer: Consensus (soft fork)
  Title: Segregated Witness (second deployment)
  Authors: Shaolin Fry 
  Status: Closed
  Type: Specification
  Assigned: 2017-04-14
  License: BSD-3-Clause OR CC0-1.0
==Abstract== This document specifies a user activated soft fork for [[bip-0141.mediawiki|BIP141]], [[bip-0143.mediawiki|BIP143]] and [[bip-0147.mediawiki|BIP147]] using versionbits with guaranteed lock-in. ==Motivation== Miners have been reluctant to signal the BIP9 segwit deployment despite a large portion of the Bitcoin ecosystem who want the soft fork activated. This BIP specifies a user activated soft fork (UASF) that deploys segwit again using versionbits with guaranteed lock-in on timeout if the BIP is not already locked-in or activated by the timeout. This ensures users have sufficient time to prepare and no longer require a miner supermajority, while still allowing for an earlier miner activated soft fork (MASF). ==Reference implementation== The reference implementation will refuse to run on Bitcoin mainnet before 7 November 2017, and can only be run on testnet and regtest until then. https://github.com/bitcoin/bitcoin/compare/master...shaolinfry:uasegwit-flagday ==Specification== This deployment will set service bit (1<<5) as NODE_UAWITNESS. ==Deployment== This BIP should only be deployed if BIP9-segwit fails to lock-in or activate before timeout on 15 November 2017. This BIP cannot be deployed before 15 November 2017. This BIP will be deployed by BIP8 with the name "segwit" and using bit 1. For Bitcoin mainnet, the BIP8 starttime will be midnight 16 November 2017 UTC (Epoch timestamp 1510790400) and BIP8 timeout will be 4 July 2018 UTC (Epoch timestamp 1530662400). For Bitcoin testnet, segwit is already activated so no deployment is specified. ==Backwards Compatibility== This deployment reuses the GBT deployment name "segwit" to maintain compatibility with existing mining software. This deployment is incompatible with the BIP9-segwit deployment and should not be run concurrently with it. ==Rationale== The '''starttime''' of this BIP is after the BIP9-segwit timeout to remove compatibility issues with old nodes. ==References== [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2017-April/014234.html Mailing list discussion] [[bip-0008.mediawiki|BIP8]] [[bip-0009.mediawiki|BIP9]] [[bip-0141.mediawiki|BIP141]] [[bip-0143.mediawiki|BIP143]] [[bip-0147.mediawiki|BIP147]] ==Copyright== This document is dual licensed as BSD 3-clause, and Creative Commons CC0 1.0 Universal. ================================================ FILE: bip-0150.mediawiki ================================================
  BIP: 150
  Layer: Peer Services
  Title: Peer Authentication
  Authors: Jonas Schnelli 
  Comments-Summary: Discouraged for implementation (one person)
  Comments-URI: https://github.com/bitcoin/bips/wiki/Comments:BIP-0150
  Status: Closed
  Type: Specification
  Assigned: 2016-03-23
  License: PD
== Abstract == This BIP describes a way for peers to authenticate to other peers to guarantee node ownership and/or allow peers to access additional or limited node services, without the possibility of fingerprinting. == Motivation == We assume peer operators want to limit the access of different node services or increase datastream priorities to a selective subset of peers. Also we assume that peers want to connect to specific peers to broadcast or filter transactions (or similar actions that reveal sensitive information) and therefore operators want to authenticate the remote peer and ensure that they have not connected to a MITM (man-in-the-middle) attacker. Benefits of peer authentication: * Peers can detect MITM attacks when connecting to known peers * Peers can allow resource hungry transaction filtering only to specific peers * Peers can allow access to sensitive information that can lead to node fingerprinting (fee estimation) * Peers can allow custom message types (private extensions) to authenticated peers A simple authentication scheme based on elliptic cryptography will allow peers to identify each other and selectively allow access to restricted services or reject the connection if the peer identity cannot be verified. == Specification == The authentication scheme proposed in this BIP uses ECDSA, '''secrets will never be transmitted'''. '''Authentication initialization must only happen if encrypted channels have been established (according to BIP-151 [1]).''' The '''encryption-session-ID''' is available once channels are encrypted (according to BIP-151 [1]). The identity-public-keys used for the authentication must be pre-shared over a different channel (mail/PGP, physical paper exchange, etc.). This BIP does not cover a "trust on first use" (TOFU) concept. The authentication state must be kept until the encryption/connection terminates. Only one authentication process is allowed per connection. Re-authentication require re-establishing the connection. === Known-peers and authorized-peers database === Each peer that supports p2p authentication must provide two user-editable "databases". # '''known-peers''' contains known identity-public-keys together with a network identifier (IP & port), similar to the "known-host" file supported by openssh. # '''authorized-peers''' contains authorized identity-public-keys === Local identity key management === Each peer can configure multiple identity-keys (ECC, 32 bytes). Peers should make sure that each network interface (IPv4, IPv6, tor) has its own identity-key (otherwise it would be possible to link a tor address to a IPvX address). The identity-public-key(s) can be shared over a different channel with other node-operators (or non-validating clients) to grant authorized access. === Authentication procedure === Authentication based on this BIP will require both sides to authenticate. Signatures/public-keys will only be revealed if the remote peer can prove that they already know the remote identity-public-key. # -> Requesting peer sends AUTHCHALLENGE (hash) # <- Responding peer sends AUTHREPLY (signature) # -> Requesting peer sends AUTHPROPOSE (hash) # <- Responding peer sends AUTHCHALLENGE (hash) # -> Requesting peer sends AUTHREPLY (signature) For privacy reasons, dropping the connection or aborting during the authentication process must not be allowed. === AUTHCHALLENGE message === A peer can send an authentication challenge to see if the responding peer can produce a valid signature with the expected responding peer's identity-public-key by sending an AUTHCHALLENGE-message to the remote peer. The responding peer needs to check if the hash matches the hash calculated with his own local identity-public-key. Fingerprinting the requesting peer is not possible. {|class="wikitable" ! Field Size !! Description !! Data type !! Comments |- | 32bytes || challenge-hash || hash || hash(encryption-session-ID || challenge_type || remote-peers-expected-identity-public-key) |} challenge_type is a single character. i if the AUTHCHALLENGE-message is the first, requesting challenge or r if it's the second, remote peers challenge message. === AUTHREPLY message === A peer must reply an AUTHCHALLENGE-message with an AUTHREPLY-message. {|class="wikitable" ! Field Size !! Description !! Data type !! Comments |- | 64bytes || signature || normalized comp.-signature || A signature of the encryption-session-ID done with the identity-key |} If the challenge-hash from the AUTHCHALLENGE-message did not match the local authentication public-key, the signature must contain 64 bytes of zeros. The requesting peer can check the responding peer's identity by checking the validity of the sent signature against with the pre-shared remote peers identity-public-key. If the signature was invalid, the requesting peer must still proceed with the authentication by sending an AUTHPROPOSE-message with 32 random bytes. === AUTHPROPOSE message === A peer can propose authentication of the channel by sending an AUTHPROPOSE-message to the remote peer. If the signature sent in AUTHREPLY was invalid, the peer must still send an AUTHPROPOSE-message containing 32 random bytes. The AUTHPROPOSE message must be answered with an AUTHCHALLENGE-message - even if the proposed requesting-peers identity-public-key has not been found in the authorized-peers database. In case of no match, the responding AUTHCHALLENGE-message must contains 32 bytes of zeros. {|class="wikitable" ! Field Size !! Description !! Data type !! Comments |- | 32bytes || auth-propose-hash || hash || hash(encryption-session-ID || "p" || identity-public-key) |} == Post-Authentication Re-Keying == After the second AUTHREPLY message (requesting peer's signature -> responding peer), both clients must re-key the symmetric encryption according to BIP151 while using '''a slightly different re-key key derivation hash'''. Both peers re-key with hash(encryption-session-ID || old_symmetric_cipher_key || requesting-peer-identity-public-key || responding-peer-identity-public-key) == Identity-Addresses == The peers should display/log the identity-public-key as an identity-address to the users, which is a base58-check encoded ripemd160(sha256) hash. The purpose of this is for better visual comparison (logs, accept-dialogs). The base58check identity byte is 0x0F followed by an identity-address version number (=0xFF01). An identity address would look like TfG4ScDgysrSpodWD4Re5UtXmcLbY5CiUHA and can be interpreted as a remote peer's fingerprint. == Compatibility == This proposal is backward compatible. Non-supporting peers will ignore the new AUTH* messages. == Example of an auth interaction == Before authentication (once during peer setup or upgrade) # Requesting peer and responding peer create each an identity-keypair (standard ECC priv/pubkey) # Requesting and responding peer share the identity-public-key over a different channel (mail/PGP, physical paper exchange, etc.) # Responding peer stores requesting peers identity-public-key in its authorized-peers database (A) # Requesting peer stores responding peers identity-public-key in its known-peers database together with its IP and port (B) Encryption # Encrypted channels must be established (according to BIP-151 [1]) Authentication # Requesting peer sends an AUTHCHALLENGE message AUTHCHALLENGE: [32 bytes, hash(encryption-session-ID || "i" || )] # Responding peer does create the same hash (encryption-session-ID || "i" || ) with its local identity-public-key # If the hash does not match, response with an AUTHREPLY message containing 64bytes of zeros. # In case of a match, response with an AUTHREPLY message AUTHREPLY: [64 bytes normalized compact ECDSA signature (H)] (sig of the encryption-session-ID done with the identity-key) # Requesting peer does verify the signature with the remote-peers-identity-public-key # If the signature is invalid, requesting peer answers with an AUTHREPLY message containing 32 random bytes # In case of a valid signature, requesting peer sends an AUTHPROPOSE message AUTHPROPOSE: [32 bytes, hash(encryption-session-ID || "p" || )] # Responding peer iterates over authorized-peers database (A), hashes the identical data and looks for a match. # If the hash does not match, responding peer answer with an AUTHCHALLENGE message containing 32 bytes of zeros. # In case of a match, responding peer sends an AUTHCHALLENGE message with the hashed client public-key AUTHCHALLENGE: [32 bytes, hash(encryption-session-ID || "r" || )] # Requesting peer sends an AUTHREPLY message containing 64 bytes of zeros if server failed to authenticate # Otherwise, response with signature in the AUTHREPLY message AUTHREPLY: [64 bytes normalized compact ECDSA signature (H)] (sig of the encryption-session-ID done with the identity-key) # Responding peer must verify the signature and can grant access to restricted services. # Both peers re-key the encryption after BIP151 including the requesting-peer-identity-public-key and responding-peer-identity-public-key == Disadvantages == The protocol may be slow if a peer has a large authorized-peers database due to the requirement of iterating and hashing over all available authorized peer identity-public-keys. == Reference implementation == == References == * [1] [[bip-0151.mediawiki|BIP 151: Peer-to-Peer Communication Encryption]] == Acknowledgements == * Gregory Maxwell and Pieter Wuille for most of the ideas in this BIP. * Bryan Bishop for editing. == Copyright == This work is placed in the public domain. ================================================ FILE: bip-0151.mediawiki ================================================
  BIP: 151
  Layer: Peer Services
  Title: Peer-to-Peer Communication Encryption
  Authors: Jonas Schnelli 
  Comments-Summary: Controversial; some recommendation, and some discouragement
  Comments-URI: https://github.com/bitcoin/bips/wiki/Comments:BIP-0151
  Status: Closed
  Type: Specification
  Assigned: 2016-03-23
  License: PD
  Proposed-Replacement: 324
== Abstract == This BIP describes an alternative way that a peer can encrypt their communication between a selective subset of remote peers. == Motivation == The Bitcoin network does not encrypt communication between peers today. This opens up security issues (eg: traffic manipulation by others) and allows for mass surveillance / analysis of bitcoin users. Mostly this is negligible because of the nature of Bitcoin's trust model, however, for SPV nodes this can have significant privacy impacts [1] and could reduce the censorship-resistance of a peer. Encrypting peer traffic will make analysis and specific user targeting much more difficult than it currently is. Today it's trivial for a network provider or any other men-in-the-middle to identify a Bitcoin user and its controlled addresses/keys (and link with his Google profile, etc.). Just created and broadcasted transactions will reveal the amount and the payee to the network provider. This BIP also describes a way that data manipulation (blocking commands by a intercepting TCP/IP node) would be identifiable by the communicating peers. Analyzing the type of p2p communication would still be possible because of the characteristics (size, sending-interval, etc.) of the encrypted messages. Encrypting traffic between peers is already possible with VPN, tor, stunnel, curveCP or any other encryption mechanism on a deeper OSI level, however, most mechanisms are not practical for SPV or other DHCP/NAT environment and will require significant knowhow in how to setup such a secure channel. == Specification == A peer that supports encryption must accept encryption requests from all peers. An independent ECDH negotiation for both communication directions is required and therefore a bidirectional communication will use two symmetric cipher keys (one per direction). Both peers must only send encrypted messages after a successful ECDH negotiation in ''both directions''. Encryption initialization must happen before sending any other messages to the responding peer (encinit message after a version message must be ignored). === Symmetric Encryption Cipher Keys === The symmetric encryption cipher keys will be calculated with ECDH/HKDF by sharing the pubkeys of an ephemeral key. Once the ECDH secret is calculated on each side, the symmetric encryption cipher keys must be derived with HKDF [2] after the following specification: 1. HKDF extraction PRK = HKDF_EXTRACT(hash=SHA256, salt="bitcoinecdh", ikm=ecdh_secret|cipher-type). 2. Derive Key1 K_1 = HKDF_EXPAND(prk=PRK, hash=SHA256, info="BitcoinK1", L=32) 3. Derive Key2 K_2 = HKDF_EXPAND(prk=PRK, hash=SHA256, info="BitcoinK2", L=32) It is important to include the cipher-type into the symmetric cipher key derivation to avoid weak-cipher-attacks. === Session ID === Both sides must also calculate the 256bit session-id using SID = HKDF_EXPAND(prk=PRK, hash=SHA256, info="BitcoinSessionID", L=32). The session-id can be used for linking the encryption-session to an identity check. === The encinit message type === To request encrypted communication, the requesting peer generates an EC ephemeral-session-keypair and sends an encinit message to the responding peer and waits for an encack message. The responding node must do the same encinit/encack interaction for the opposite communication direction. {|class="wikitable" ! Field Size !! Description !! Data type !! Comments |- | 33bytes || ephemeral-pubkey || comp.-pubkey || The session pubkey from the requesting peer |- | 1bytes || symmetric key cipher type || int8 || symmetric key cipher type to use |} Possible symmetric key ciphers types {|class="wikitable" ! Number !! symmetric key ciphers type |- | 0 || chacha20-poly1305@openssh.com |} === ChaCha20-Poly1305 Cipher Suite === ChaCha20 is a stream cipher designed by Daniel Bernstein [3]. It operates by permuting 128 fixed bits, 128 or 256 bits of key, a 64 bit nonce and a 64 bit counter into 64 bytes of output. This output is used as a keystream, with any unused bytes simply discarded. Poly1305, also by Daniel Bernstein [4], is a one-time Carter-Wegman MAC that computes a 128 bit integrity tag given a message and a single-use 256 bit secret key. The chacha20-poly1305@openssh.com specified and defined by openssh [5] combines these two primitives into an authenticated encryption mode. The construction used is based on that proposed for TLS by Adam Langley [6], but differs in the layout of data passed to the MAC and in the addition of encryption of the packet lengths. K_1 must be used to only encrypt the payload size of the encrypted message to avoid leaking information by revealing the message size. K_2 must be used in conjunction with poly1305 to build an AEAD. Optimized implementations of ChaCha20-Poly1305 are very fast in general, therefore it is very likely that encrypted messages require less CPU cycles per byte than the current unencrypted p2p message format. A quick analysis by Pieter Wuille of the current ''standard implementations'' has shown that SHA256 requires more CPU cycles per byte than ChaCha20 & Poly1304. === The encack message type === The responding peer accepts the encryption request by sending an encack message. {|class="wikitable" ! Field Size !! Description !! Data type !! Comments |- | 33bytes || ephemeral-pubkey || comp.-pubkey || The session pubkey from the responding peer |} At this point, the shared secret key for the symmetric key cipher must be calculated by using ECDH (own privkey x remote pub key). Private keys will never be transmitted. The shared secret can only be calculated if an attacker knows at least one private key and the remote peer's public key. * '''The encinit/encack interaction must be done from both sides.''' * Each communication direction uses its own secret key for the symmetric cipher. * The second encinit request (from the responding peer) must use the same symmetric cipher type. * All unencrypted messages before the second encack response (from the responding peer) must be ignored. * After a successful encinit/encack interaction, the "encrypted messages structure" must be used. Non-encrypted messages from the requesting peer must lead to a connection termination. After a successful encinit/encack interaction from both sides, the messages format must use the "encrypted messages structure". Non-encrypted messages from the requesting peer must lead to a connection termination (can be detected by the 4 byte network magic in the unencrypted message structure). === Encrypted Messages Structure === {|class="wikitable" ! Field Size !! Description !! Data type !! Comments |- | 4 || length || uint32_t || Length of ciphertext payload in number of bytes |- | ? || ciphertext payload || ? || One or many ciphertext command & message data |- | 16 || MAC tag || ? || 128bit MAC-tag |} Encrypted messages do not have the 4byte network magic. The maximum message length needs to be chosen carefully. The 4 byte length field can lead to a required message buffer of 4 GiB. Processing the message before the authentication succeeds must not be done. The 4byte sha256 checksum is no longer required because the AEAD. Both peers need to track the message sequence number (uint32) of sent messages to the remote peer for building a 64 bit symmetric cipher IV. Sequence numbers are allowed to overflow to zero after 4294967295 (2^32-1). The encrypted payload will result decrypted in one or many unencrypted messages: {|class="wikitable" ! Field Size !! Description !! Data type !! Comments |- | ? || command || varlen || ASCII string identifying the packet content, we are using varlen in the encrypted messages. |- | 4 || length || uint32_t || Length of plaintext payload |- | ? || payload || ? || The actual data |} If more data is present, another message must be deserialized. There is no explicit amount-of-messages integer. === Re-Keying === A responding peer can inform the requesting peer over a re-keying with an encack message containing 33byte of zeros to indicate that all encrypted message following after this encack message will be encrypted with ''the next symmetric cipher key''. The new symmetric cipher key will be calculated by SHA256(SHA256(session_id || old_symmetric_cipher_key)). Re-Keying interval is a peer policy with a minimum timespan of 10 seconds. The Re-Keying must be done after every 1GB of data sent or received (recommended by RFC4253 SSH Transport). === Risks === The encryption does not include an identity authentication scheme. This BIP does not cover a proposal to avoid MITM attacks during the encryption initialization. Identity authentication will be covered in another BIP and will presume communication encryption after this BIP. == Compatibility == This proposal is backward compatible. Non-supporting peers will ignore the encinit messages. == Reference implementation == == References == * [1] https://e-collection.library.ethz.ch/eserv/eth:48205/eth-48205-01.pdf * [2] HKDF (RFC 5869) https://tools.ietf.org/html/rfc5869 * [3] ChaCha20 https://cr.yp.to/chacha/chacha-20080128.pdf * [4] Poly1305 https://cr.yp.to/mac/poly1305-20050329.pdf * [5] https://github.com/openssh/openssh-portable/blob/05855bf2ce7d5cd0a6db18bc0b4214ed5ef7516d/PROTOCOL.chacha20poly1305 * [6] "ChaCha20 and Poly1305 based Cipher Suites for TLS", Adam Langley https://tools.ietf.org/html/draft-agl-tls-chacha20poly1305-03 == Acknowledgements == * Pieter Wuille and Gregory Maxwell for most of the ideas in this BIP. == Copyright == This work is placed in the public domain. ================================================ FILE: bip-0152.mediawiki ================================================
  BIP: 152
  Layer: Peer Services
  Title: Compact Block Relay
  Authors: Matt Corallo 
  Comments-Summary: Unanimously Recommended for implementation
  Comments-URI: https://github.com/bitcoin/bips/wiki/Comments:BIP-0152
  Status: Deployed
  Type: Specification
  Assigned: 2016-04-27
  License: PD
==Abstract== Compact blocks on the wire as a way to save bandwidth for nodes on the P2P network. The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED", "MAY", and "OPTIONAL" in this document are to be interpreted as described in RFC 2119. ==Motivation== Historically, the Bitcoin P2P protocol has not been very bandwidth efficient for block relay. Every transaction in a block is included when relayed, even though a large number of the transactions in a given block are already available to nodes before the block is relayed. This causes moderate inbound bandwidth spikes for nodes when receiving blocks, but can cause very significant outbound bandwidth spikes for some nodes which receive a block before their peers. When such spikes occur, buffer bloat can make consumer-grade internet connections temporarily unusable, and can delay the relay of blocks to remote peers who may choose to wait instead of redundantly requesting the same block from other, less congested, peers. Thus, decreasing the bandwidth used during block relay is very useful for many individuals running nodes. While the goal of this work is explicitly not to reduce block transfer latency, it does, as a side effect reduce block transfer latencies in some rather significant ways. Additionally, this work forms a foundation for future work explicitly targeting low-latency block transfer. ==Specification for version 1== ===Intended Protocol Flow=== The protocol is intended to be used in two ways, depending on the peers and bandwidth available, as discussed [[#Implementation_Notes|later]]. The "high-bandwidth" mode, which nodes may only enable for a few of their peers, is enabled by setting the first boolean to 1 in a sendcmpct message. In this mode, peers send new block announcements with the short transaction IDs already (via a cmpctblock message), possibly even before fully validating the block (as indicated by the grey box in the image above). In some cases no further round-trip is needed, and the receiver can reconstruct the block and process it as usual immediately. When some transactions were not available from local sources (ie mempool), a getblocktxn/blocktxn roundtrip is necessary, bringing the best-case latency to the same 1.5*RTT minimum time that nodes take today, though with significantly less bandwidth usage. The "low-bandwidth" mode is enabled by setting the first boolean to 0 in a sendcmpct message. In this mode, peers send new block announcements with the usual inv/headers announcements (as per BIP130, and after fully validating the block). The receiving peer may then request the block using a MSG_CMPCT_BLOCK getdata request, which will receive a response of the header and short transaction IDs. In some cases no further round-trip is needed, and the receiver can reconstruct the block and process it as usual, taking the same 1.5*RTT minimum time that nodes take today, though with significantly less bandwidth usage. When some transactions were not available from local sources (ie mempool), a getblocktxn/blocktxn roundtrip is necessary, bringing the latency to at least 2.5*RTT in this case, again with significantly less bandwidth usage than today. Because TCP often exhibits worse transfer latency for larger data sizes (as a multiple of RTT), total latency is expected to be reduced even when the full 2.5*RTT transfer mechanism is used. ===New data structures=== Several new data structures are added to the P2P network to relay compact blocks: PrefilledTransaction, HeaderAndShortIDs, BlockTransactionsRequest, and BlockTransactions. For the purposes of this section, CompactSize refers to the variable-length integer encoding used across the existing P2P protocol to encode array lengths, among other things, in 1, 3, 5 or 9 bytes. Only CompactSize encodings which are minimally-encoded (ie the shortest length possible) are used by this spec. Any other CompactSize encodings are left with undefined behavior. Several uses of CompactSize below are "differentially encoded". For these, instead of using raw indexes, the number encoded is the difference between the current index and the previous index, minus one. For example, a first index of 0 implies a real index of 0, a second index of 0 thereafter refers to a real index of 1, etc. ====PrefilledTransaction==== A PrefilledTransaction structure is used in HeaderAndShortIDs to provide a list of a few transactions explicitly. {| |Field Name||Type||Size||Encoding||Purpose |- |index||CompactSize||1, 3 bytes||Compact Size, differentially encoded since the last PrefilledTransaction in a list||The index into the block at which this transaction is |- |tx||Transaction||variable||As encoded in "tx" messages sent in response to getdata MSG_TX||The transaction which is in the block at index index. |} ====HeaderAndShortIDs==== A HeaderAndShortIDs structure is used to relay a block header, the short transactions IDs used for matching already-available transactions, and a select few transactions which we expect a peer may be missing. {| |Field Name||Type||Size||Encoding||Purpose |- |header||Block header||80 bytes||First 80 bytes of the block as defined by the encoding used by "block" messages||The header of the block being provided |- |nonce||uint64_t||8 bytes||Little Endian||A nonce for use in short transaction ID calculations |- |shortids_length||CompactSize||1 or 3 bytes||As used to encode array lengths elsewhere||||The number of short transaction IDs in shortids (ie block tx count - prefilledtxn_length) |- |shortids||List of 6-byte integers||6*shortids_length bytes||Little Endian||The short transaction IDs calculated from the transactions which were not provided explicitly in prefilledtxn |- |prefilledtxn_length||CompactSize||1 or 3 bytes||As used to encode array lengths elsewhere||||The number of prefilled transactions in prefilledtxn (ie block tx count - shortids_length) |- |prefilledtxn||List of PrefilledTransactions||variable size*prefilledtxn_length||As defined by PrefilledTransaction definition, above||Used to provide the coinbase transaction and a select few which we expect a peer may be missing |} ====BlockTransactionsRequest==== A BlockTransactionsRequest structure is used to list transaction indexes in a block being requested. {| |Field Name||Type||Size||Encoding||Purpose |- |blockhash||Binary blob||32 bytes||The output from a double-SHA256 of the block header, as used elsewhere||The blockhash of the block which the transactions being requested are in |- |indexes_length||CompactSize||1 or 3 bytes||As used to encode array lengths elsewhere||||The number of transactions being requested |- |indexes||List of CompactSizes||1 or 3 bytes*indexes_length||Differentially encoded||The indexes of the transactions being requested in the block |} ====BlockTransactions==== A BlockTransactions structure is used to provide some of the transactions in a block, as requested. {| |Field Name||Type||Size||Encoding||Purpose |- |blockhash||Binary blob||32 bytes||The output from a double-SHA256 of the block header, as used elsewhere||The blockhash of the block which the transactions being provided are in |- |transactions_length||CompactSize||1 or 3 bytes||As used to encode array lengths elsewhere||||The number of transactions provided |- |transactions||List of Transactions||variable||As encoded in "tx" messages in response to getdata MSG_TX||The transactions provided |} ====Short transaction IDs==== Short transaction IDs are used to represent a transaction without sending a full 256-bit hash. They are calculated by: # single-SHA256 hashing the block header with the nonce appended (in little-endian) # Running SipHash-2-4 with the input being the transaction ID and the keys (k0/k1) set to the first two little-endian 64-bit integers from the above hash, respectively. # Dropping the 2 most significant bytes from the SipHash output to make it 6 bytes. ===New messages=== A new inv type (MSG_CMPCT_BLOCK == 4) and several new protocol messages are added: sendcmpct, cmpctblock, getblocktxn, and blocktxn. ====sendcmpct==== # The sendcmpct message is defined as a message containing a 1-byte integer followed by a 8-byte integer where pchCommand == "sendcmpct". # The first integer SHALL be interpreted as a boolean (and MUST have a value of either 1 or 0) # The second integer SHALL be interpreted as a little-endian version number. Nodes sending a sendcmpct message MUST currently set this value to 1. # Upon receipt of a "sendcmpct" message with the first and second integers set to 1, the node SHOULD announce new blocks by sending a cmpctblock message. # Upon receipt of a "sendcmpct" message with the first integer set to 0, the node SHOULD NOT announce new blocks by sending a cmpctblock message, but SHOULD announce new blocks by sending invs or headers, as defined by BIP130. # Upon receipt of a "sendcmpct" message with the second integer set to something other than 1, nodes MUST treat the peer as if they had not received the message (as it indicates the peer will provide an unexpected encoding in cmpctblock, and/or other, messages). This allows future versions to send duplicate sendcmpct messages with different versions as a part of a version handshake for future versions. See Protocol Versioning section, below, for more info on the specifics of the version-negotiation mechanics. # Nodes SHOULD check for a protocol version of >= 70014 before sending sendcmpct messages. # Nodes MUST NOT send a request for a MSG_CMPCT_BLOCK object to a peer before having received a sendcmpct message from that peer. # Nodes MUST NOT request a MSG_CMPCT_BLOCK object before having sent all sendcmpct messages to that peer which they intend to send, as the peer cannot know what version protocol to use in the response. ====MSG_CMPCT_BLOCK==== # getdata messages may now contain requests for MSG_CMPCT_BLOCK objects. # Upon receipt of a getdata containing a request for a MSG_CMPCT_BLOCK object with the hash of a block which was recently announced and is close to the tip of the best chain of the receiver and after having sent the requesting peer a sendcmpct message, nodes MUST respond with a cmpctblock message containing appropriate data representing the block being requested. # Upon receipt of a getdata containing a request for a MSG_CMPCT_BLOCK object for which a cmpctblock message is not sent in response, a block message containing the requested block in non-compact form MUST be sent. # MSG_CMPCT_BLOCK inv objects MUST NOT appear anywhere except for in getdata messages. ====cmpctblock==== # The cmpctblock message is defined as a message containing a serialized HeaderAndShortIDs message and pchCommand == "cmpctblock". # Upon receipt of a cmpctblock message after sending a sendcmpct message, nodes SHOULD calculate the short transaction ID for each unconfirmed transaction they have available (ie in their mempool) and compare each to each short transaction ID in the cmpctblock message. # After finding already-available transactions, nodes which do not have all transactions available to reconstruct the full block SHOULD request the missing transactions using a getblocktxn message. # A node MUST NOT send a cmpctblock message unless they are able to respond to a getblocktxn message which requests every transaction in the block. # A node MUST NOT send a cmpctblock message without having validated that the header properly commits to each transaction in the block, and properly builds on top of the existing, fully-validated chain with a valid proof-of-work either as a part of the current most-work valid chain, or building directly on top of it. A node MAY send a cmpctblock before validating that each transaction in the block validly spends existing UTXO set entries. ====getblocktxn==== # The getblocktxn message is defined as a message containing a serialized BlockTransactionsRequest message and pchCommand == "getblocktxn". # Upon receipt of a properly-formatted getblocktxn message, nodes which recently provided the sender of such a message a cmpctblock for the block hash identified in this message MUST respond with either an appropriate blocktxn message, or a full block message. A blocktxn response MUST contain exactly and only each transaction which is present in the appropriate block at the index specified in the getblocktxn indexes list, in the order requested. ====blocktxn==== # The blocktxn message is defined as a message containing a serialized BlockTransactions message and pchCommand == "blocktxn". # Upon receipt of a properly-formatted requested blocktxn message, nodes SHOULD attempt to reconstruct the full block by: ## Taking the prefilledtxn transactions from the original cmpctblock and placing them in the marked positions. ## For each short transaction ID from the original cmpctblock, in order, find the corresponding transaction either from the blocktxn message or from other sources and place it in the first available position in the block. # Once the block has been reconstructed, it shall be processed as normal, keeping in mind that short transaction IDs are expected to occasionally collide, and that nodes MUST NOT be penalized for such collisions, wherever they appear. ==Protocol Versioning== # The protocol version negotiation allows two nodes to agree on the versions of compact blocks which they will exchange. As it is only in a single field, it does not allow a node to support a specific version in only one direction (sending or receiving). # Upon connection establishment, a node SHOULD send a burst of sendcmpct messages containing every version of compact block encodings for which they are willing to support sending cmpctblock and blocktxn messages, and receiving getblocktxn messages. These messages SHOULD be ordered in the order of the priority which the node wishes to receive cmpctblock/blocktxn messages, with the highest-priority version sendcmpct message sent first. # The encoding version used to send a cmpctblock or blocktxn message or to receive a getblocktxn message MUST be the second integer (version number) in the first sendcmpct message received for which a sendcmpct message with the same version number was sent. # Nodes MUST NOT send a sendcmpct message which contains a version number other than the version number which has been negotiated for receiving cmpctblock/blocktxn messages after sending a request for a MSG_CMPCT_BLOCK object, sending a cmpctblock, getblocktxn, blocktxn, or pong message. # As a node must send all sendcmpct messages which contain a novel version announcement before any other compact block-related messages, it is possible to determine which version of compact blocks will be used for each object received. It is, however, not possible to know which version will be used to encode the response to a request for a compact block object before any MSG_CMPCT_BLOCK-containing getdata, cmpctblock, getblocktxn, blocktxn, or ping/pong messages have been exchanged. # Thus, if a node wishes to determine exactly which version of compact blocks will be used before requesting a compact block object, it must send all of its sendcmpct version announcements, followed by a ping, and wait for the pong response to ensure it has received all sendcmpctblock version announcement messages from the remote peer. Nodes can, obviously, however, determine that the version used will be at least a certain version (in their priority order) after having received a sendcmpct message from the remote peer containing that version as the second integer. ===Sample Version Implementation=== # By way of example, an implementation of the above protocol might look like the following. # Upon exchanging version/verack messages, a node immediately sends its list of sendcmpct announcements to the other side, with the version which it wants to receive sent first. # Upon receiving the first sendcmpct announcement with a protocol version which is understood from the remote peer, a node will "lock in" the compact block encoding version which will be used to encode compact blocks to that peer. # The node then sets the current receive-protocol-version in use on the connection to that version, and uses it to decode new compact block messages. # Upon receiving subsequent sendcmpct announcements with a protocol version which is understood from the remote peer (ie a version which has been announced using a sendcmpct in the other direction), a node will check if that protocol version is higher-receive-priority than the current receive-protocol-version in use on the connection, and switch to that version for decoding new compact block messages received. # A node might wish to keep a flag for each peer which indicates compact block version negotiation is complete, which can be set upon receiving any compact block-related, or pong message. # The above implementation requires only a compile-time list of supported versions in some static priority order, two version fields per peer, and an optional negotiation-complete boolean per-peer. ==Specification for version 2== Compact blocks version 2 is almost identical to version 1, but supports segregated witness transactions (BIP 141 and BIP 144). The changes are: # The second integer (version number) inside sendcmpct is 2 instead of 1 (see Protocol Versioning section, above). # Transactions inside cmpctblock messages (both those used as direct announcement and those in response to getdata) and in blocktxn should include witness data, using the same format as responses to getdata MSG_WITNESS_TX, specified in BIP144. # Short transaction IDs sent to us in cmpctblock messages, and sent by us in getblocktxn messages, are computed using the same process as in version 1, but using the wtxid as defined in BIP 141 instead of the txid. Note that, though a node normally SHOULD, if a node does not include (ie must then include the short ID for) the coinbase transaction, it must be computed by encoding the transaction in witness format as defined by BIP 141. # Upon receipt of a getdata containing a request for a MSG_CMPCT_BLOCK object for which a cmpctblock message is not sent in response, the block message containing the requested block in non-compact form MUST be encoded with witnesses (as is sent in reply to a MSG_WITNESS_BLOCK getdata) if the protocol version used to encode the cmpctblock message would have been 2, and encoded without witnesses (as is sent in response to a MSG_BLOCK getdata) if the protocol version used to encode the cmpctblock message would have been 1. ==Implementation Notes== # For nodes which have sufficient inbound bandwidth, sending a sendcmpct message with the first integer set to 1 to up to 3 peers is RECOMMENDED. If possible, it is RECOMMENDED that those peers be selected based on their past performance in providing blocks quickly (eg the three peers which provided the highest number of the recent N blocks the quickest), allowing nodes to receive blocks which come from those peers in only 0.5*RTT. # Nodes MUST NOT send such sendcmpct messages to more than three peers, as it encourages wasting outbound bandwidth across the network. # All nodes SHOULD send a sendcmpct message to all appropriate peers. This will reduce their outbound bandwidth usage by allowing their peers to request compact blocks instead of full blocks. # Nodes with limited inbound bandwidth SHOULD request blocks using MSG_CMPCT_BLOCK/getblocktxn requests, when possible. While this increases worst-case message round-trips, it is expected to reduce overall transfer latency as TCP is more likely to exhibit poor throughput on low-bandwidth nodes. # Nodes sending cmpctblock messages SHOULD limit prefilledtxn to 10KB of transactions. When in doubt, nodes SHOULD only include the coinbase transaction in prefilledtxn. # Nodes MAY pick one nonce per block they wish to send, and only build a cmpctblock message once for all peers which they wish to send a given block to. Nodes SHOULD NOT use the same nonce across multiple different blocks. # Nodes MAY impose additional requirements on when they announce new blocks by sending cmpctblock messages. For example, nodes with limited outbound bandwidth MAY choose to announce new blocks using inv/header messages (as per BIP130) to conserve outbound bandwidth. # Note that the MSG_CMPCT_BLOCK section does not require that nodes respond to MSG_CMPCT_BLOCK getdata requests for blocks which they did not recently announce. This allows nodes to calculate cmpctblock messages at announce-time instead of at request-time. Blocks which are requested with a MSG_CMPCT_BLOCK getdata, but which are not responded to with a cmpctblock message MUST be responded to with a block message, allowing nodes to request all blocks using MSG_CMPCT_BLOCK getdatas and rely on their peer to pick an appropriate response. # While the current version sends transactions with the same encodings as are used in tx messages and elsewhere in the protocol, the version field in sendcmpct is intended to allow this to change in the future. For this reason, it is recommended that the code used to decode PrefilledTransaction and BlockTransactions messages be prepared to take a different transaction encoding, if and when the version field in sendcmpct changes in a future BIP. # Any undefined behavior in this spec may cause failure to transfer block to, peer disconnection by, or self-destruction by the receiving node. A node receiving non-minimally-encoded CompactSize encodings should make a best-effort to eat the sender's cat. ===Pre-Validation Relay and Consistency Considerations=== # As high-bandwidth mode permits relaying of CMPCTBLOCK messages prior to full validation (requiring only that the block header is valid before relay), nodes SHOULD NOT ban a peer for announcing a new block with a CMPCTBLOCK message that is invalid, but has a valid header. For avoidance of doubt, nodes SHOULD bump their peer-to-peer protocol version to 70015 or higher to signal that they will not ban or punish a peer for announcing compact blocks prior to full validation, and nodes SHOULD NOT announce a CMPCTBLOCK to a peer with a version number below 70015 before fully validating the block. # SPV nodes which implement this spec must consider the implications of accepting blocks which were not validated by the node which provided them. Especially SPV nodes which allow users to select a "trusted full node" to sync from may wish to avoid implementing this spec in high-bandwidth mode. # Note that this spec does not change the requirement that nodes only relay information about blocks which they have fully validated in response to GETDATA/GETHEADERS/GETBLOCKS/etc requests. Nodes which announce using CMPCTBLOCK message and then receive a request for associated block data SHOULD ensure that messages do not go unresponded to, and that the appropriate data is provided after the block has been validated, subject to standard message-response ordering requirements. Note that no requirement is added that the node respond to the request with the new block included in eg GETHEADERS or GETBLOCKS messages, but the node SHOULD re-announce the block using the associated announcement methods after validation has completed if it is not included in the original response. On the other hand, nodes SHOULD delay responding to GETDATA requests for the block until validation has completed, stalling all message processing for the associated peer. REJECT messages are not considered "responses" for the purpose of this section. # As a result of the above requirements, implementers may wish to consider the potential for the introduction of delays in responses while remote peers validate blocks, avoiding delay-causing requests where possible. ==Justification== ====Protocol design==== There have been many proposals to save wire bytes when relaying blocks. Many of them have a two-fold goal of reducing block relay time and thus rely on the use of significant processing power in order to avoid introducing additional worst-case RTTs. Because this work is not focused primarily on reducing block relay time, its design is much simpler (ie does not rely on set reconciliation protocols). Still, in testing at the time of writing, nodes are able to relay blocks without the extra getblocktxn/blocktxn RTT around 90% of the time. With a smart compact-block-announcement policy, it is thus expected that this work might allow blocks to be relayed between nodes in 0.5*RTT instead of 1.5*RTT at least 75% of the time. ====Short transaction ID calculation==== There are several design goals for the Short ID calculation: * '''Performance''' The sender needs to compute short IDs for all block transactions, and the receiver for all mempool transactions they are being compared to. As we're easily talking about several thousand transactions, sub-microsecond processing per-transactions is needed. * '''Space''' cmpctblock messages are never optional in this protocol, and contain a short ID for each non-prefilled transaction in the block. Thus, the size of short IDs is directly proportional to the maximum bandwidth savings possible. * '''Collision resistance''' It should be hard for network participants to create transactions that cause collisions. If an attacker were able to cause such collisions, filling mempools (and, thus, blocks) with them would cause poor network propagation of new (or non-attacker, in the case of a miner) blocks. SipHash is a secure, fast, and simple 64-bit MAC designed for network traffic authentication and collision-resistant hash tables. We truncate the output from SipHash-2-4 to 48 bits (see next section) in order to minimize space. The resulting 48-bit hash is certainly not large enough to avoid intentionally created individual collisions, but by using the block hash as a key to SipHash, an attacker cannot predict what keys will be used once their transactions are actually included in a relayed block. We mix in a per-connection 64-bit nonce to obtain independent short IDs on every connection, so that even block creators cannot control where collisions occur, and random collisions only ever affect a small number of connections at any given time. The mixing is done using SHA256(block_header || nonce), which is slow compared to SipHash, but only done once per block. It also adds the ability for nodes to choose the nonce in a better than random way to minimize collisions, though that is not necessary for correct behaviour. Conversely, nodes can also abuse this ability to increase their ability to introduce collisions in the blocks they relay themselves. However, they can already cause more problems by simply refusing to relay blocks. That is inevitable, and this design only seeks to prevent network-wide misbehavior. ====Random collision probability==== Thanks to the block-header-based SipHash keys, we can assume that the only collisions on links between honest nodes are random ones. For each of the ''t'' block transactions, the receiver will compare its received short ID with that of a set of ''m'' mempool transactions. We assume that each of those ''t'' has a chance ''r'' to be included in that set of ''m''. If we use ''B'' bits short IDs, for each comparison between a received short ID and a mempool transaction, there is a chance of ''P = 1 - 1 / 2^B'' that a mismatch is detected as such. When comparing a given block transaction to the whole set of mempool transactions, there are 5 cases to distinguish: # The receiver has exactly one match, which is the correct one. This has chance ''r * P^(m - 1)''. # The receiver has no matches. This has chance ''(1 - r) * P^m''. # The receiver has at least two matches, one of which is correct. This has chance ''r * (1 - P^(m - 1))''. # The receiver has at least two matches, both of which are incorrect. This has chance ''(1 - r) * (1 - P^m - m * (1 - P) * P^(m - 1))''. # The receiver has exactly one match, but an incorrect one. This has chance ''(1 - r) * m * (1 - P) * P^(m - 1)''. (note that these 5 numbers always add up to 100%) In case 1, we're good. In cases 2, 3, or 4, we request the full transaction because we know we're uncertain. Only in case 5, we fail to reconstruct. The chance that case 5 does not occur in any of the ''t'' transactions in a block is ''(1 - (1 - r) * m * (1 - P) * P^(m - 1))^t''. This expression is well approximated by ''1 - (1 - r) * m * (1 - P) * t'' = ''1 - (1 - r) * m * t / 2^B''. Thus, if we want only one in F block transmissions between honest nodes to fail under the conservative ''r = 0'' assumption, we need ''log2(F * m * t)'' bits hash functions. This means that ''B = 48'' bits short IDs suffice for blocks with up to ''t = 10000'' transactions, mempools up to ''m = 100000'' transactions, with failure to reconstruct at most one in ''F = 281474'' blocks. Since failure to reconstruct just means we fall back to normal inv/header based relay, it isn't necessary to avoid such failure completely. It just needs to be sufficiently rare they have a lower impact than random transmission failures (for example, network disconnection, node overloaded, ...). ====Separate version for segregated witness==== The changes to transaction and block relay in BIP 144 introduce separate MSG_FILTERED_ versions of messages in getdata, allowing a receiver to choose individually where witness data is wanted. This method is not useful for compact blocks because `cmpctblock` blocks can be sent unsolicitedly in high-bandwidth mode, so we need to negotiate at least whether those should include witness data up front. There is little use for a validating node that only sometimes processes witness data, so we may as well use that negotiation for everything and turn it into a separate protocol version. We also need a means to distinguish different versions of the same transaction with different witnesses for correct reconstruction, so this also forces us to use wtxids instead of txids for short IDs everywhere in that case. ==Backward compatibility== Older clients remain fully compatible and interoperable after this change. ==Implementation== https://github.com/bitcoin/bitcoin/pull/8068 for version 1. https://github.com/bitcoin/bitcoin/pull/8393 for version 2. ==Acknowledgements== Thanks to Gregory Maxwell for the initial suggestion as well as a lot of back-and-forth design and significant testing. Thanks to Nicolas Dorier for the protocol flow diagram. ==Copyright== This document is placed in the public domain. ================================================ FILE: bip-0154.mediawiki ================================================
  BIP: 154
  Layer: Peer Services
  Title: Rate Limiting via peer specified challenges
  Authors: Karl-Johan Alm 
  Status: Closed
  Type: Specification
  Assigned: 2017-04-12
  License: BSD-2-Clause
==Abstract== An anti-DoS system which provides additional service for peers which perform proof of work. ==Definitions== * '''POW''' : a proof of work using some arbitrary algorithm, such as SHA256 * '''challenge''' : a problem in the form of a POW specification and other data * '''solution''' : a set of inputs which solve a given challenge * '''free connection slot''' : an inbound connection slot that does not require POW * '''POW connection slot''' : an inbound connection slot that requires POW * '''SPH''' : Special Purpose Hardware, such as an ASIC chip * '''GPH''' : General Purpose Hardware, such as a desktop computer * '''Work''' : A measurement of optimized average resources (clock cycles, memory, ...) required to perform a single attempt at solving a given POW algorithm on GPH ==Motivation== The Bitcoin network has a maximum number of inbound and outbound connections (125). It is trivial and relatively cheap to flood the network with connections via dummy nodes. Such an attack would result in (1) nodes evicting some other nodes in order to facilitate the new connection, and (2) nodes' ability to connect to each other being severely hampered. In this state, the network is vulnerable to e.g. a Sybil attack. While the network is under pressure as in the above case, nodes could allow incoming connections anyway by requiring that the incoming peer performs some form of proof of work, to prove that they are not simply spamming the network. This would severely ramp up the costs of a Sybil attack, as the attacker would now have to perform proof of work for each node, beyond the free slots. However, using the "standard" double-SHA256 POW algorithm in use by Bitcoin nodes to generate blocks means attackers can use special-purpose hardware to greatly accelerate the POW solving process. To counter this, the proof weight would have to be raised, but this would mean standard nodes would need to solve unacceptably costly challenges for simple operation. Therefore, a different proof of work which is arguably less sensitive to special-purpose hardware implementations is introduced. As this is not consensus sensitive, additional POW algorithms may be added in the future. ==Specification== A peer that supports Proof of Work Rate Limiting defines two maximums: * max connections, from which the maximum inbound connections is calculated as nMaxConnections - (nMaxOutbound + nMaxFeeler) * POW connection slots, which define how many of the above inbound connections require a POW challenge The peer must interpret two new network peer message types, challenge and solution. In addition, the network handshake sequence must be altered slightly to facilitate the exchange of challenges and/or solutions: * when a node connects, it may send a solution message prior to the version * if it does, and ** the solution satisfies the local node, it is given a connection, but if ** the solution does not satisfy the local node (unknown, wrong, ...), a new challenge is sent and the connection is closed * if it does not, and it is marked as needing to do POW, a challenge is sent and the connection is closed This means nodes will be disconnected after receiving the challenge. It is then up to the individual nodes whether they solve the challenge and reconnect, or discard it and find a different peer (or wait for the peer to have an open free slot). ===POW Identifiers=== There are two POW identifiers currently. When a new identifier is introduced, it should be added with an increment of 1 to the last identifier in the list. When an identifier is deprecated, its status should be changed to Deprecated but it should retain its place in the list indefinitely. {|class="wikitable" ! ID !! Algorithm Name !! Work !! Param size !! Solution size !! Provably Secure !! SPH Resistance !! Status |- | 1 || sha256 || 11k cycles || 11+ bytes || 0, 4 or 8 bytes || Yes || Low || Active |- | 2 || cuckoo-cycle || ss 28: 150G cycles / ~48M RAM || 6+ bytes || 168 bytes || No || High || Active |} ====sha256==== Properties: {|class="wikitable" ! Property !! Value |- | Solution probability || sum((1/2)^i*(1-targetBE[i])) |} Challenge format: {|class="wikitable" ! Range !! Field Name !! Data Type !! Description |- | 0 || config_length || varint || Length of configuration part; always 9 |- | 1..4 || target || uint32 || Difficulty target, in the form of a compact size (like nBits in blocks). |- | 5 || nonce_size || uint8 || Size of nonce in bytes; must be 0 (no nonce), 4 (uint32) or 8 (uint64) |- | 6..9 || nonce_offset || uint32 || Location of nonce value in target |- | 10.. || payload_length || varint || Length of the input data |- | .. || payload || byte array || Input data |} Solution format: {|class="wikitable" ! Range !! Field Name !! Data Type !! Description |- | 0.. || nonce || uint32/64, or data || Nonce value that satisfies challenge; for zero-byte nonces, this is variable data that is appended to the challenge payload before hashing |} Note: SHA256 works in two "modes". # One is where the task is to insert a nonce into an existing data block so that the hash of the data block matches a given target; this is the conventional block proof of work behavior. # The other is where the whole or parts of the data chunk are given as input (a "big nonce"). In this case, the internal nonce size is zero bytes, and the task is simply to check whether the hash of the data matches the target. If it does not, there is no way to find a solution except by getting different input from the generator (a successor algorithm). This mode is used when SHA256 is a predecessor to another algorithm. Additional notes: * The initial nonce value (when present) for finding a suitable digest should be randomized, or a challenger may deliberately pick a challenge with "poor" outcomes to fool a node into spending more than predicted time solving. ====cuckoo-cycle==== Properties: {|class="wikitable" ! Property !! Value |- | Solution probability || ~1.0 for sizeshift=28, proofsize-min:-max=12:228 |} Challenge format: {|class="wikitable" ! Range !! Field Name !! Data Type !! Description |- | 0 || config_length || varint || Length of configuration part; always 5 |- | 1 || sizeshift || uint8 || Size shift; must be equal to 28, but may be variable in the future |- | 2..3 || proofsize-min || uint16 || Minimum number of edges in cycle; must be even and greater than or equal to 12 (recommended: 12) |- | 4..5 || proofsize-max || uint16 || Maximum number of edges in cycle; must be even, greater than or equal to proofsize-min, and smaller than or equal to 254 (recommended: 228) |- | 6 || payload_length || varint || Length of the input data; must be 76, but may be variable in the future |- | 7.. || payload || byte array || Input data |} Solution format: {|class="wikitable" ! Range !! Field Name !! Data Type !! Description |- | 0..3 || nonce || uint32 || Nonce which is appended to challenge payload to form solution graph |- | 4..171 || edges || uint32 array || 42 values which identify each of the 42 edges in the cycle |} Additional notes: * The initial nonce value used for finding a graph with a suitable solution should be randomized, or a challenger may deliberately pick a challenge with "poor" outcomes to fool a node into spending more than predicted time solving. * Further information on the recommended challenge parameters can be found here: https://web.archive.org/web/20230207054058/http://bc-2.jp/cuckoo-profile.pdf ===Purpose Identifiers=== There is only one Purpose Identifier currently. In the future, more Purpose Identifiers could be added for at-DoS-risk operations, such as bloom filters. When a new identifier is introduced, it should be added with an increment of 1 to the last identifier in the list. When an identifier is deprecated, its status should be changed to Deprecated but it should retain its place in the list indefinitely. {|class="wikitable" ! ID !! Purpose Name !! Description !! Status |- | 1 || connect || Establish peer to peer connection || Active |} ===Challenges=== Challenges consist of one or several chained POW identifiers with accompanying parameters, as well as indicators for the purpose of the challenge, and a signature that lets the node verify the challenge authenticity. After creating a challenge, the node signs it, delivers it to the peer, then discards it. When a node provides a solution to a challenge, the node verifies the signature and adds the challenge hash to a list of solved challenges along with its expiration time. This list is pruned on each insertion, removing any expired challenges. If nodes needed to keep track of unsolved challenges, an attacker could hypothetically swarm a node, causing a DoS by having it generate so many challenges that it runs out of memory and crashes. By signing and discarding challenges, a node only has to retain challenges that were solved, and which have not yet expired, effectively DoS- protecting the node via the challenges themselves. ===The challenge message type=== A challenge consists of four parts: the POW specification, a purpose identifier, an expiration date, and a signature. The POW specification contains a list of tuples containing a POW identifier and corresponding POW parameters. * Each POW identifier specifies a POW algorithm (see POW Identifiers) * The POW parameters define the inputs and requirements of the POW algorithm * The purpose identifier specifies the purpose of the challenge (see Purpose Identifiers) * The expiration date is a UNIX timestamp indicating when the challenge expires * The signed content should contain a signature of the hash SHA256(SHA256(pow-count || pow-id || pow-params || ... || purpose-id || expiration)), i.e. the hash of the entire challenge except for the signature length and data. {|class="wikitable" ! Field Size !! Description !! Data type !! Description |- | 1 byte || pow-count || uint8 || Number of POW algorithms in the range [1..255] |- | 4 bytes || pow-id || uint32 || The POW algorithm to solve the problem with |- | ? || pow-params || ? || The POW parameters and payload |- | ... || ... || ... || pow-id and pow-params for algorithms 2 and beyond |- | 4 bytes || purpose-id || uint32 || The purpose of the challenge |- | 8 bytes || expiration || int64 || Expiration UNIX timestamp |- | ? || sign-len || varint || The length of the signature |- | ? || sign || byte array || The signature data |} For POW specifications with a pow-count > 1, the output of the succeeding POW algorithm will be appended to the input of the predecessor for all POW algorithms except the last one. Normally mid-layer (all but the last) POW algorithms have a zero-length input. Example implementing sha256(cuckoo-cycle): {|class="wikitable" ! Range !! Field Name !! Value !! Comment |- | 0 || pow-count || 2 || Two POW algorithms |- | 1..4 || pow-id || 1 || sha256 |- | 5 || pow-params (config_length) || 9 || |- | 6..9 || pow-params (target) || 0x207fffff || Resulting hash must be <= the compact hash 0x207fffff* |- | 10 || pow-params (nonce_size) || 0 || No nonce |- | 11..14 || pow-params (nonce_offset) || 0 || -- |- | 15..18 || pow-params (payload_length) || 0 || 0 byte input (turns into 32 byte input from successor) |- | 19..22 || pow-id || 2 || cuckoo-cycle |- | 23 || pow-params (config_length) || 8 || |- | 24 || pow-params (sizeshift) || 28 |- | 25..26 || pow-params (proofsize-min) || 12 || |- | 27..28 || pow-params (proofsize-max) || 228 || |- | 29 || pow-params (payload_length) || 76 || 76 byte input |- | 30..105 || pow-params || (random data) || A randomized challenge of 76 bytes |- | 106..109 || purpose-id || 1 || Purpose is a peer-to-peer connection |- | 110..117 || expiration || 1491285696 || Expiration is April 4 2017, 15:01:36 (JST) |- | 118 || sign-len || 71 || 71 byte signature |- | 119..189 || sign || (signature) || Signature of above challenge |} (* Compact 0x207fffff = 0x7fffff0000000000000000000000000000000000000000000000000000000000.) The above should be interpreted as SHA256(cuckoo-cycle(random data || nonce)) < 0x7fffff0000000000000000000000000000000000000000000000000000000000. * Run cuckoo-cycle on random data || nonce; increment nonce until solution is found, then ** Run SHA256 on 32 byte digest from above; if less than 0x7fffff0000000000000000000000000000000000000000000000000000000000, *** Mark solved. * Otherwise loop back and increase nonce and continue finding solutions ===The solution message type=== A solution consists of two parts: the entire challenge, and solution parameters: * The challenge must match the given challenge up to and including the signature bytes * The solution parameters must form a valid solution to each POW step in the challenge {|class="wikitable" ! Field Size !! Description !! Data type !! Description |- | 1 byte || pow-count || uint8 || Number of POW algorithms in the range [1..255] |- | 4 bytes || pow-id || uint32 || The POW algorithm used to solve the problem |- | ? || pow-params || ? || The input to the POW solver for the above algorithm |- | ... || ... || ... || pow-id and pow-params for algorithms 2 and beyond |- | 4 bytes || purpose-id || uint32 || The purpose of the challenge |- | 8 bytes || expiration || int64 || Expiration UNIX timestamp |- | ? || sign-len || varint || The length of the signature |- | ? || sign || byte array || The signature data |- | ? || solution || ? || The solution to the challenge |} Note that the solution contains the parameters for the last algorithm only. For each algorithm except the last one, the input is derived from the output of the successor. Example solution: {|class="wikitable" ! Range !! Name !! Value !! Description |- | 0 || length || 4 || The input to the innermost POW is 4 bytes in length |- | 1..4 || nonce32 || 0x12345 || The nonce used as input is 0x12345 |} The above example will provide a single nonce for the inner POW. For the SHA256(SHA256(challenge data || nonce32)) case, the solution would claim that SHA256(SHA256(challenge data || 0x00012345)) solves the challenge. ==Signing and Verifying Challenges== Below is a suggestion for how to sign a challenge. The implementation generates a new, random key-pair at launch and uses that to sign all challenges until the node is shutdown. ===Signing a Challenge=== # (first time) Create a new random key-pair key and pubkey and keep these around until shutdown # (second+ time) Fetch key created above # Create a double-SHA256 sighash of the challenge in serialized form up until and including the expiration bytes # Create a signature sign of sighash using key # Append varint(len(sign)) and sign to challenge ===Verifying a Challenge=== # Fetch pubkey and declare failure if not defined (that means we never issued a challenge) # Create a double-SHA256 sighash of the challenge provided with the solution up until and including the expiration bytes # Verify sighash is not known, and add it to known hashes along with its expiration date for pruning purposes # Set sign to the signature included in the challenge # Verify the signature sign using pubkey and sighash # Check that the solution solves the challenge Note that a list of known hashes should be kept and pruned of expired challenges on verification. Otherwise nodes may reuse the same solution repeatedly up until its expiration. ==Difficulty and Cost== ===Estimating Challenge Cost=== Nodes need to be able to make a judgement call on whether solving a given challenge is worth their efforts. If a challenge is expected to take so much time that it would expire before being solved (on average), it should be immediately discarded. Beyond this, a threshold should be established for nodes based on their "value" to the node, which is inversely proportional to the current number of connections as a function of uptime, with arbitrary modifiers (a whitelisted node or a node added via -addnode has a much higher threshold). It is hard to obtain an accurate value for cycles_per_second, and as such a fixed value of 1700000000=1.7e9 may be used. Given a threshold t, calculate the estimated work required to solve the challenge as follows: # Define p(alg) as the probability that an attempt at finding a solution given the algorithm alg succeeds # Define w(alg) as the work parameter of the algorithm alg. # Let Wc ← 0, Wm ← 1, Wi ← 1 # For each proof of work pow in the POW specification: ## Let p ← p(pow), w ← w(pow) ## Update Wc ← Wc + w_cycles, Wi ← Wi * 1/p, Wm ← Wm + w_ram # Let eta ← (Wc * Wi) / cycles_per_second # If date() + eta >= expiration, discard challenge # If eta > t, discard challenge Example: SHA256(cuckoo-cycle(...)) < 0x7fffff0000000000000000000000000000000000000000000000000000000000 # p(cuckoo-cycle) = 1, p(sha256, 0x7fffff000...) ~= (1/2)^1 = 1/2 # w(cuckoo-cycle) = (1.5e11 cycles, 5e7 ram), w(sha256, 0x7fffff000...) = (11e3 cycles) # Wc = 0, Wm = 1, Wi = 1 ## p = p(cuckoo-cycle) = 1, w = w(cuckoo-cycle) = (1.5e11 cycles, 5e7 ram) ## Wc = 0 + 1.5e11 = 1.5e11, Wi = 1 * 1 = 1, Wm = 1 + 5e7 = 5e7 ## p = p(sha256) = 1/2, w = w(sha256) = (11e3 cycles) ## Wc = 1.5e11 + 11e3 ~= 1.5e11, Wi = 1 * 2 = 2, Wm = 5e7 + 0 = 5e7 # eta = (1.5e11 * 2) / cycles_per_second = 7.5e10 / 1.7e9 = 44.1 seconds TODO: Determine how memory impacts threshold. To avoid other nodes dropping our challenges due to early expiration, we use a fairly generous expiration based on the pressure value
expiration = date() + 600 * (1 + pressure)
which means the expiration is 10 minutes for the weakest challenge, and gradually rises to 20 minutes for the hardest one. ===Establishing Difficulty Parameters=== The difficulty setting for the network should change based on connection slot availability. The amount of pressure on the network in the sense of connection slot availability is proportional to the number of established connections over the number of total available connections. This can be locally approximated by a node to the number of local connections compared to the local connection maximum. In other words, the network pressure can be approximated by any node as connections / max and the difficulty can be based on e.g. (connections - free) / pow_slots. The challenge difficulty parameters can be set based on this, where 0.0 means "low pressure" and 1.0 means "maximum pressure". The GetPressure method below gives 0.0 at 67 connections (for a 50 POW slot set up), and hits the 1.0 mark at (nMaxConnections - nMaxOutbound - nMaxFeeler), incrementing by 0.02 for each new connection:
int nMaxInbound = nMaxConnections - (nMaxOutbound + nMaxFeeler + nPOWConnectionSlots);
return ((double)GetNodeCount(CONNECTIONS_ALL) - nMaxInbound) / nPOWConnectionSlots;
An example of difficulty for a SHA256(Cuckoo-Cycle) specification would be based on a desired probability of a random SHA256 digest matching a given target:
prob_target = 1 / (1 + pressure^2 * 15)
This would result in probability targets according to the table below, for varying pressures (where the pressure is in the range [0..1]): {|class="wikitable" ! pressure !! prob_target !! solution time sha256(cc) |- | 0.0 || 1.00 || 00:45 |- | 0.1 || 0.87 || 00:51 |- | 0.2 || 0.63 || 01:11 |- | 0.3 || 0.43 || 01:45 |- | 0.4 || 0.29 || 02:32 |- | 0.5 || 0.21 || 03:32 |- | 0.6 || 0.16 || 04:46 |- | 0.7 || 0.12 || 06:13 |- | 0.8 || 0.09 || 07:54 |- | 0.9 || 0.08 || 09:48 |- | 1.0 || 0.06 || 11:55 |- |} ==Cuckoo Cycle== Cuckoo Cycle[1] is a "graph-theoretic proof-of-work system, based on finding small cycles or other structures in large random graphs." It is memory hard, which greatly increases the complexity and cost of producing dedicated (special purpose) hardware, an ideal property for an anti-DoS system. The implementation specifics of the algorithm are beyond the scope of this BIP, but the github repository[2] has several reference implementations in various languages. ==Compatibility== This proposal is backward compatible. Non-supporting peers will ignore the challenge message and be disconnected, as if they hit the peer connection limit as normal. ==Reference implementation== https://github.com/kallewoof/bitcoin/pull/2 (https://github.com/kallewoof/bitcoin/tree/pow-connection-slots) ==References== * [1] Cuckoo Cycle https://github.com/tromp/cuckoo/blob/master/doc/cuckoo.pdf?raw=true * [2] Cuckoo Cycle github https://github.com/tromp/cuckoo ==Test vectors== ===Cuckoo-Cycle=== Cuckoo Cycle header (76 bytes):
00..1f   68a639cb 3deab5b6 23054d60 e7856037 8afa0f31 4f08dec1 6cc4ec4f d9bef1ff
20..3f   468af883 c6c9c3d5 4260087a 046d12a0 7cc3988f 9ff2957a 384de8ed db75b037
40..4b   798d1073 214b7ea6 954f1b3a
Example solution nonce: 0 (00000000) Solution edges (16 number of 32-bit unsigned integers, read horizontally from top left):
550b1100 0fc89a00 45034401 ddfce701 08da0e02 6ccc5703 06fe8404 1d3f8504
559e3e05 d41a9905 17075206 97cfa006 59e50d07 7bd71f07 13fe2607 14493007
===SHA256(Cuckoo-Cycle)=== SHA256 target: 0x205fffff Cuckoo Cycle header (76 bytes, same as above):
00..1f   68a639cb 3deab5b6 23054d60 e7856037 8afa0f31 4f08dec1 6cc4ec4f d9bef1ff
20..3f   468af883 c6c9c3d5 4260087a 046d12a0 7cc3988f 9ff2957a 384de8ed db75b037
40..4b   798d1073 214b7ea6 954f1b3a
Example solution nonce: 0 (00000000) SHA256 input (cuckoo-cycle nonce + solution):
00000000
550b1100 0fc89a00 45034401 ddfce701 08da0e02 6ccc5703 06fe8404 1d3f8504
559e3e05 d41a9905 17075206 97cfa006 59e50d07 7bd71f07 13fe2607 14493007
SHA256 hash: 262c8558c7c589b19b3d513abf5fcb15162745473e603f0146889ceff750bcc3 Must be less than: 5fffff0000000000000000000000000000000000000000000000000000000000 ===Serialized challenge example===
020100000009ffff5f2000000000000002000000051c0c00e4004c68a639cb3deab5b623054d60e7
8560378afa0f314f08dec16cc4ec4fd9bef1ff468af883c6c9c3d54260087a046d12a07cc3988f9f
f2957a384de8eddb75b037798d1073214b7ea6954f1b3a01000000a49d0659000000004730450221
0095fc5fafe2032097c4d12a8901401cda297aad614e16f23ec42d4b78955856c002206ab7ada4ac
8f6fa9d5bd7cd06f9ba89587a28e14cea14e7f8f8d5ab851541791
{|class="wikitable" ! Hex !! Description |- | 0x02 || Two proofs of work |- | 0x01000000 || Proof of work ID = 1 (SHA256) |- | 0x09 || Config is 9 bytes |- | 0xffff5f20 || SHA256: Compact target = 0x205fffff |- | 0x00 || SHA256: Nonce size is 0 bytes |- | 0x00000000 || SHA256: Nonce offset is 0 |- | 0x00 || Payload is 0 bytes |- | 0x02000000 || Proof of work ID = 2 (cuckoo-cycle) |- | 0x05 || Config is 5 bytes |- | 0x1c || Size shift is 28 |- | 0x0c00 || Proof size min is 12 |- | 0xe400 || Proof size max is 228 |- | 0x4c || Payload is 76 bytes |- | 0x68a639cb3deab5b623054d60e7856037 || Payload |- | 0x8afa0f314f08dec16cc4ec4fd9bef1ff |- | 0x468af883c6c9c3d54260087a046d12a0 |- | 0x7cc3988f9ff2957a384de8eddb75b037 |- | 0x798d1073214b7ea6954f1b3a |- | 0x01000000 || Purpose ID = 1 (PURPOSE_CONNECT) |- | 0xa49d065900000000 || UNIX timestamp 1493605796 |- | 0x47 || 71 byte signature |- | 0x304502210095fc5fafe2032097c4d12a || Signature data |- | 0x8901401cda297aad614e16f23ec42d4b |- | 0x78955856c002206ab7ada4ac8f6fa9d5 |- | 0xbd7cd06f9ba89587a28e14cea14e7f8f |- | 0x8d5ab851541791 |} ===Serialized solution example===
020100000009ffff5f2000000000000002000000051c0c00e4004c68a639cb3deab5b623054d60e7
8560378afa0f314f08dec16cc4ec4fd9bef1ff468af883c6c9c3d54260087a046d12a07cc3988f9f
f2957a384de8eddb75b037798d1073214b7ea6954f1b3a01000000a49d0659000000004730450221
0095fc5fafe2032097c4d12a8901401cda297aad614e16f23ec42d4b78955856c002206ab7ada4ac
8f6fa9d5bd7cd06f9ba89587a28e14cea14e7f8f8d5ab8515417914400000000550b11000fc89a00
45034401ddfce70108da0e026ccc570306fe84041d3f8504559e3e05d41a99051707520697cfa006
59e50d077bd71f0713fe260714493007
Note that the first 187 bytes are identical to the challenge above. {|class="wikitable" ! Hex !! Description |- | 0x0201..1791 || Challenge |- | 0x44 || Solution is 68 bytes long |- | 0x00000000 || The cuckoo cycle nonce is 0 |- | 0x550b11000fc89a0045034401ddfce701 || Cycle edges 0..3 |- | 0x08da0e026ccc570306fe84041d3f8504 || Cycle edges 4..7 |- | 0x559e3e05d41a99051707520697cfa006 || Cycle edges 8..11 |- | 0x59e50d077bd71f0713fe260714493007 || Cycle edges 12..15 |} ===Cuckoo-Cycle Example 2=== Cuckoo Cycle header (76 bytes):
00..1f   3c1e3ee5 c799b7e9 92bcccbb 8985979d cb8dd229 b8d0db06 e677d00b b3a43c88
20..3f   ef8596a7 7cbd1dda 23b0a0b8 4bdf6084 d7aa28dd bd5e91b5 11b3578c baf92707
40..4b   c940b051 a0759b3f 80c5fb65
Example solution nonce: 4 (04000000) Solution edges (22 number of 32-bit unsigned integers, read horizontally from top left):
5a013700 7074ce00 e3dbeb00 e88f7901 06d71d02 984d3d02 091b5002 378a8e02
90a6d202 b3c67003 757cb703 44d9cf03 297f2004 8e76a604 67e44a05 7b077405
634f8405 23e88c05 0d887606 109d3e07 c4bdcd07 3db2d407
===SHA256(Cuckoo-Cycle)=== SHA256 target: 0x2021642c Cuckoo Cycle header (76 bytes, same as above):
00..1f   3c1e3ee5 c799b7e9 92bcccbb 8985979d cb8dd229 b8d0db06 e677d00b b3a43c88
20..3f   ef8596a7 7cbd1dda 23b0a0b8 4bdf6084 d7aa28dd bd5e91b5 11b3578c baf92707
40..4b   c940b051 a0759b3f 80c5fb65
Example solution nonce: 4 (04000000) SHA256 input (cuckoo-cycle nonce + solution):
04000000
5a013700 7074ce00 e3dbeb00 e88f7901 06d71d02 984d3d02 091b5002 378a8e02
90a6d202 b3c67003 757cb703 44d9cf03 297f2004 8e76a604 67e44a05 7b077405
634f8405 23e88c05 0d887606 109d3e07 c4bdcd07 3db2d407
SHA256 hash: 08210561257e26776135ec1cb92cfe17f46803613c0bdc02043e5545b18556ce Must be less than: 21642c0000000000000000000000000000000000000000000000000000000000 ===Serialized challenge example===
0201000000092c64212000000000000002000000051c0c00e4004c3c1e3ee5c799b7e992bcccbb89
85979dcb8dd229b8d0db06e677d00bb3a43c88ef8596a77cbd1dda23b0a0b84bdf6084d7aa28ddbd
5e91b511b3578cbaf92707c940b051a0759b3f80c5fb650100000024aa0659000000004630440220
0edfb5c4812a31d84cbbd4b24e631795435a0d16b57d37ef773735b8a87caa8a0220631d0b78b7f1
d29c9e54a76f3457ff1a2ee19490ff027c528a896f4bf6aff577
{|class="wikitable" ! Hex !! Description |- | 0x02 || Two proofs of work |- | 0x01000000 || Proof of work ID = 1 (SHA256) |- | 0x09 || Config is 9 bytes |- | 0x2c642120 || SHA256: Compact target = 0x2021642c |- | 0x00 || SHA256: Nonce size is 0 bytes |- | 0x00000000 || SHA256: Nonce offset is 0 |- | 0x00 || Payload is 0 bytes |- | 0x02000000 || Proof of work ID = 2 (cuckoo-cycle) |- | 0x05 || Config is 5 bytes |- | 0x1c || Size shift is 28 |- | 0x0c00 || Proof size min is 12 |- | 0xe400 || Proof size max is 228 |- | 0x4c || Payload is 76 bytes |- | 0x3c1e3ee5c799b7e992bcccbb8985979d || Payload |- | 0xcb8dd229b8d0db06e677d00bb3a43c88 |- | 0xef8596a77cbd1dda23b0a0b84bdf6084 |- | 0xd7aa28ddbd5e91b511b3578cbaf92707 |- | 0xc940b051a0759b3f80c5fb65 |- | 0x01000000 || Purpose ID = 1 (PURPOSE_CONNECT) |- | 0x24aa065900000000 || UNIX timestamp 1493608996 |- | 0x46 || 70 byte signature |- | 0x304402200edfb5c4812a31d84cbbd4b2 || Signature data |- | 0x4e631795435a0d16b57d37ef773735b8 |- | 0xa87caa8a0220631d0b78b7f1d29c9e54 |- | 0xa76f3457ff1a2ee19490ff027c528a89 |- | 0x6f4bf6aff577 |} ===Serialized solution example===
0201000000092c64212000000000000002000000051c0c00e4004c3c1e3ee5c799b7e992bcccbb89
85979dcb8dd229b8d0db06e677d00bb3a43c88ef8596a77cbd1dda23b0a0b84bdf6084d7aa28ddbd
5e91b511b3578cbaf92707c940b051a0759b3f80c5fb650100000024aa0659000000004630440220
0edfb5c4812a31d84cbbd4b24e631795435a0d16b57d37ef773735b8a87caa8a0220631d0b78b7f1
d29c9e54a76f3457ff1a2ee19490ff027c528a896f4bf6aff5775c040000005a0137007074ce00e3
dbeb00e88f790106d71d02984d3d02091b5002378a8e0290a6d202b3c67003757cb70344d9cf0329
7f20048e76a60467e44a057b077405634f840523e88c050d887606109d3e07c4bdcd073db2d407
Note that the first 186 bytes are identical to the challenge above. {|class="wikitable" ! Hex !! Description |- | 0x0201..f577 || Challenge |- | 0x5c || Solution is 92 bytes long |- | 0x04000000 || The cuckoo cycle nonce is 4 |- | 0x5a0137007074ce00e3dbeb00e88f7901 || Cycle edges 0..3 |- | 0x06d71d02984d3d02091b5002378a8e02 || Cycle edges 4..7 |- | 0x90a6d202b3c67003757cb70344d9cf03 || Cycle edges 8..11 |- | 0x297f20048e76a60467e44a057b077405 || Cycle edges 12..15 |- | 0x634f840523e88c050d887606109d3e07 || Cycle edges 16..19 |- | 0xc4bdcd073db2d407 || Cycle edges 20..21 |} ==Copyright== This BIP is licensed under the BSD 2-clause license. ================================================ FILE: bip-0155.mediawiki ================================================
  BIP: 155
  Layer: Peer Services
  Title: addrv2 message
  Authors: Wladimir J. van der Laan 
  Status: Deployed
  Type: Specification
  Assigned: 2019-02-27
  License: BSD-2-Clause
  Version: 2.0.0
==Introduction== ===Abstract=== This document proposes a new P2P message to gossip longer node addresses over the P2P network. This is required to support new-generation Onion addresses, I2P, and potentially other networks that have longer endpoint addresses than fit in the 128 bits of the current addr message. ===Copyright=== This BIP is licensed under the 2-clause BSD license. ===Motivation=== Tor v3 hidden services are part of the stable release of Tor since version 0.3.2.9. They have various advantages compared to the old hidden services, among which are better encryption and privacy [https://gitweb.torproject.org/torspec.git/tree/rend-spec-v3.txt Tor Rendezvous Specification - Version 3]. These services have 256 bit addresses and thus do not fit in the existing addr message, which encapsulates onion addresses in OnionCat IPv6 addresses. Other transport-layer protocols such as I2P have always used longer addresses. This change would make it possible to gossip such addresses over the P2P network, so that other peers can connect to them. ==Specification==
The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED", "MAY", and "OPTIONAL" in this document are to be interpreted as described in RFC 2119[https://tools.ietf.org/html/rfc2119 RFC 2119].
The addrv2 message is defined as a message where pchCommand == "addrv2". It is serialized in the standard encoding for P2P messages. Its format is similar to the current addr message format, with the difference that the fixed 16-byte IP address is replaced by a network ID and a variable-length address, and the services format has been changed to [https://en.bitcoin.it/wiki/Protocol_documentation#Variable_length_integer CompactSize]. This means that the message contains a serialized std::vector of the following structure: {| class="wikitable" style="width: auto; text-align: center; font-size: smaller; table-layout: fixed;" !Type !Name !Description |- | uint32_t | time | Time that this node was last seen as connected to the network. A time in Unix epoch time format. |- | CompactSize | services | Service bits. A bit field that is 64 bits wide, encoded in [https://en.bitcoin.it/wiki/Protocol_documentation#Variable_length_integer CompactSize]. |- | uint8_t | networkID | Network identifier. An 8-bit value that specifies which network is addressed. |- | std::vector | addr | Network address. The interpretation depends on networkID. |- | uint16_t | port | Network port. If not relevant for the network this MUST be 0. |} One message can contain up to 1,000 addresses. Clients SHOULD reject messages with more addresses. Field addr has a variable length, with a maximum of 512 bytes (4096 bits). Clients SHOULD reject messages with longer addresses, irrespective of the network ID. The list of reserved network IDs is as follows: {| class="wikitable" style="width: auto; text-align: center; font-size: smaller; table-layout: fixed;" !Network ID !Enumeration !Address length (bytes) !Description |- | 0x01 | IPV4 | 4 | IPv4 address (globally routed internet) |- | 0x02 | IPV6 | 16 | IPv6 address (globally routed internet) |- | 0x03 | TORV2 | 10 | Tor v2 hidden service address (no longer usedTor v2 is no longer operational; clients MUST NOT gossip or relay Tor v2 addresses and MUST ignore them on receive) |- | 0x04 | TORV3 | 32 | Tor v3 hidden service address |- | 0x05 | I2P | 32 | I2P overlay network address |- | 0x06 | CJDNS | 16 | Cjdns overlay network address |- | 0x07 | YGGDRASIL | 16 | Yggdrasil overlay network address |} Clients are RECOMMENDED to gossip addresses from all known networks even if they are currently not connected to some of them. That could help multi-homed nodes and make it more difficult for an observer to tell which networks a node is connected to. Clients SHOULD NOT gossip addresses from unknown networks because they have no means to validate those addresses and so can be tricked to gossip invalid addresses. Further network ID numbers MUST be reserved in a new BIP document. Clients SHOULD reject messages that contain addresses that have a different length than specified in this table for a specific network ID, as these are meaningless. See the appendices for the address encodings to be used for the various networks. ==Signaling support and compatibility== Introduce a new message type sendaddrv2. Sending such a message indicates that a node can understand and prefers to receive addrv2 messages instead of addr messages. I.e. "Send me addrv2". Sending or not sending this message does not imply any preference with respect to receiving unrequested address messages. The sendaddrv2 message MUST only be sent in response to the version message from a peer and prior to sending the verack message. For older peers, that did not emit sendaddrv2, keep sending the legacy addr message, ignoring addresses with the newly introduced address types. ==Reference implementation== The reference implementation is available at (to be done) ==Acknowledgements== - Jonas Schnelli: change services field to [https://en.bitcoin.it/wiki/Protocol_documentation#Variable_length_integer CompactSize], to make the message more compact in the likely case instead of always using 8 bytes. - Gregory Maxwell: various suggestions regarding extensibility ==Appendix A: Tor v2 address encoding (no longer used )== The new message introduces a separate network ID for TORV2. Clients MUST send Tor hidden service addresses with this network ID, with the 80-bit hidden service ID in the address field. This is the same as the representation in the legacy addr message, minus the 6 byte prefix of the OnionCat wrapping. Clients SHOULD ignore OnionCat (fd87:d87e:eb43::/48) addresses on receive if they come with the IPV6 network ID. ==Appendix B: Tor v3 address encoding== According to the spec [https://gitweb.torproject.org/torspec.git/tree/rend-spec-v3.txt Tor Rendezvous Specification - Version 3: Encoding onion addresses], next-gen .onion addresses are encoded as follows:
onion_address = base32(PUBKEY | CHECKSUM | VERSION) + ".onion"
 CHECKSUM = H(".onion checksum" | PUBKEY | VERSION)[:2]

 where:
   - PUBKEY is the 32 bytes ed25519 master pubkey of the hidden service
   - VERSION is a one byte version field (default value '\x03')
   - ".onion checksum" is a constant string
   - CHECKSUM is truncated to two bytes before inserting it in onion_address
   - H() is the SHA3-256 cryptographic hash function
Tor v3 addresses MUST be sent with the TORV3 network ID, with the 32-byte PUBKEY part in the address field. As VERSION will always be '\x03' in the case of v3 addresses, this is enough to reconstruct the onion address. ==Appendix C: I2P address encoding== Like Tor, I2P naming uses a base32-encoded address format[https://geti2p.net/en/docs/naming#base32 I2P: Naming and address book]. I2P uses 52 characters (256 bits) to represent the full SHA-256 hash, followed by .b32.i2p. I2P addresses MUST be sent with the I2P network ID, with the decoded SHA-256 hash as address field. ==Appendix D: Cjdns address encoding== Cjdns addresses are simply IPv6 addresses in the fc00::/8 range[https://github.com/cjdelisle/cjdns/blob/6e46fa41f5647d6b414612d9d63626b0b952746b/doc/Whitepaper.md#pulling-it-all-together Cjdns whitepaper: Pulling It All Together]. They MUST be sent with the CJDNS network ID. ==Appendix E: Yggdrasil address encoding== Yggdrasil addresses are simply IPv6 addresses in the 0200::/7 range[https://yggdrasil-network.github.io/faq.html#will-yggdrasil-conflict-with-my-network-routing Yggdrasil FAQ]. They MUST be sent with the YGGDRASIL network ID. == Changelog == * 2.0.0 (2025-10-01): ** Add note that Tor v2 is no longer operational. * 1.0.0 (2019-02-27): ** Initial version ==References== ================================================ FILE: bip-0156/bitcoin.conf ================================================ regtest=1 # Run this node on its own independent test network debug=net # Enable network debug logs debug=mempool # Enable mempool debug logs debug=mempoolrej # Enable mempool rejection debug logs debug=dandelion # Enable dandelion debug logs logips=1 # Log IP addresses in debug output logtimemicros=1 # Log timestamps with microsecond precision printtoconsole=1 # Print debug logs to console instead of debug.log server=1 # Accept command line JSON-RPC commands rpcuser=xxx # Username for JSON-RPC connections rpcpassword=xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx rpcauth=xxx:xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx dns=0 # Do not allow DNS lookups for -addnode, -seednode, and -connect dnsseed=0 # Do not query for peer addresses via DNS lookup persistmempool=0 # Do not save mempool on shutdown to load on restart dandelion=1 # Enable Dandelion transactions ================================================ FILE: bip-0156.mediawiki ================================================
  BIP: 156
  Layer: Peer Services
  Title: Dandelion - Privacy Enhancing Routing
  Authors: Brad Denby 
           Andrew Miller 
           Giulia Fanti 
           Surya Bakshi 
           Shaileshh Bojja Venkatakrishnan 
           Pramod Viswanath 
  Status: Closed
  Type: Specification
  Assigned: 2017-06-09
  License: CC0-1.0
==Abstract== Bitcoin's transaction spreading protocol is vulnerable to deanonymization attacks. Dandelion is a transaction routing mechanism that provides formal anonymity guarantees against these attacks. When a node generates a transaction without Dandelion, it transmits that transaction to its peers with independent, exponential delays. This approach, known as diffusion in academia, allows network adversaries to link transactions to IP addresses. Dandelion mitigates this class of attacks by sending transactions over a randomly selected path before diffusion. Transactions travel along this path during the "stem phase" and are then diffused during the "fluff phase" (hence Dandelion). We have shown that this routing protocol provides near-optimal anonymity guarantees among schemes that do not introduce additional encryption mechanisms. ==Motivation== Transaction diffusion in Bitcoin is vulnerable to deanonymization attacks. Because transactions are sent to peers with independent, exponential delays, messages spread through the network in a statistically symmetric manner. This pattern allows colluding spy nodes to infer the transaction source. Breaking this symmetry prevents the attack. However, we have shown that an adversary with knowledge of the network topology can launch a much more effective "fingerprint" attack if the symmetry breaking is not done properly. Consider a botnet-style adversary with access to the P2P graph. Botnets of size comparable to the Bitcoin P2P network are common and cheap, and these adversaries can learn the network structure with probe messages. We have shown that such an adversary can achieve total deanonymization of the entire network after observing less than ten transactions per node. Dandelion is a practical, lightweight privacy solution that provides the Bitcoin network formal anonymity guarantees. While other privacy solutions aim to protect individual users, Dandelion protects anonymity by limiting the capability of adversaries to deanonymize the entire network. ==How Dandelion Works== Dandelion enhances user privacy by sending transactions through an anonymity phase before diffusing them throughout the network. At a high level, Dandelion enhances privacy by (i) breaking the symmetry of diffusion and (ii) mixing transactions by forwarding messages from different sources along the same path. Dandelion routing can be conceptualized in three phases. First, a privacy graph is constructed. In practice, this privacy graph is constructed in a fully decentralized manner and is a subgraph of the existing Bitcoin P2P network. Next, transactions are forwarded along this privacy graph during the "stem phase." Finally, messages are broadcast to the network during the "fluff phase" using the typical method of diffusion. [[File:bip-0156/1-dandelion.png|framed|center|alt=An illustration of Dandelion routing|Figure 1]] Figure 1 In order to select the privacy graph in a decentralized manner, each node selects a subset of its outbound peers to be Dandelion destinations. Dandelion transactions (transactions in their stem phase) that arrive at this node via inbound connections are forwarded to these Dandelion destinations. In an ideal setting, we have found that a Hamiltonian circuit provides near-optimal privacy guarantees. However, constructing a Hamiltonian circuit through the Bitcoin P2P network in a decentralized, trustless manner is not feasible. Thus, we recommend that each node select two Dandelion destinations uniformly at random without replacement from its list of outbound peers. Our tests have shown that this method provides comparable privacy with increased robustness. During stem phase routing, there is a question of how to route messages in order to protect privacy. For example, if two Dandelion transactions arrive at a node from different inbound peers, to which Dandelion destination(s) should these transactions be sent? We have found that some choices are much better than others. Consider the case in which each Dandelion transaction is forwarded to a Dandelion destination selected uniformly at random. This approach results in a fingerprint attack allowing network-level botnet adversaries to achieve total deanonymization of the P2P network after observing less than ten transactions per node. [[File:bip-0156/2-attack.png|framed|center|alt=An illustration of a fingerprint attack|Figure 2]] Figure 2 During a fingerprint attack, a botnet-style adversary with knowledge of the graph structure first simulates transaction propagation. This offline step lets the adversary generate fingerprints for each network node. During the online attack, the adversary collects transactions at its spy nodes and matches these observations to the simulated fingerprints. Our simulations have shown that this attack results in devastating, network-wide deanonymization. [[File:bip-0156/3-attack-plot.png|framed|center|alt=A plot illustrating total deanonymization|Figure 3]] Figure 3 To avoid this issue, we suggest "per-inbound-edge" routing. Each inbound peer is assigned a particular Dandelion destination. Each Dandelion transaction that arrives via this peer is forwarded to the same Dandelion destination. Per-inbound-edge routing breaks the described attack by blocking an adversary's ability to construct useful fingerprints. Fingerprints arise when routing decisions are made independently per transaction at each node. In this case, two transactions from the same node generally take different paths through the network. Crucially, this results in multiple, unique data points that are aggregated to match with a fingerprint. Dandelion ensures that two transactions from the same node take the same network path, limiting adversaries to the far-left of the graph in Figure 3. In other words, adversary knowledge is limited to the case of one observed message rather than a rich profile of multiple transaction paths. Dandelion also breaks the symmetry of diffusion, making the source of the transaction difficult to infer. [[File:bip-0156/4-dandelion-plot.png|framed|center|alt=A plot illustrating limited deanonymization|Figure 4]] Figure 4 After a transaction has traveled along a Dandelion stem for a random number of hops, it transitions into the fluff phase of routing. The transaction is shared with the network through the existing process of diffusion. In practice, this fluff mechanism is enforced by a weighted coin flip at each node. If the random value is below some threshold, the Dandelion transaction is transformed into a typical transaction. In our testing, we have chosen a probability of ten percent that a given Dandelion transaction enters fluff phase when leaving a given node. This value strikes a good balance between stem path length and transaction spreading latency. Note that Dandelion's expected precision guarantees are a population-level metric, whereas the expected recall guarantees can be interpreted as an individual-level metric. Expected recall is equivalent to the probability that an adversary associates a single transaction with a given source. These guarantees are probabilistic. They do not address scenarios in which a node has been eclipsed by other nodes, or when a node is specifically targeted by an ISP-like adversary. Individuals who are concerned about targeted deanonymization should still use Tor. At a high level, Dandelion is like an "anonymity inoculation" for the public at large - including users who are not aware of Bitcoin's privacy issues. Higher adoption leads to greater benefits, even for users who do not use Tor. Early adopters of Dandelion still receive privacy benefits. In the worst case when no neighbors support Dandelion, transactions make at least one hop before diffusing. Note that any solution based only on routing cannot be perfectly anonymous due to the fundamental lower bounds on precision and recall shown in the original Dandelion paper. Dandelion provides near-optimal anonymity guarantees among such solutions. ==Specification== Dandelion can be specified with a handful of features: Dandelion transaction support, Dandelion routing data and logic, periodic Dandelion route shuffling, memory pool logic, the fluff mechanism, transaction embargoes, and Dandelion transaction logic. Specification details are summarized below. ===Dandelion transaction support=== During the stem phase, transactions are "Dandelion transactions." When a Dandelion transaction enters fluff phase, it becomes a typical Bitcoin transaction. Dandelion transactions and typical transactions differ only in their NetMsgType. Dandelion (stem phase) transactions MUST be differentiable from typical Bitcoin transactions. ===Dandelion routing data and logic=== Dandelion routing during the stem phase requires notions of inbound peers, outbound peers, Dandelion destinations, and Dandelion routes. Inbound peers consist of all currently connected peers that initiated the peer connection. Outbound peers consist of all currently connected peers that were connected to by this node. Dandelion destinations are a subset of outbound peers. The number of Dandelion destinations is limited by the DANDELION_MAX_DESTINATIONS parameter. In the reference implementation, this parameter is set to two. Our tests have shown that this value provides both privacy and robustness (see the reference paper for more details on the parameter tradeoffs). Dandelion routes are a map of inbound peers to Dandelion destinations. Every inbound peer is mapped to a Dandelion destination. Note that a Dandelion node may choose a different DANDELION_MAX_DESTINATIONS parameter without splitting from the privacy graph. When mapping inbound connections to outbound connections for Dandelion routes, we implement the following routing logic. First, select a set of Dandelion destinations from the set of outbound peers. This set of Dandelion destinations is of size less than or equal to DANDELION_MAX_DESTINATIONS. For each inbound connection, first identify the subset of Dandelion destinations with the least number of routes. For example, some subset of Dandelion destinations may be affiliated with zero routes while all other Dandelion destinations are affiliated with one or more routes. From this subset, select one Dandelion destination uniformly at random. Establish a Dandelion route from the inbound connection to this Dandelion destination. For a given Dandelion routing epoch, two distinct Dandelion destinations SHOULD be selected uniformly at random from the set of outbound connections. All Dandelion transactions that arrive via a given inbound connection MUST be transmitted to the same Dandelion destination. When choosing a Dandelion destination for a given inbound connection, the destination MUST be selected uniformly at random from the set of Dandelion destinations with the least number of inbound connections mapped to them. ===Periodic Dandelion route shuffling=== The map of Dandelion routes is cleared and reconstructed every ten minutes on average. We have chosen the value of ten minutes heuristically in order to make privacy graph learning difficult for adversaries. Note that a Dandelion node may choose a different average shuffle time without splitting from the privacy graph. Dandelion routes MUST be cleared and reconstructed at random intervals. Dandelion routes SHOULD be cleared and reconstructed every ten minutes on average. ===Memory pool logic=== Dandelion transactions are segregated from typical transactions. The mempool remains unchanged. Another instance of the CTxMemPool class, called the stempool, is used for Dandelion transactions. Information flows from mempool to stempool in order to ensure proper transaction propagation. Information does not flow from stempool to mempool, except when a Dandelion transaction fluffs into a typical transaction. When a Dandelion transaction arrives, the transaction MUST be added to the stempool and MUST NOT be added to the mempool. When a typical Bitcoin transaction arrives, the transaction MUST be added to the mempool and MUST be added to the stempool. When a Dandelion transaction fluffs, the transaction MUST be added to the mempool. ===The fluff mechanism=== When relaying a Dandelion transaction along a Dandelion route, there is a 10% chance that the Dandelion transaction becomes a typical Bitcoin transaction and is therefore relayed via diffusion. In our testing, this value strikes a good balance between stem path length and transaction spreading latency. Note that a Dandelion node may choose a different chance of fluffing without splitting from the privacy graph. When a node prepares to transmit a Dandelion transaction, the node MUST flip a biased coin. If the outcome is "Dandelion transaction," then the node MUST transmit the transaction to the appropriate Dandelion destination. Otherwise, the node MUST convert the Dandelion transaction into a typical Bitcoin transaction. A Dandelion transaction SHOULD fluff into a typical Bitcoin transaction with a 10% probability. ===Transaction embargoes=== During the stem phase, transactions are relayed along a single path. If any node in this path were to receive the Dandelion transaction and go offline, then the transaction would cease to propagate. To increase robustness, every node that forwards a Dandelion transaction initializes a timer at the time of reception. If the Dandelion transaction does not appear in the memory pool by the time the timer expires, then the transaction enters fluff phase and is forwarded via diffusion. When a Dandelion transaction arrives, the node MUST set an embargo timer for a random time in the future. If the Dandelion transaction arrives as a typical Bitcoin transaction, the node MUST cancel the timer. If the timer expires before the Dandelion transaction is observed as a typical Bitcoin transaction, then the node MUST fluff the Dandelion transaction. ===Dandelion transaction logic=== The following cases define a node's behavior when receiving network packets referencing Dandelion transactions. * Receive INV for Dandelion TX: If the peer is inbound and the Dandelion transaction has not been received from this peer, then reply with GETDATA. * Receive GETDATA for Dandelion TX: If the peer is not inbound and the Dandelion transaction has been advertised to this peer, then reply with the Dandelion transaction. * Receive Dandelion TX: If the peer is inbound, then relay the Dandelion TX to the appropriate Dandelion destination. ==Implementation== A reference implementation is available at the following URL: https://github.com/dandelion-org/bitcoin/tree/dandelion-feature-commits All features have been compressed into a single commit at the following URL: https://github.com/dandelion-org/bitcoin/tree/dandelion ==Compatibility== Dandelion does not conflict with existing versions of Bitcoin. A Bitcoin node that supports Dandelion appears no differently to Bitcoin nodes running older software versions. Bitcoin nodes that support Dandelion can identify feature support through a probe message. Obviously, older nodes are not capable of Dandelion routing. If a Bitcoin node supporting Dandelion has no peers that also support Dandelion, then its behavior naturally decays to that of a Bitcoin node without Dandelion support due to the Dandelion transaction embargoes. ==Acknowledgements== We would like to thank the Bitcoin Core developers and Gregory Maxwell in particular for their insightful comments, which helped to inform this implementation and some of the follow-up work we conducted. We would also like to thank the Mimblewimble development community for coining the term "stempool," which we happily adopted for this implementation. ==References== # An Analysis of Anonymity in Bitcoin Using P2P Network Traffic http://fc14.ifca.ai/papers/fc14_submission_71.pdf # Deanonymisation of clients in Bitcoin P2P network https://arxiv.org/abs/1405.7418 # Discovering Bitcoin’s Public Topology and Influential Nodes https://cs.umd.edu/projects/coinscope/coinscope.pdf # (Sigmetrics 2017) Dandelion: Redesigning the Bitcoin Network for Anonymity https://arxiv.org/abs/1701.04439 # (Sigmetrics 2018) Dandelion++: Lightweight Cryptocurrency Networking with Formal Anonymity Guarantees https://arxiv.org/pdf/1805.11060.pdf ==Copyright== To the extent possible under law, the author(s) have dedicated all copyright and related and neighboring rights to this work to the public domain worldwide. This work is distributed without any warranty. You should have received a copy of the CC0 Public Domain Dedication with this work. If not, see https://creativecommons.org/publicdomain/zero/1.0/ . ================================================ FILE: bip-0157.mediawiki ================================================
  BIP: 157
  Layer: Peer Services
  Title: Client Side Block Filtering
  Authors: Olaoluwa Osuntokun 
           Alex Akselrod 
           Jim Posen 
  Status: Deployed
  Type: Specification
  Assigned: 2017-05-24
  License: CC0-1.0
  Requires: 158
== Abstract == This BIP describes a new light client protocol in Bitcoin that improves upon currently available options. The standard light client protocol in use today, defined in BIP 37https://github.com/bitcoin/bips/blob/master/bip-0037.mediawiki, has known flaws that weaken the security and privacy of clients and allow denial-of-service attack vectors on full nodeshttps://lists.linuxfoundation.org/pipermail/bitcoin-dev/2016-May/012636.html. The new protocol overcomes these issues by allowing light clients to obtain compact probabilistic filters of block content from full nodes and download full blocks if the filter matches relevant data. New P2P messages empower light clients to securely sync the blockchain without relying on a trusted source. This BIP also defines a filter header, which serves as a commitment to all filters for previous blocks and provides the ability to efficiently detect malicious or faulty peers serving invalid filters. The resulting protocol guarantees that light clients with at least one honest peer are able to identify the correct block filters. == Motivation == Bitcoin light clients allow applications to read relevant transactions from the blockchain without incurring the full cost of downloading and validating all data. Such applications seek to simultaneously minimize the trust in peers and the amount of bandwidth, storage space, and computation required. They achieve this by downloading all block headers, verifying the proofs of work, and following the longest proof-of-work chain. Since block headers are a fixed 80-bytes and are generated every 10 minutes on average, the bandwidth required to sync the block headers is minimal. Light clients then download only the blockchain data relevant to them directly from peers and validate inclusion in the header chain. Though clients do not check the validity of all blocks in the longest proof-of-work chain, they rely on miner incentives for security. BIP 37 is currently the most widely used light client execution mode for Bitcoin. With BIP 37, a client sends a Bloom filter it wants to watch to a full node peer, then receives notifications for each new transaction or block that matches the filter. The client then requests relevant transactions from the peer along with Merkle proofs of inclusion in the blocks containing them, which are verified against the block headers. The Bloom filters match data such as client addresses and unspent outputs, and the filter size must be carefully tuned to balance the false positive rate with the amount of information leaked to peer. It has been shown, however, that most implementations available offer virtually ''zero privacy'' to wallets and other applicationshttps://eprint.iacr.org/2014/763.pdfhttps://jonasnick.github.io/blog/2015/02/12/privacy-in-bitcoinj/. Additionally, malicious full nodes serving light clients can omit critical data with little risk of detection, which is unacceptable for some applications (such as Lightning Network clients) that must respond to certain on-chain events. Finally, honest nodes servicing BIP 37 light clients may incur significant I/O and CPU resource usage due to maliciously crafted Bloom filters, creating a denial-of-service (DoS) vector and disincentizing node operators from supporting the protocolhttps://github.com/bitcoin/bips/blob/master/bip-0111.mediawiki. The alternative detailed in this document can be seen as the opposite of BIP 37: instead of the client sending a filter to a full node peer, full nodes generate deterministic filters on block data that are served to the client. A light client can then download an entire block if the filter matches the data it is watching for. Since filters are deterministic, they only need to be constructed once and stored on disk, whenever a new block is connected to the chain. This keeps the computation required to serve filters minimal, and eliminates the I/O asymmetry that makes BIP 37 enabled nodes vulnerable. Clients also get better assurance of seeing all relevant transactions because they can check the validity of filters received from peers more easily than they can check completeness of filtered blocks. Finally, client privacy is improved because blocks can be downloaded from ''any source'', so that no one peer gets complete information on the data required by a client. Extremely privacy conscious light clients may opt to anonymously fetch blocks using advanced techniques such a Private Information Retrievalhttps://en.wikipedia.org/wiki/Private_information_retrieval. == Definitions == []byte represents a vector of bytes. [N]byte represents a fixed-size byte array with length N. ''CompactSize'' is a compact encoding of unsigned integers used in the Bitcoin P2P protocol. ''double-SHA256'' is a hash algorithm defined by two invocations of SHA-256: double-SHA256(x) = SHA256(SHA256(x)). The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED", "MAY", and "OPTIONAL" in this document are to be interpreted as described in RFC 2119. == Specification == === Filter Types === For the sake of future extensibility and reducing filter sizes, there are multiple ''filter types'' that determine which data is included in a block filter as well as the method of filter construction/querying. In this model, full nodes generate one filter per block per filter type supported. Each type is identified by a one byte code, and specifies the contents and serialization format of the filter. A full node MAY signal support for particular filter types using service bits. The initial filter types are defined separately in [[bip-0158.mediawiki|BIP 158]], and one service bit is allocated to signal support for them. === Filter Headers === This proposal draws inspiration from the headers-first mechanism that Bitcoin nodes use to sync the block chainhttps://bitcoin.org/en/developer-guide#headers-first. Similar to how block headers have a Merkle commitment to all transaction data in the block, we define filter headers that have commitments to the block filters. Also like block headers, filter headers each have a commitment to the preceding one. Before downloading the block filters themselves, a light client can download all filter headers for the current block chain and use them to verify the authenticity of the filters. If the filter header chains differ between multiple peers, the client can identify the point where they diverge, then download the full block and compute the correct filter, thus identifying which peer is faulty. The canonical hash of a block filter is the double-SHA256 of the serialized filter. Filter headers are 32-byte hashes derived for each block filter. They are computed as the double-SHA256 of the concatenation of the filter hash with the previous filter header. The previous filter header used to calculate that of the genesis block is defined to be the 32-byte array of 0's. === New Messages === ==== getcfilters ==== getcfilters is used to request the compact filters of a particular type for a particular range of blocks. The message contains the following fields: {| class="wikitable" ! Field Name ! Data Type ! Byte Size ! Description |- | FilterType | byte | 1 | Filter type for which headers are requested |- | StartHeight | uint32 | 4 | The height of the first block in the requested range |- | StopHash | [32]byte | 32 | The hash of the last block in the requested range |} # Nodes SHOULD NOT send getcfilters unless the peer has signaled support for this filter type. Nodes receiving getcfilters with an unsupported filter type SHOULD NOT respond. # StopHash MUST be known to belong to a block accepted by the receiving peer. This is the case if the peer had previously sent a headers or inv message with that block or any descendents. A node that receives getcfilters with an unknown StopHash SHOULD NOT respond. # The height of the block with hash StopHash MUST be greater than or equal to StartHeight, and the difference MUST be strictly less than 1000. # The receiving node MUST respond to valid requests by sending one cfilter message for each block in the requested range, sequentially in order by block height. ==== cfilter ==== cfilter is sent in response to getcfilters, one for each block in the requested range. The message contains the following fields: {| class="wikitable" ! Field Name ! Data Type ! Byte Size ! Description |- | FilterType | byte | 1 | Byte identifying the type of filter being returned |- | BlockHash | [32]byte | 32 | Block hash of the Bitcoin block for which the filter is being returned |- | NumFilterBytes | CompactSize | 1-5 | A variable length integer representing the size of the filter in the following field |- | FilterBytes | []byte | NumFilterBytes | The serialized compact filter for this block |} # The FilterType SHOULD match the field in the getcfilters request, and BlockHash must correspond to a block that is an ancestor of StopHash with height greater than or equal to StartHeight. ==== getcfheaders ==== getcfheaders is used to request verifiable filter headers for a range of blocks. The message contains the following fields: {| class="wikitable" ! Field Name ! Data Type ! Byte Size ! Description |- | FilterType | byte | 1 | Filter type for which headers are requested |- | StartHeight | uint32 | 4 | The height of the first block in the requested range |- | StopHash | [32]byte | 32 | The hash of the last block in the requested range |} # Nodes SHOULD NOT send getcfheaders unless the peer has signaled support for this filter type. Nodes receiving getcfheaders with an unsupported filter type SHOULD NOT respond. # StopHash MUST be known to belong to a block accepted by the receiving peer. This is the case if the peer had previously sent a headers or inv message with that block or any descendents. A node that receives getcfheaders with an unknown StopHash SHOULD NOT respond. # The height of the block with hash StopHash MUST be greater than or equal to StartHeight, and the difference MUST be strictly less than 2,000. ==== cfheaders ==== cfheaders is sent in response to getcfheaders. Instead of including the filter headers themselves, the response includes one filter header and a sequence of filter hashes, from which the headers can be derived. This has the benefit that the client can verify the binding links between the headers. The message contains the following fields: {| class="wikitable" ! Field Name ! Data Type ! Byte Size ! Description |- | FilterType | byte | 1 | Filter type for which hashes are requested |- | StopHash | [32]byte | 32 | The hash of the last block in the requested range |- | PreviousFilterHeader | [32]byte | 32 | The filter header preceding the first block in the requested range |- | FilterHashesLength | CompactSize | 1-3 | The length of the following vector of filter hashes |- | FilterHashes | [][32]byte | FilterHashesLength * 32 | The filter hashes for each block in the requested range |} # The FilterType and StopHash SHOULD match the fields in the getcfheaders request. # FilterHashesLength MUST NOT be greater than 2,000. # FilterHashes MUST have one entry for each block on the chain terminating with tip StopHash, starting with the block at height StartHeight. The entries MUST be the filter hashes of the given type for each block in that range, in ascending order by height. # PreviousFilterHeader MUST be set to the previous filter header of first block in the requested range. ==== getcfcheckpt ==== getcfcheckpt is used to request filter headers at evenly spaced intervals over a range of blocks. Clients may use filter hashes from getcfheaders to connect these checkpoints, as is described in the [[#client-operation|Client Operation]] section below. The getcfcheckpt message contains the following fields: {| class="wikitable" ! Field Name ! Data Type ! Byte Size ! Description |- | FilterType | byte | 1 | Filter type for which headers are requested |- | StopHash | [32]byte | 32 | The hash of the last block in the chain that headers are requested for |} # Nodes SHOULD NOT send getcfcheckpt unless the peer has signaled support for this filter type. Nodes receiving getcfcheckpt with an unsupported filter type SHOULD NOT respond. # StopHash MUST be known to belong to a block accepted by the receiving peer. This is the case if the peer had previously sent a headers or inv message with any descendent blocks. A node that receives getcfcheckpt with an unknown StopHash SHOULD NOT respond. ==== cfcheckpt ==== cfcheckpt is sent in response to getcfcheckpt. The filter headers included are the set of all filter headers on the requested chain where the height is a positive multiple of 1,000. The message contains the following fields: {| class="wikitable" ! Field Name ! Data Type ! Byte Size ! Description |- | FilterType | byte | 1 | Filter type for which headers are requested |- | StopHash | [32]byte | 32 | The hash of the last block in the chain that headers are requested for |- | FilterHeadersLength | CompactSize | 1-3 | The length of the following vector of filter headers |- | FilterHeaders | [][32]byte | FilterHeadersLength * 32 | The filter headers at intervals of 1,000 |} # The FilterType and StopHash SHOULD match the fields in the getcfcheckpt request. # FilterHeaders MUST have exactly one entry for each block on the chain terminating in StopHash, where the block height is a multiple of 1,000 greater than 0. The entries MUST be the filter headers of the given type for each such block, in ascending order by height. === Node Operation === Full nodes MAY opt to support this BIP and generate filters for any of the specified filter types. Such nodes SHOULD treat the filters as an additional index of the blockchain. For each new block that is connected to the main chain, nodes SHOULD generate filters for all supported types and persist them. Nodes that are missing filters and are already synced with the blockchain SHOULD reindex the chain upon start-up, constructing filters for each block from genesis to the current tip. They also SHOULD keep every checkpoint header in memory, so that getcfcheckpt requests do not result in many random-access disk reads. Nodes SHOULD NOT generate filters dynamically on request, as malicious peers may be able to perform DoS attacks by requesting small filters derived from large blocks. This would require an asymmetrical amount of I/O on the node to compute and serve, similar to attacks against BIP 37 enabled nodes noted in BIP 111. Nodes MAY prune block data after generating and storing all filters for a block. === Client Operation === This section provides recommendations for light clients to download filters with maximal security. Clients SHOULD first sync the entire block header chain from peers using the standard headers-first syncing mechanism before downloading any block filters or filter headers. Clients configured with trusted checkpoints MAY only sync headers started from the last checkpoint. Clients SHOULD disconnect any outbound peers whose best chain has significantly less work than the known longest proof-of-work chain. Once a client's block headers are in sync, it SHOULD download and verify filter headers for all blocks and filter types that it might later download. The client SHOULD send getcfheaders messages to peers and derive and store the filter headers for each block. The client MAY first fetch headers at evenly spaced intervals of 1,000 by sending getcfcheckpt. The header checkpoints allow the client to download filter headers for different intervals from multiple peers in parallel, verifying each range of 1,000 headers against the checkpoints. Unless securely connected to a trusted peer that is serving filter headers, the client SHOULD connect to multiple outbound peers that support each filter type to mitigate the risk of downloading incorrect headers. If the client receives conflicting filter headers from different peers for any block and filter type, it SHOULD interrogate them to determine which is faulty. The client SHOULD use getcfheaders and/or getcfcheckpt to first identify the first filter headers that the peers disagree on. The client then SHOULD download the full block from any peer and derive the correct filter and filter header. The client SHOULD ban any peers that sent a filter header that does not match the computed one. Once the client has downloaded and verified all filter headers needed, ''and'' no outbound peers have sent conflicting headers, the client can download the actual block filters it needs. The client MAY backfill filter headers before the first verified one at this point if it only downloaded them starting at a later point. Clients SHOULD persist the verified filter headers for the last 100 blocks in the chain (or whatever finality depth is desired), to compare against headers received from new peers after restart. They MAY store more filter headers to avoid redownloading them if a rescan is later necessary. Starting from the first block in the desired range, the client now MAY download the filters. The client SHOULD test that each filter links to its corresponding filter header and ban peers that send incorrect filters. The client MAY download multiple filters at once to increase throughput, though it SHOULD test the filters sequentially. The client MAY check if a filter is empty before requesting it by checking if the filter header commits to the hash of the empty filter, saving a round trip if that is the case. Each time a new valid block header is received, the client SHOULD request the corresponding filter headers from all eligible peers. If two peers send conflicting filter headers, the client should interrogate them as described above and ban any peers that send an invalid header. If a client is fetching full blocks from the P2P network, they SHOULD be downloaded from outbound peers at random to mitigate privacy loss due to transaction intersection analysis. Note that blocks may be downloaded from peers that do not support this BIP. == Rationale == The filter headers and checkpoints messages are defined to help clients identify the correct filter for a block when connected to peers sending conflicting information. An alternative solution is to require Bitcoin blocks to include commitments to derived block filters, so light clients can verify authenticity given block headers and some additional witness data. This would require a network-wide change to the Bitcoin consensus rules, however, whereas this document proposes a solution purely at the P2P layer. The constant interval of 1,000 blocks between checkpoints was chosen so that, given the current chain height and rate of growth, the size of a cfcheckpt message is not drastically different from a cfheaders message between two checkpoints. Also, 1,000 is a nice round number, at least to those of us who think in decimal. == Compatibility == This light client mode is not compatible with current node deployments and requires support for the new P2P messages. The node implementation of this proposal is not incompatible with the current P2P network rules (ie. doesn't affect network topology of full nodes). Light clients may adopt protocols based on this as an alternative to the existing BIP 37. Adoption of this BIP may result in reduced network support for BIP 37. == Acknowledgments == We would like to thank bfd (from the bitcoin-dev mailing list) for bringing the basis of this BIP to our attention, Joseph Poon for suggesting the filter header chain scheme, and Pedro Martelletto for writing the initial indexing code for btcd. We would also like to thank Dave Collins, JJ Jeffrey, Eric Lombrozo, and Matt Corallo for useful discussions. == Reference Implementation == Light client: [https://github.com/lightninglabs/neutrino] Full-node indexing: https://github.com/Roasbeef/btcd/tree/segwit-cbf Golomb-Rice Coded sets: https://github.com/Roasbeef/btcutil/tree/gcs/gcs == References == == Copyright == This document is licensed under the Creative Commons CC0 1.0 Universal license. ================================================ FILE: bip-0158/gentestvectors.go ================================================ // This program connects to your local btcd and generates test vectors for // 5 blocks and collision space sizes of 1-32 bits. Change the RPC cert path // and credentials to run on your system. The program assumes you're running // a btcd with cfilter support, which mainline btcd doesn't have; in order to // circumvent this assumption, comment out the if block that checks the // filter size of DefaultP. package main import ( "bytes" "encoding/hex" "encoding/json" "fmt" "io" "io/ioutil" "os" "path/filepath" "github.com/btcsuite/btcd/blockchain" "github.com/btcsuite/btcd/chaincfg/chainhash" "github.com/btcsuite/btcd/rpcclient" "github.com/btcsuite/btcd/wire" "github.com/btcsuite/btcutil" "github.com/btcsuite/btcutil/gcs/builder" "github.com/davecgh/go-spew/spew" ) var ( // testBlockHeights are the heights of the blocks to include in the test // vectors. Any new entries must be added in sorted order. testBlockHeights = []testBlockCase{ {0, "Genesis block"}, {2, ""}, {3, ""}, {15007, "Tx has non-standard OP_RETURN output followed by opcodes"}, {49291, "Tx pays to empty output script"}, {180480, "Tx spends from empty output script"}, {926485, "Duplicate pushdata 913bcc2be49cb534c20474c4dee1e9c4c317e7eb"}, {987876, "Coinbase tx has unparsable output script"}, {1263442, "Includes witness data"}, {1414221, "Empty data"}, } defaultBtcdDir = btcutil.AppDataDir("btcd", false) defaultBtcdRPCCertFile = filepath.Join(defaultBtcdDir, "rpc.cert") ) const ( fp = 19 ) type testBlockCase struct { height uint32 comment string } type JSONTestWriter struct { writer io.Writer firstRowWritten bool } func NewJSONTestWriter(writer io.Writer) *JSONTestWriter { return &JSONTestWriter{writer: writer} } func (w *JSONTestWriter) WriteComment(comment string) error { return w.WriteTestCase([]interface{}{comment}) } func (w *JSONTestWriter) WriteTestCase(row []interface{}) error { var err error if w.firstRowWritten { _, err = io.WriteString(w.writer, ",\n") } else { _, err = io.WriteString(w.writer, "[\n") w.firstRowWritten = true } if err != nil { return err } rowBytes, err := json.Marshal(row) if err != nil { return err } _, err = w.writer.Write(rowBytes) return err } func (w *JSONTestWriter) Close() error { if !w.firstRowWritten { return nil } _, err := io.WriteString(w.writer, "\n]\n") return err } func fetchPrevOutputScripts(client *rpcclient.Client, block *wire.MsgBlock) ([][]byte, error) { var prevScripts [][]byte txCache := make(map[chainhash.Hash]*wire.MsgTx) for _, tx := range block.Transactions { if blockchain.IsCoinBaseTx(tx) { continue } for _, txIn := range tx.TxIn { prevOp := txIn.PreviousOutPoint tx, ok := txCache[prevOp.Hash] if !ok { originTx, err := client.GetRawTransaction( &prevOp.Hash, ) if err != nil { return nil, fmt.Errorf("unable to get "+ "txid=%v: %v", prevOp.Hash, err) } txCache[prevOp.Hash] = originTx.MsgTx() tx = originTx.MsgTx() } index := prevOp.Index prevScripts = append( prevScripts, tx.TxOut[index].PkScript, ) } } return prevScripts, nil } func main() { var ( writerFile *JSONTestWriter prevBasicHeader chainhash.Hash ) fName := fmt.Sprintf("testnet-%02d.json", fp) file, err := os.Create(fName) if err != nil { fmt.Println("Error creating output file: ", err.Error()) return } defer file.Close() writer := &JSONTestWriter{ writer: file, } defer writer.Close() err = writer.WriteComment("Block Height,Block Hash,Block," + "[Prev Output Scripts for Block],Previous Basic Header," + "Basic Filter,Basic Header,Notes") if err != nil { fmt.Println("Error writing to output file: ", err.Error()) return } writerFile = writer cert, err := ioutil.ReadFile(defaultBtcdRPCCertFile) if err != nil { fmt.Println("Couldn't read RPC cert: ", err.Error()) return } conf := rpcclient.ConnConfig{ Host: "127.0.0.1:18334", Endpoint: "ws", User: "kek", Pass: "kek", Certificates: cert, } client, err := rpcclient.New(&conf, nil) if err != nil { fmt.Println("Couldn't create a new client: ", err.Error()) return } var testBlockIndex int for height := 0; testBlockIndex < len(testBlockHeights); height++ { blockHash, err := client.GetBlockHash(int64(height)) if err != nil { fmt.Println("Couldn't get block hash: ", err.Error()) return } block, err := client.GetBlock(blockHash) if err != nil { fmt.Println("Couldn't get block data: ", err.Error()) return } var blockBuf bytes.Buffer err = block.Serialize(&blockBuf) if err != nil { fmt.Println("Error serializing block to buffer: ", err.Error()) return } blockBytes := blockBuf.Bytes() prevOutputScripts, err := fetchPrevOutputScripts(client, block) if err != nil { fmt.Println("Couldn't fetch prev output scripts: ", err) return } basicFilter, err := builder.BuildBasicFilter(block, prevOutputScripts) if err != nil { fmt.Println("Error generating basic filter: ", err.Error()) return } basicHeader, err := builder.MakeHeaderForFilter(basicFilter, prevBasicHeader) if err != nil { fmt.Println("Error generating header for filter: ", err.Error()) return } // We'll now ensure that we've constructed the same filter as // the chain server we're fetching blocks from. filter, err := client.GetCFilter( blockHash, wire.GCSFilterRegular, ) if err != nil { fmt.Println("Error getting basic filter: ", err.Error()) return } nBytes, err := basicFilter.NBytes() if err != nil { fmt.Println("Couldn't get NBytes(): ", err) return } if !bytes.Equal(filter.Data, nBytes) { // Don't error on empty filters fmt.Printf("basic filter doesn't match: generated "+ "%x, rpc returns %x, block %v", nBytes, filter.Data, spew.Sdump(block)) return } header, err := client.GetCFilterHeader( blockHash, wire.GCSFilterRegular, ) if err != nil { fmt.Println("Error getting basic header: ", err.Error()) return } if !bytes.Equal(header.PrevFilterHeader[:], basicHeader[:]) { fmt.Println("Basic header doesn't match!") return } if height%1000 == 0 { fmt.Printf("Verified height %v against server\n", height) } if uint32(height) == testBlockHeights[testBlockIndex].height { var bfBytes []byte bfBytes, err = basicFilter.NBytes() if err != nil { fmt.Println("Couldn't get NBytes(): ", err) return } prevScriptStrings := make([]string, len(prevOutputScripts)) for i, prevScript := range prevOutputScripts { prevScriptStrings[i] = hex.EncodeToString(prevScript) } row := []interface{}{ height, blockHash.String(), hex.EncodeToString(blockBytes), prevScriptStrings, prevBasicHeader.String(), hex.EncodeToString(bfBytes), basicHeader.String(), testBlockHeights[testBlockIndex].comment, } err = writerFile.WriteTestCase(row) if err != nil { fmt.Println("Error writing test case to output: ", err.Error()) return } testBlockIndex++ } prevBasicHeader = basicHeader } } ================================================ FILE: bip-0158/go.mod ================================================ module github.com/bitcoin/bips/bip-0158 require ( github.com/btcsuite/btcd v0.0.0-20190115013929-ed77733ec07d github.com/btcsuite/btcutil v0.0.0-20190207003914-4c204d697803 github.com/davecgh/go-spew v1.1.1 ) ================================================ FILE: bip-0158/go.sum ================================================ github.com/aead/siphash v1.0.1 h1:FwHfE/T45KPKYuuSAKyyvE+oPWcaQ+CUmFW0bPlM+kg= github.com/aead/siphash v1.0.1/go.mod h1:Nywa3cDsYNNK3gaciGTWPwHt0wlpNV15vwmswBAUSII= github.com/btcsuite/btcd v0.0.0-20190115013929-ed77733ec07d h1:xG8Pj6Y6J760xwETNmMzmlt38QSwz0BLp1cZ09g27uw= github.com/btcsuite/btcd v0.0.0-20190115013929-ed77733ec07d/go.mod h1:d3C0AkH6BRcvO8T0UEPu53cnw4IbV63x1bEjildYhO0= github.com/btcsuite/btclog v0.0.0-20170628155309-84c8d2346e9f h1:bAs4lUbRJpnnkd9VhRV3jjAVU7DJVjMaK+IsvSeZvFo= github.com/btcsuite/btclog v0.0.0-20170628155309-84c8d2346e9f/go.mod h1:TdznJufoqS23FtqVCzL0ZqgP5MqXbb4fg/WgDys70nA= github.com/btcsuite/btcutil v0.0.0-20180706230648-ab6388e0c60a/go.mod h1:+5NJ2+qvTyV9exUAL/rxXi3DcLg2Ts+ymUAY5y4NvMg= github.com/btcsuite/btcutil v0.0.0-20190207003914-4c204d697803 h1:j3AgPKKZtZStM2nyhrDSLSYgT7YHrZKdSkq1OYeLjvM= github.com/btcsuite/btcutil v0.0.0-20190207003914-4c204d697803/go.mod h1:+5NJ2+qvTyV9exUAL/rxXi3DcLg2Ts+ymUAY5y4NvMg= github.com/btcsuite/go-socks v0.0.0-20170105172521-4720035b7bfd h1:R/opQEbFEy9JGkIguV40SvRY1uliPX8ifOvi6ICsFCw= github.com/btcsuite/go-socks v0.0.0-20170105172521-4720035b7bfd/go.mod h1:HHNXQzUsZCxOoE+CPiyCTO6x34Zs86zZUiwtpXoGdtg= github.com/btcsuite/goleveldb v0.0.0-20160330041536-7834afc9e8cd h1:qdGvebPBDuYDPGi1WCPjy1tGyMpmDK8IEapSsszn7HE= github.com/btcsuite/goleveldb v0.0.0-20160330041536-7834afc9e8cd/go.mod h1:F+uVaaLLH7j4eDXPRvw78tMflu7Ie2bzYOH4Y8rRKBY= github.com/btcsuite/snappy-go v0.0.0-20151229074030-0bdef8d06723 h1:ZA/jbKoGcVAnER6pCHPEkGdZOV7U1oLUedErBHCUMs0= github.com/btcsuite/snappy-go v0.0.0-20151229074030-0bdef8d06723/go.mod h1:8woku9dyThutzjeg+3xrA5iCpBRH8XEEg3lh6TiUghc= github.com/btcsuite/websocket v0.0.0-20150119174127-31079b680792 h1:R8vQdOQdZ9Y3SkEwmHoWBmX1DNXhXZqlTpq6s4tyJGc= github.com/btcsuite/websocket v0.0.0-20150119174127-31079b680792/go.mod h1:ghJtEyQwv5/p4Mg4C0fgbePVuGr935/5ddU9Z3TmDRY= github.com/btcsuite/winsvc v1.0.0/go.mod h1:jsenWakMcC0zFBFurPLEAyrnc/teJEM1O46fmI40EZs= github.com/davecgh/go-spew v0.0.0-20171005155431-ecdeabc65495/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/fsnotify/fsnotify v1.4.7 h1:IXs+QLmnXW2CcXuY+8Mzv/fWEsPGWxqefPtCP5CnV9I= github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo= github.com/golang/protobuf v1.2.0 h1:P3YflyNX/ehuJFLhxviNdFxQPkGK5cDcApsge1SqnvM= github.com/golang/protobuf v1.2.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U= github.com/hpcloud/tail v1.0.0 h1:nfCOvKYfkgYP8hkirhJocXT2+zOD8yUNjXaWfTlyFKI= github.com/hpcloud/tail v1.0.0/go.mod h1:ab1qPbhIpdTxEkNHXyeSf5vhxWSCs/tWer42PpOxQnU= github.com/jessevdk/go-flags v0.0.0-20141203071132-1679536dcc89/go.mod h1:4FA24M0QyGHXBuZZK/XkWh8h0e1EYbRYJSGM75WSRxI= github.com/jrick/logrotate v1.0.0/go.mod h1:LNinyqDIJnpAur+b8yyulnQw/wDuN1+BYKlTRt3OuAQ= github.com/kkdai/bstream v0.0.0-20161212061736-f391b8402d23 h1:FOOIBWrEkLgmlgGfMuZT83xIwfPDxEI2OHu6xUmJMFE= github.com/kkdai/bstream v0.0.0-20161212061736-f391b8402d23/go.mod h1:J+Gs4SYgM6CZQHDETBtE9HaSEkGmuNXF86RwHhHUvq4= github.com/onsi/ginkgo v1.6.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= github.com/onsi/ginkgo v1.7.0 h1:WSHQ+IS43OoUrWtD1/bbclrwK8TTH5hzp+umCiuxHgs= github.com/onsi/ginkgo v1.7.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= github.com/onsi/gomega v1.4.3 h1:RE1xgDvH7imwFD45h+u2SgIfERHlS2yNG4DObb5BSKU= github.com/onsi/gomega v1.4.3/go.mod h1:ex+gbHU/CVuBBDIJjb2X0qEXbFg53c61hWP/1CpauHY= golang.org/x/crypto v0.0.0-20170930174604-9419663f5a44 h1:9lP3x0pW80sDI6t1UMSLA4to18W7R7imwAI/sWS9S8Q= golang.org/x/crypto v0.0.0-20170930174604-9419663f5a44/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4= golang.org/x/net v0.0.0-20180906233101-161cd47e91fd h1:nTDtHvHSdCn1m6ITfMRqtOd/9+7a3s8RBNOZ3eYZzJA= golang.org/x/net v0.0.0-20180906233101-161cd47e91fd/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f h1:wMNYb4v58l5UBM7MYRLPG6ZhfOqbKu7X5eyFl8ZhKvA= golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sys v0.0.0-20180909124046-d0be0721c37e h1:o3PsSEY8E4eXWkXrIP9YJALUkVZqzHJT5DOasTyn8Vs= golang.org/x/sys v0.0.0-20180909124046-d0be0721c37e/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/text v0.3.0 h1:g61tztE5qeGQ89tm6NTjjM9VPIm088od1l6aSorWRWg= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405 h1:yhCVgyC4o1eVCa2tZl7eS0r+SDo693bJlVdllGtEeKM= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/fsnotify.v1 v1.4.7 h1:xOHLXZwVvI9hhs+cLKq5+I5onOuwQLhQwiu63xxlHs4= gopkg.in/fsnotify.v1 v1.4.7/go.mod h1:Tz8NjZHkW78fSQdbUxIjBTcgA1z1m8ZHf0WmKUhAMys= gopkg.in/tomb.v1 v1.0.0-20141024135613-dd632973f1e7 h1:uRGJdciOHaEIrze2W8Q3AKkepLTh2hOroT7a+7czfdQ= gopkg.in/tomb.v1 v1.0.0-20141024135613-dd632973f1e7/go.mod h1:dt/ZhP58zS4L8KSrWDmTeBkI65Dw0HsyUHuEVlX15mw= gopkg.in/yaml.v2 v2.2.1 h1:mUhvW9EsL+naU5Q3cakzfE91YhliOondGd6ZrsDBHQE= gopkg.in/yaml.v2 v2.2.1/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= ================================================ FILE: bip-0158/testnet-19.json ================================================ [ ["Block Height,Block Hash,Block,[Prev Output Scripts for Block],Previous Basic Header,Basic Filter,Basic Header,Notes"], [0,"000000000933ea01ad0ee984209779baaec3ced90fa3f408719526f8d77f4943","0100000000000000000000000000000000000000000000000000000000000000000000003ba3edfd7a7b12b27ac72c3e67768f617fc81bc3888a51323a9fb8aa4b1e5e4adae5494dffff001d1aa4ae180101000000010000000000000000000000000000000000000000000000000000000000000000ffffffff4d04ffff001d0104455468652054696d65732030332f4a616e2f32303039204368616e63656c6c6f72206f6e206272696e6b206f66207365636f6e64206261696c6f757420666f722062616e6b73ffffffff0100f2052a01000000434104678afdb0fe5548271967f1a67130b7105cd6a828e03909a67962e0ea1f61deb649f6bc3f4cef38c4f35504e51ec112de5c384df7ba0b8d578a4c702b6bf11d5fac00000000",[],"0000000000000000000000000000000000000000000000000000000000000000","019dfca8","21584579b7eb08997773e5aeff3a7f932700042d0ed2a6129012b7d7ae81b750","Genesis block"], [2,"000000006c02c8ea6e4ff69651f7fcde348fb9d557a06e6957b65552002a7820","0100000006128e87be8b1b4dea47a7247d5528d2702c96826c7a648497e773b800000000e241352e3bec0a95a6217e10c3abb54adfa05abb12c126695595580fb92e222032e7494dffff001d00d235340101000000010000000000000000000000000000000000000000000000000000000000000000ffffffff0e0432e7494d010e062f503253482fffffffff0100f2052a010000002321038a7f6ef1c8ca0c588aa53fa860128077c9e6c11e6830f4d7ee4e763a56b7718fac00000000",[],"d7bdac13a59d745b1add0d2ce852f1a0442e8945fc1bf3848d3cbffd88c24fe1","0174a170","186afd11ef2b5e7e3504f2e8cbf8df28a1fd251fe53d60dff8b1467d1b386cf0",""], [3,"000000008b896e272758da5297bcd98fdc6d97c9b765ecec401e286dc1fdbe10","0100000020782a005255b657696ea057d5b98f34defcf75196f64f6eeac8026c0000000041ba5afc532aae03151b8aa87b65e1594f97504a768e010c98c0add79216247186e7494dffff001d058dc2b60101000000010000000000000000000000000000000000000000000000000000000000000000ffffffff0e0486e7494d0151062f503253482fffffffff0100f2052a01000000232103f6d9ff4c12959445ca5549c811683bf9c88e637b222dd2e0311154c4c85cf423ac00000000",[],"186afd11ef2b5e7e3504f2e8cbf8df28a1fd251fe53d60dff8b1467d1b386cf0","016cf7a0","8d63aadf5ab7257cb6d2316a57b16f517bff1c6388f124ec4c04af1212729d2a",""], [15007,"0000000038c44c703bae0f98cdd6bf30922326340a5996cc692aaae8bacf47ad","0100000002394092aa378fe35d7e9ac79c869b975c4de4374cd75eb5484b0e1e00000000eb9b8670abd44ad6c55cee18e3020fb0c6519e7004b01a16e9164867531b67afc33bc94fffff001d123f10050101000000010000000000000000000000000000000000000000000000000000000000000000ffffffff0e04c33bc94f0115062f503253482fffffffff0100f2052a01000000232103f268e9ae07e0f8cb2f6e901d87c510d650b97230c0365b021df8f467363cafb1ac00000000",[],"18b5c2b0146d2d09d24fb00ff5b52bd0742f36c9e65527abdb9de30c027a4748","013c3710","07384b01311867949e0c046607c66b7a766d338474bb67f66c8ae9dbd454b20e","Tx has non-standard OP_RETURN output followed by opcodes"], [49291,"0000000018b07dca1b28b4b5a119f6d6e71698ce1ed96f143f54179ce177a19c","02000000abfaf47274223ca2fea22797e44498240e482cb4c2f2baea088962f800000000604b5b52c32305b15d7542071d8b04e750a547500005d4010727694b6e72a776e55d0d51ffff001d211806480201000000010000000000000000000000000000000000000000000000000000000000000000ffffffff0d038bc0000102062f503253482fffffffff01a078072a01000000232102971dd6034ed0cf52450b608d196c07d6345184fcb14deb277a6b82d526a6163dac0000000001000000081cefd96060ecb1c4fbe675ad8a4f8bdc61d634c52b3a1c4116dee23749fe80ff000000009300493046022100866859c21f306538152e83f115bcfbf59ab4bb34887a88c03483a5dff9895f96022100a6dfd83caa609bf0516debc2bf65c3df91813a4842650a1858b3f61cfa8af249014730440220296d4b818bb037d0f83f9f7111665f49532dfdcbec1e6b784526e9ac4046eaa602204acf3a5cb2695e8404d80bf49ab04828bcbe6fc31d25a2844ced7a8d24afbdff01ffffffff1cefd96060ecb1c4fbe675ad8a4f8bdc61d634c52b3a1c4116dee23749fe80ff020000009400483045022100e87899175991aa008176cb553c6f2badbb5b741f328c9845fcab89f8b18cae2302200acce689896dc82933015e7230e5230d5cff8a1ffe82d334d60162ac2c5b0c9601493046022100994ad29d1e7b03e41731a4316e5f4992f0d9b6e2efc40a1ccd2c949b461175c502210099b69fdc2db00fbba214f16e286f6a49e2d8a0d5ffc6409d87796add475478d601ffffffff1e4a6d2d280ea06680d6cf8788ac90344a9c67cca9b06005bbd6d3f6945c8272010000009500493046022100a27400ba52fd842ce07398a1de102f710a10c5599545e6c95798934352c2e4df022100f6383b0b14c9f64b6718139f55b6b9494374755b86bae7d63f5d3e583b57255a01493046022100fdf543292f34e1eeb1703b264965339ec4a450ec47585009c606b3edbc5b617b022100a5fbb1c8de8aaaa582988cdb23622838e38de90bebcaab3928d949aa502a65d401ffffffff1e4a6d2d280ea06680d6cf8788ac90344a9c67cca9b06005bbd6d3f6945c8272020000009400493046022100ac626ac3051f875145b4fe4cfe089ea895aac73f65ab837b1ac30f5d875874fa022100bc03e79fa4b7eb707fb735b95ff6613ca33adeaf3a0607cdcead4cfd3b51729801483045022100b720b04a5c5e2f61b7df0fcf334ab6fea167b7aaede5695d3f7c6973496adbf1022043328c4cc1cdc3e5db7bb895ccc37133e960b2fd3ece98350f774596badb387201ffffffff23a8733e349c97d6cd90f520fdd084ba15ce0a395aad03cd51370602bb9e5db3010000004a00483045022100e8556b72c5e9c0da7371913a45861a61c5df434dfd962de7b23848e1a28c86ca02205d41ceda00136267281be0974be132ac4cda1459fe2090ce455619d8b91045e901ffffffff6856d609b881e875a5ee141c235e2a82f6b039f2b9babe82333677a5570285a6000000006a473044022040a1c631554b8b210fbdf2a73f191b2851afb51d5171fb53502a3a040a38d2c0022040d11cf6e7b41fe1b66c3d08f6ada1aee07a047cb77f242b8ecc63812c832c9a012102bcfad931b502761e452962a5976c79158a0f6d307ad31b739611dac6a297c256ffffffff6856d609b881e875a5ee141c235e2a82f6b039f2b9babe82333677a5570285a601000000930048304502205b109df098f7e932fbf71a45869c3f80323974a826ee2770789eae178a21bfc8022100c0e75615e53ee4b6e32b9bb5faa36ac539e9c05fa2ae6b6de5d09c08455c8b9601483045022009fb7d27375c47bea23b24818634df6a54ecf72d52e0c1268fb2a2c84f1885de022100e0ed4f15d62e7f537da0d0f1863498f9c7c0c0a4e00e4679588c8d1a9eb20bb801ffffffffa563c3722b7b39481836d5edfc1461f97335d5d1e9a23ade13680d0e2c1c371f030000006c493046022100ecc38ae2b1565643dc3c0dad5e961a5f0ea09cab28d024f92fa05c922924157e022100ebc166edf6fbe4004c72bfe8cf40130263f98ddff728c8e67b113dbd621906a601210211a4ed241174708c07206601b44a4c1c29e5ad8b1f731c50ca7e1d4b2a06dc1fffffffff02d0223a00000000001976a91445db0b779c0b9fa207f12a8218c94fc77aff504588ac80f0fa02000000000000000000",["5221033423007d8f263819a2e42becaaf5b06f34cb09919e06304349d950668209eaed21021d69e2b68c3960903b702af7829fadcd80bd89b158150c85c4a75b2c8cb9c39452ae","52210279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f8179821021d69e2b68c3960903b702af7829fadcd80bd89b158150c85c4a75b2c8cb9c39452ae","522102a7ae1e0971fc1689bd66d2a7296da3a1662fd21a53c9e38979e0f090a375c12d21022adb62335f41eb4e27056ac37d462cda5ad783fa8e0e526ed79c752475db285d52ae","52210279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f8179821022adb62335f41eb4e27056ac37d462cda5ad783fa8e0e526ed79c752475db285d52ae","512103b9d1d0e2b4355ec3cdef7c11a5c0beff9e8b8d8372ab4b4e0aaf30e80173001951ae","76a9149144761ebaccd5b4bbdc2a35453585b5637b2f8588ac","522103f1848b40621c5d48471d9784c8174ca060555891ace6d2b03c58eece946b1a9121020ee5d32b54d429c152fdc7b1db84f2074b0564d35400d89d11870f9273ec140c52ae","76a914f4fa1cc7de742d135ea82c17adf0bb9cf5f4fb8388ac"],"ed47705334f4643892ca46396eb3f4196a5e30880589e4009ef38eae895d4a13","0afbc2920af1b027f31f87b592276eb4c32094bb4d3697021b4c6380","b6d98692cec5145f67585f3434ec3c2b3030182e1cb3ec58b855c5c164dfaaa3","Tx pays to empty output script"], [180480,"00000000fd3ceb2404ff07a785c7fdcc76619edc8ed61bd25134eaa22084366a","020000006058aa080a655aa991a444bd7d1f2defd9a3bbe68aabb69030cf3b4e00000000d2e826bfd7ef0beaa891a7eedbc92cd6a544a6cb61c7bdaa436762eb2123ef9790f5f552ffff001d0002c90f0501000000010000000000000000000000000000000000000000000000000000000000000000ffffffff0e0300c102024608062f503253482fffffffff01c0c6072a01000000232102e769e60137a4df6b0df8ebd387cca44c4c57ae74cc0114a8e8317c8f3bfd85e9ac00000000010000000381a0802911a01ffb025c4dea0bc77963e8c1bb46313b71164c53f72f37fe5248010000000151ffffffffc904b267833d215e2128bd9575242232ac2bc311550c7fc1f0ef6f264b40d14c010000000151ffffffffdf0915666649dba81886519c531649b7b02180b4af67d6885e871299e9d5f775000000000151ffffffff0180817dcb00000000232103bb52138972c48a132fc1f637858c5189607dd0f7fe40c4f20f6ad65f2d389ba4ac0000000001000000018da38b434fba82d66052af74fc5e4e94301b114d9bc03f819dc876398404c8b4010000006c493046022100fe738b7580dc5fb5168e51fc61b5aed211125eb71068031009a22d9bbad752c5022100be5086baa384d40bcab0fa586e4f728397388d86e18b66cc417dc4f7fa4f9878012103f233299455134caa2687bdf15cb0becdfb03bd0ff2ff38e65ec6b7834295c34fffffffff022ebc1400000000001976a9147779b7fba1c1e06b717069b80ca170e8b04458a488ac9879c40f000000001976a9142a0307cd925dbb66b534c4db33003dd18c57015788ac0000000001000000026139a62e3422a602de36c873a225c1d3ca5aeee598539ceecb9f0dc8d1ad0f83010000006b483045022100ad9f32b4a0a2ddc19b5a74eba78123e57616f1b3cfd72ce68c03ea35a3dda1f002200dbd22aa6da17213df5e70dfc3b2611d40f70c98ed9626aa5e2cde9d97461f0a012103ddb295d2f1e8319187738fb4b230fdd9aa29d0e01647f69f6d770b9ab24eea90ffffffff983c82c87cf020040d671956525014d5c2b28c6d948c85e1a522362c0059eeae010000006b4830450221009ca544274c786d30a5d5d25e17759201ea16d3aedddf0b9e9721246f7ef6b32e02202cfa5564b6e87dfd9fd98957820e4d4e6238baeb0f65fe305d91506bb13f5f4f012103c99113deac0d5d044e3ac0346abc02501542af8c8d3759f1382c72ff84e704f7ffffffff02c0c62d00000000001976a914ae19d27efe12f5a886dc79af37ad6805db6f922d88ac70ce2000000000001976a9143b8d051d37a07ea1042067e93efe63dbf73920b988ac000000000100000002be566e8cd9933f0c75c4a82c027f7d0c544d5c101d0607ef6ae5d07b98e7f1dc000000006b483045022036a8cdfd5ea7ebc06c2bfb6e4f942bbf9a1caeded41680d11a3a9f5d8284abad022100cacb92a5be3f39e8bc14db1710910ef7b395fa1e18f45d41c28d914fcdde33be012102bf59abf110b5131fae0a3ce1ec379329b4c896a6ae5d443edb68529cc2bc7816ffffffff96cf67645b76ceb23fe922874847456a15feee1655082ff32d25a6bf2c0dfc90000000006a47304402203471ca2001784a5ac0abab583581f2613523da47ec5f53df833c117b5abd81500220618a2847723d57324f2984678db556dbca1a72230fc7e39df04c2239942ba942012102925c9794fd7bb9f8b29e207d5fc491b1150135a21f505041858889fa4edf436fffffffff026c840f00000000001976a914797fb8777d7991d8284d88bfd421ce520f0f843188ac00ca9a3b000000001976a9146d10f3f592699265d10b106eda37c3ce793f7a8588ac00000000",["","","","76a9142903b138c24be9e070b3e73ec495d77a204615e788ac","76a91433a1941fd9a37b9821d376f5a51bd4b52fa50e2888ac","76a914e4374e8155d0865742ca12b8d4d14d41b57d682f88ac","76a914001fa7459a6cfc64bdc178ba7e7a21603bb2568f88ac","76a914f6039952bc2b307aeec5371bfb96b66078ec17f688ac"],"d34ef98386f413769502808d4bac5f20f8dfd5bffc9eedafaa71de0eb1f01489","0db414c859a07e8205876354a210a75042d0463404913d61a8e068e58a3ae2aa080026","c582d51c0ca365e3fcf36c51cb646d7f83a67e867cb4743fd2128e3e022b700c","Tx spends from empty output script"], [926485,"000000000000015d6077a411a8f5cc95caf775ccf11c54e27df75ce58d187313","0000002060bbab0edbf3ef8a49608ee326f8fd75c473b7e3982095e2d100000000000000c30134f8c9b6d2470488d7a67a888f6fa12f8692e0c3411fbfb92f0f68f67eedae03ca57ef13021acc22dc4105010000000001010000000000000000000000000000000000000000000000000000000000000000ffffffff2f0315230e0004ae03ca57043e3d1e1d0c8796bf579aef0c0000000000122f4e696e6a61506f6f6c2f5345475749542fffffffff038427a112000000001976a914876fbb82ec05caa6af7a3b5e5a983aae6c6cc6d688ac0000000000000000266a24aa21a9ed5c748e121c0fe146d973a4ac26fa4a68b0549d46ee22d25f50a5e46fe1b377ee00000000000000002952534b424c4f434b3acd16772ad61a3c5f00287480b720f6035d5e54c9efc71be94bb5e3727f10909001200000000000000000000000000000000000000000000000000000000000000000000000000100000000010145310e878941a1b2bc2d33797ee4d89d95eaaf2e13488063a2aa9a74490f510a0100000023220020b6744de4f6ec63cc92f7c220cdefeeb1b1bed2b66c8e5706d80ec247d37e65a1ffffffff01002d3101000000001976a9143ebc40e411ed3c76f86711507ab952300890397288ac0400473044022001dd489a5d4e2fbd8a3ade27177f6b49296ba7695c40dbbe650ea83f106415fd02200b23a0602d8ff1bdf79dee118205fc7e9b40672bf31563e5741feb53fb86388501483045022100f88f040e90cc5dc6c6189d04718376ac19ed996bf9e4a3c29c3718d90ffd27180220761711f16c9e3a44f71aab55cbc0634907a1fa8bb635d971a9a01d368727bea10169522103b3623117e988b76aaabe3d63f56a4fc88b228a71e64c4cc551d1204822fe85cb2103dd823066e096f72ed617a41d3ca56717db335b1ea47a1b4c5c9dbdd0963acba621033d7c89bd9da29fa8d44db7906a9778b53121f72191184a9fee785c39180e4be153ae00000000010000000120925534261de4dcebb1ed5ab1b62bfe7a3ef968fb111dc2c910adfebc6e3bdf010000006b483045022100f50198f5ae66211a4f485190abe4dc7accdabe3bc214ebc9ea7069b97097d46e0220316a70a03014887086e335fc1b48358d46cd6bdc9af3b57c109c94af76fc915101210316cff587a01a2736d5e12e53551b18d73780b83c3bfb4fcf209c869b11b6415effffffff0220a10700000000001976a91450333046115eaa0ac9e0216565f945070e44573988ac2e7cd01a000000001976a914c01a7ca16b47be50cbdbc60724f701d52d75156688ac00000000010000000203a25f58630d7a1ea52550365fd2156683f56daf6ca73a4b4bbd097e66516322010000006a47304402204efc3d70e4ca3049c2a425025edf22d5ca355f9ec899dbfbbeeb2268533a0f2b02204780d3739653035af4814ea52e1396d021953f948c29754edd0ee537364603dc012103f7a897e4dbecab2264b21917f90664ea8256189ea725d28740cf7ba5d85b5763ffffffff03a25f58630d7a1ea52550365fd2156683f56daf6ca73a4b4bbd097e66516322000000006a47304402202d96defdc5b4af71d6ba28c9a6042c2d5ee7bc6de565d4db84ef517445626e03022022da80320e9e489c8f41b74833dfb6a54a4eb5087cdb46eb663eef0b25caa526012103f7a897e4dbecab2264b21917f90664ea8256189ea725d28740cf7ba5d85b5763ffffffff0200e1f5050000000017a914b7e6f7ff8658b2d1fb107e3d7be7af4742e6b1b3876f88fc00000000001976a914913bcc2be49cb534c20474c4dee1e9c4c317e7eb88ac0000000001000000043ffd60d3818431c495b89be84afac205d5d1ed663009291c560758bbd0a66df5010000006b483045022100f344607de9df42049688dcae8ff1db34c0c7cd25ec05516e30d2bc8f12ac9b2f022060b648f6a21745ea6d9782e17bcc4277b5808326488a1f40d41e125879723d3a012103f7a897e4dbecab2264b21917f90664ea8256189ea725d28740cf7ba5d85b5763ffffffffa5379401cce30f84731ef1ba65ce27edf2cc7ce57704507ebe8714aa16a96b92010000006a473044022020c37a63bf4d7f564c2192528709b6a38ab8271bd96898c6c2e335e5208661580220435c6f1ad4d9305d2c0a818b2feb5e45d443f2f162c0f61953a14d097fd07064012103f7a897e4dbecab2264b21917f90664ea8256189ea725d28740cf7ba5d85b5763ffffffff70e731e193235ff12c3184510895731a099112ffca4b00246c60003c40f843ce000000006a473044022053760f74c29a879e30a17b5f03a5bb057a5751a39f86fa6ecdedc36a1b7db04c022041d41c9b95f00d2d10a0373322a9025dba66c942196bc9d8adeb0e12d3024728012103f7a897e4dbecab2264b21917f90664ea8256189ea725d28740cf7ba5d85b5763ffffffff66b7a71b3e50379c8e85fc18fe3f1a408fc985f257036c34702ba205cef09f6f000000006a4730440220499bf9e2db3db6e930228d0661395f65431acae466634d098612fd80b08459ee022040e069fc9e3c60009f521cef54c38aadbd1251aee37940e6018aadb10f194d6a012103f7a897e4dbecab2264b21917f90664ea8256189ea725d28740cf7ba5d85b5763ffffffff0200e1f5050000000017a9148fc37ad460fdfbd2b44fe446f6e3071a4f64faa6878f447f0b000000001976a914913bcc2be49cb534c20474c4dee1e9c4c317e7eb88ac00000000",["a914feb8a29635c56d9cd913122f90678756bf23887687","76a914c01a7ca16b47be50cbdbc60724f701d52d75156688ac","76a914913bcc2be49cb534c20474c4dee1e9c4c317e7eb88ac","76a914913bcc2be49cb534c20474c4dee1e9c4c317e7eb88ac","76a914913bcc2be49cb534c20474c4dee1e9c4c317e7eb88ac","76a914913bcc2be49cb534c20474c4dee1e9c4c317e7eb88ac","76a914913bcc2be49cb534c20474c4dee1e9c4c317e7eb88ac","76a914913bcc2be49cb534c20474c4dee1e9c4c317e7eb88ac"],"8f13b9a9c85611635b47906c3053ac53cfcec7211455d4cb0d63dc9acc13d472","09027acea61b6cc3fb33f5d52f7d088a6b2f75d234e89ca800","546c574a0472144bcaf9b6aeabf26372ad87c7af7d1ee0dbfae5e099abeae49c","Duplicate pushdata 913bcc2be49cb534c20474c4dee1e9c4c317e7eb"], [987876,"0000000000000c00901f2049055e2a437c819d79a3d54fd63e6af796cd7b8a79","000000202694f74969fdb542090e95a56bc8aa2d646e27033850e32f1c5f000000000000f7e53676b3f12d5beb524ed617f2d25f5a93b5f4f52c1ba2678260d72712f8dd0a6dfe5740257e1a4b1768960101000000010000000000000000000000000000000000000000000000000000000000000000ffffffff1603e4120ff9c30a1c216900002f424d4920546573742fffffff0001205fa012000000001e76a914c486de584a735ec2f22da7cd9681614681f92173d83d0aa68688ac00000000",[],"fe4d230dbb0f4fec9bed23a5283e08baf996e3f32b93f52c7de1f641ddfd04ad","010c0b40","0965a544743bbfa36f254446e75630c09404b3d164a261892372977538928ed5","Coinbase tx has unparseable output script"], [1263442,"000000006f27ddfe1dd680044a34548f41bed47eba9e6f0b310da21423bc5f33","000000201c8d1a529c39a396db2db234d5ec152fa651a2872966daccbde028b400000000083f14492679151dbfaa1a825ef4c18518e780c1f91044180280a7d33f4a98ff5f45765aaddc001d38333b9a02010000000001010000000000000000000000000000000000000000000000000000000000000000ffffffff230352471300fe5f45765afe94690a000963676d696e6572343208000000000000000000ffffffff024423a804000000001976a914f2c25ac3d59f3d674b1d1d0a25c27339aaac0ba688ac0000000000000000266a24aa21a9edcb26cb3052426b9ebb4d19c819ef87c19677bbf3a7c46ef0855bd1b2abe83491012000000000000000000000000000000000000000000000000000000000000000000000000002000000000101d20978463906ba4ff5e7192494b88dd5eb0de85d900ab253af909106faa22cc5010000000004000000014777ff000000000016001446c29eabe8208a33aa1023c741fa79aa92e881ff0347304402207d7ca96134f2bcfdd6b536536fdd39ad17793632016936f777ebb32c22943fda02206014d2fb8a6aa58279797f861042ba604ebd2f8f61e5bddbd9d3be5a245047b201004b632103eeaeba7ce5dc2470221e9517fb498e8d6bd4e73b85b8be655196972eb9ccd5566754b2752103a40b74d43df244799d041f32ce1ad515a6cd99501701540e38750d883ae21d3a68ac00000000",["002027a5000c7917f785d8fc6e5a55adfca8717ecb973ebb7743849ff956d896a7ed"],"31d66d516a9eda7de865df29f6ef6cb8e4bf9309e5dac899968a9a62a5df61e3","0385acb4f0fe889ef0","4e6d564c2a2452065c205dd7eb2791124e0c4e0dbb064c410c24968572589dec","Includes witness data"], [1414221,"0000000000000027b2b3b3381f114f674f481544ff2be37ae3788d7e078383b1","000000204ea88307a7959d8207968f152bedca5a93aefab253f1fb2cfb032a400000000070cebb14ec6dbc27a9dfd066d9849a4d3bac5f674665f73a5fe1de01a022a0c851fda85bf05f4c19a779d1450102000000010000000000000000000000000000000000000000000000000000000000000000ffffffff18034d94154d696e6572476174653030310d000000f238f401ffffffff01c817a804000000000000000000",[],"5e5e12d90693c8e936f01847859404c67482439681928353ca1296982042864e","00","021e8882ef5a0ed932edeebbecfeda1d7ce528ec7b3daa27641acf1189d7b5dc","Empty data"] ] ================================================ FILE: bip-0158.mediawiki ================================================
  BIP: 158
  Layer: Peer Services
  Title: Compact Block Filters for Light Clients
  Authors: Olaoluwa Osuntokun 
           Alex Akselrod 
  Status: Deployed
  Type: Specification
  Assigned: 2017-05-24
  License: CC0-1.0
  Requires: 157
== Abstract == This BIP describes a structure for compact filters on block data, for use in the BIP 157 light client protocolbip-0157.mediawiki. The filter construction proposed is an alternative to Bloom filters, as used in BIP 37, that minimizes filter size by using Golomb-Rice coding for compression. This document specifies one initial filter type based on this construction that enables basic wallets and applications with more advanced smart contracts. == Motivation == [[bip-0157.mediawiki|BIP 157]] defines a light client protocol based on deterministic filters of block content. The filters are designed to minimize the expected bandwidth consumed by light clients, downloading filters and full blocks. This document defines the initial filter type ''basic'' that is designed to reduce the filter size for regular wallets. == Definitions == []byte represents a vector of bytes. [N]byte represents a fixed-size byte array with length N. ''CompactSize'' is a compact encoding of unsigned integers used in the Bitcoin P2P protocol. ''Bit streams'' are readable and writable streams of individual bits. The following functions are used in the pseudocode in this document: * new_bit_stream instantiates a new writable bit stream * new_bit_stream(vector) instantiates a new bit stream reading data from vector * write_bit(stream, b) appends the bit b to the end of the stream * read_bit(stream) reads the next available bit from the stream * write_bits_big_endian(stream, n, k) appends the k least significant bits of integer n to the end of the stream in big-endian bit order * read_bits_big_endian(stream, k) reads the next available k bits from the stream and interprets them as the least significant bits of a big-endian integer The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED", "MAY", and "OPTIONAL" in this document are to be interpreted as described in RFC 2119. == Specification == === Golomb-Coded Sets === For each block, compact filters are derived containing sets of items associated with the block (eg. addresses sent to, outpoints spent, etc.). A set of such data objects is compressed into a probabilistic structure called a ''Golomb-coded set'' (GCS), which matches all items in the set with probability 1, and matches other items with probability 1/M for some integer parameter M. The encoding is also parameterized by P, the bit length of the remainder code. Each filter defined specifies values for P and M. At a high level, a GCS is constructed from a set of N items by: # hashing all items to 64-bit integers in the range [0, N * M) # sorting the hashed values in ascending order # computing the differences between each value and the previous one # writing the differences sequentially, compressed with Golomb-Rice coding The following sections describe each step in greater detail. ==== Hashing Data Objects ==== The first step in the filter construction is hashing the variable-sized raw items in the set to the range [0, F), where F = N * M. Customarily, M is set to 2^P. However, if one is able to select both Parameters independently, then more optimal values can be selectedhttps://gist.github.com/sipa/576d5f09c3b86c3b1b75598d799fc845. Set membership queries against the hash outputs will have a false positive rate of 1 / M. To avoid integer overflow, the number of items N MUST be <2^32 and M MUST be <2^32. The items are first passed through the pseudorandom function ''SipHash'', which takes a 128-bit key k and a variable-sized byte vector and produces a uniformly random 64-bit output. Implementations of this BIP MUST use the SipHash parameters c = 2 and d = 4. The 64-bit SipHash outputs are then mapped uniformly over the desired range by multiplying with F and taking the top 64 bits of the 128-bit result. This algorithm is a faster alternative to modulo reduction, as it avoids the expensive division operationhttps://lemire.me/blog/2016/06/27/a-fast-alternative-to-the-modulo-reduction/. Note that care must be taken when implementing this reduction to ensure the upper 64 bits of the integer multiplication are not truncated; certain architectures and high level languages may require code that decomposes the 64-bit multiplication into four 32-bit multiplications and recombines into the result.
hash_to_range(item: []byte, F: uint64, k: [16]byte) -> uint64:
    return (siphash(k, item) * F) >> 64

hashed_set_construct(raw_items: [][]byte, k: [16]byte, M: uint) -> []uint64:
    let N = len(raw_items)
    let F = N * M

    let set_items = []

    for item in raw_items:
        let set_value = hash_to_range(item, F, k)
        set_items.append(set_value)

    return set_items
==== Golomb-Rice Coding ==== Instead of writing the items in the hashed set directly to the filter, greater compression is achieved by only writing the differences between successive items in sorted order. Since the items are distributed uniformly, it can be shown that the differences resemble a geometric distributionhttps://en.wikipedia.org/wiki/Geometric_distribution. ''Golomb-Rice'' ''coding''https://en.wikipedia.org/wiki/Golomb_coding#Rice_coding is a technique that optimally compresses geometrically distributed values. With Golomb-Rice, a value is split into a quotient and remainder modulo 2^P, which are encoded separately. The quotient q is encoded as ''unary'', with a string of q 1's followed by one 0. The remainder r is represented in big-endian by P bits. For example, this is a table of Golomb-Rice coded values using P=2: {| class="wikitable" ! n !! (q, r) !! c |- | 0 || (0, 0) || 0 00 |- | 1 || (0, 1) || 0 01 |- | 2 || (0, 2) || 0 10 |- | 3 || (0, 3) || 0 11 |- | 4 || (1, 0) || 10 00 |- | 5 || (1, 1) || 10 01 |- | 6 || (1, 2) || 10 10 |- | 7 || (1, 3) || 10 11 |- | 8 || (2, 0) || 110 00 |- | 9 || (2, 1) || 110 01 |}
golomb_encode(stream, x: uint64, P: uint):
    let q = x >> P

    while q > 0:
        write_bit(stream, 1)
        q--
    write_bit(stream, 0)

    write_bits_big_endian(stream, x, P)

golomb_decode(stream, P: uint) -> uint64:
    let q = 0
    while read_bit(stream) == 1:
        q++

    let r = read_bits_big_endian(stream, P)

    let x = (q << P) + r
    return x
==== Set Construction ==== A GCS is constructed from four parameters: * L, a vector of N raw items * P, the bit parameter of the Golomb-Rice coding * M, the inverse of the target false positive rate * k, the 128-bit key used to randomize the SipHash outputs The result is a byte vector with a minimum size of N * (P + 1) bits. The raw items in L are first hashed to 64-bit unsigned integers as specified above and sorted. The differences between consecutive values, hereafter referred to as ''deltas'', are encoded sequentially to a bit stream with Golomb-Rice coding. Finally, the bit stream is padded with 0's to the nearest byte boundary and serialized to the output byte vector.
construct_gcs(L: [][]byte, P: uint, k: [16]byte, M: uint) -> []byte:
    let set_items = hashed_set_construct(L, k, M)

    set_items.sort()

    let output_stream = new_bit_stream()

    let last_value = 0
    for item in set_items:
        let delta = item - last_value
        golomb_encode(output_stream, delta, P)
        last_value = item

    return output_stream.bytes()
==== Set Querying/Decompression ==== To check membership of an item in a compressed GCS, one must reconstruct the hashed set members from the encoded deltas. The procedure to do so is the reverse of the compression: deltas are decoded one by one and added to a cumulative sum. Each intermediate sum represents a hashed value in the original set. The queried item is hashed in the same way as the set members and compared against the reconstructed values. Note that querying does not require the entire decompressed set be held in memory at once.
gcs_match(key: [16]byte, compressed_set: []byte, target: []byte, P: uint, N: uint, M: uint) -> bool:
    let F = N * M
    let target_hash = hash_to_range(target, F, k)

    stream = new_bit_stream(compressed_set)

    let last_value = 0

    loop N times:
        let delta = golomb_decode(stream, P)
        let set_item = last_value + delta

        if set_item == target_hash:
            return true

        // Since the values in the set are sorted, terminate the search once
        // the decoded value exceeds the target.
        if set_item > target_hash:
            break

        last_value = set_item

    return false
Some applications may need to check for set intersection instead of membership of a single item. This can be performed far more efficiently than checking each item individually by leveraging the sorted structure of the compressed GCS. First the query elements are all hashed and sorted, then compared in order against the decompressed GCS contents. See [[#golomb-coded-set-multi-match|Appendix B]] for pseudocode. === Block Filters === This BIP defines one initial filter type: * Basic (0x00) ** M = 784931 ** P = 19 ==== Contents ==== The basic filter is designed to contain everything that a light client needs to sync a regular Bitcoin wallet. A basic filter MUST contain exactly the following items for each transaction in a block: * The previous output script (the script being spent) for each input, except for the coinbase transaction. * The scriptPubKey of each output, aside from all OP_RETURN output scripts. Any "nil" items MUST NOT be included into the final set of filter elements. We exclude all outputs that start with OP_RETURN in order to allow filters to easily be committed to in the future via a soft-fork. A likely area for future commitments is an additional OP_RETURN output in the coinbase transaction similar to the current witness commitment https://github.com/bitcoin/bips/blob/master/bip-0141.mediawiki. By excluding all OP_RETURN outputs we avoid a circular dependency between the commitment, and the item being committed to. ==== Construction ==== The basic type is constructed as Golomb-coded sets with the following parameters. The parameter P MUST be set to 19, and the parameter M MUST be set to 784931. Analysis has shown that if one is able to select P and M independently, then setting M=1.497137 * 2^P is close to optimal https://gist.github.com/sipa/576d5f09c3b86c3b1b75598d799fc845. Empirical analysis also shows that these parameters minimize the bandwidth utilized, considering both the expected number of blocks downloaded due to false positives and the size of the filters themselves. The parameter k MUST be set to the first 16 bytes of the hash (in standard little-endian representation) of the block for which the filter is constructed. This ensures the key is deterministic while still varying from block to block. Since the value N is required to decode a GCS, a serialized GCS includes it as a prefix, written as a CompactSize. Thus, the complete serialization of a filter is: * N, encoded as a CompactSize * The bytes of the compressed filter itself A zero element filter MUST be written as one byte containing zeroes. ==== Signaling ==== This BIP allocates a new service bit: {| class="wikitable" |- | NODE_COMPACT_FILTERS | style="white-space: nowrap;" | 1 << 6 | If enabled, the node MUST respond to all BIP 157 messages for filter type 0x00 |} == Compatibility == This block filter construction is not incompatible with existing software, though it requires implementation of the new filters. == Acknowledgments == We would like to thank bfd (from the bitcoin-dev mailing list) for bringing the basis of this BIP to our attention, Greg Maxwell for pointing us in the direction of Golomb-Rice coding and fast range optimization, Pieter Wullie for his analysis of optimal GCS parameters, and Pedro Martelletto for writing the initial indexing code for btcd. We would also like to thank Dave Collins, JJ Jeffrey, and Eric Lombrozo for useful discussions. == Reference Implementation == Light client: [https://github.com/lightninglabs/neutrino] Full-node indexing: https://github.com/Roasbeef/btcd/tree/segwit-cbf Golomb-Rice Coded sets: https://github.com/btcsuite/btcd/tree/master/btcutil/gcs == Appendix A: Alternatives == A number of alternative set encodings were considered before Golomb-coded sets were settled upon. In this appendix section, we'll list a few of the alternatives along with our rationale for not pursuing them. ==== Bloom Filters ==== Bloom Filters are perhaps the best known probabilistic data structure for testing set membership, and were introduced into the Bitcoin protocol with BIP 37. The size of a Bloom filter is larger than the expected size of a GCS with the same false positive rate, which is the main reason the option was rejected. ==== Cryptographic Accumulators ==== Cryptographic accumulatorshttps://en.wikipedia.org/wiki/Accumulator_(cryptography) are a cryptographic data structures that enable (amongst other operations) a one way membership test. One advantage of accumulators are that they are constant size, independent of the number of elements inserted into the accumulator. However, current constructions of cryptographic accumulators require an initial trusted set up. Additionally, accumulators based on the Strong-RSA Assumption require mapping set items to prime representatives in the associated group which can be preemptively expensive. ==== Matrix Based Probabilistic Set Data Structures ==== There exist data structures based on matrix solving which are even more space efficient compared to Bloom filtershttps://arxiv.org/pdf/0804.1845.pdf. We instead opted for our GCS-based filters as they have a much lower implementation complexity and are easier to understand. == Appendix B: Pseudocode == === Golomb-Coded Set Multi-Match ===
gcs_match_any(key: [16]byte, compressed_set: []byte, targets: [][]byte, P: uint, N: uint, M: uint) -> bool:
    let F = N * M

    // Map targets to the same range as the set hashes.
    let target_hashes = []
    for target in targets:
        let target_hash = hash_to_range(target, F, k)
        target_hashes.append(target_hash)

    // Sort targets so matching can be checked in linear time.
    target_hashes.sort()

    stream = new_bit_stream(compressed_set)

    let value = 0
    let target_idx = 0
    let target_val = target_hashes[target_idx]

    loop N times:
        let delta = golomb_decode(stream, P)
        value += delta

        inner loop:
            if target_val == value:
                return true

            // Move on to the next set value.
            else if target_val > value:
                break inner loop

            // Move on to the next target value.
            else if target_val < value:
                target_idx++

                // If there are no targets left, then there are no matches.
                if target_idx == len(targets):
                    break outer loop

                target_val = target_hashes[target_idx]

    return false
== Appendix C: Test Vectors == Test vectors for basic block filters on five testnet blocks, including the filters and filter headers, can be found [[bip-0158/testnet-19.json|here]]. The code to generate them can be found [[bip-0158/gentestvectors.go|here]]. == References == == Copyright == This document is licensed under the Creative Commons CC0 1.0 Universal license. ================================================ FILE: bip-0159.mediawiki ================================================
  BIP: 159
  Layer: Peer Services
  Title: NODE_NETWORK_LIMITED service bit
  Authors: Jonas Schnelli 
  Status: Deployed
  Type: Specification
  Assigned: 2017-05-11
  License: BSD-2-Clause
== Abstract == Define a service bit that allows pruned peers to signal their limited services. ==Motivation== Pruned peers can offer the same services as traditional peers, except that of serving all historical blocks. Bitcoin right now only offers the NODE_NETWORK service bit to indicate that a peer can serve all historical blocks. # Pruned peers can relay blocks, headers, transactions, and addresses, but they only guarantee serving a minimum number of historical blocks; thus, they should have a way to announce their service(s) # Peers no longer in initial block download should consider connecting some of their outbound connections to pruned peers, to allow other peers to bootstrap from non-pruned peers == Specification == === New service bit === This BIP proposes a new service bit {|class="wikitable" |- | NODE_NETWORK_LIMITED || bit 10 (0x400) || If signaled, the peer MUST be capable of serving at least the last 288 blocks (~2 days). |} Pruned/limited peers MUST NOT set a service bit that signals serving the complete block chain (e.g., NODE_NETWORK). Rationale: nodes that signal serving the complete block chain may also signal NODE_NETWORK_LIMITED. A safety buffer of 144 blocks to handle chain reorganizations SHOULD be taken into account when connecting to a peer signaling the NODE_NETWORK_LIMITED service bit. === Address relay === Full nodes following this BIP SHOULD relay address/services (addr message) from peers they would connect to (including peers signaling NODE_NETWORK_LIMITED). === Counter-measures for peer fingerprinting === Peers may have different prune depths (depending on their configuration, disk space, etc.), which can result in a fingerprinting weakness (finding the prune depth through getdata requests). Pruned nodes should therefore avoid leaking the prune depth and SHOULD NOT serve blocks deeper than the signaled NODE_NETWORK_LIMITED threshold of 288 blocks. === Risks === Pruned peers following this BIP may consume more outbound bandwidth. Light clients (and such) who are not checking the nServiceFlags (service bits) from a relayed addr-message may unwittingly connect to a pruned peer and ask for (filtered) blocks at a depth below the peer’s pruned depth. Light clients should therefore check the service bits and either (1) connect to peers signaling NODE_NETWORK_LIMITED that preferably do not also signal serving the full block chain, if they only require (filtered) blocks around the tip, or (2) connect to peers signaling serving the full block chain if they need data older than the latest 288 blocks. Light clients obtaining peer IPs through DNS seeds should use the DNS filtering option. == Compatibility == This proposal is backward compatible. == Reference implementation == * https://github.com/bitcoin/bitcoin/pull/11740 (signaling) * https://github.com/bitcoin/bitcoin/pull/10387 (connection and relay) == Copyright == This BIP is licensed under the 2-clause BSD license. ================================================ FILE: bip-0171.mediawiki ================================================
  BIP: 171
  Layer: Applications
  Title: Currency/exchange rate information API
  Authors: Luke Dashjr 
  Comments-Summary: No comments yet.
  Comments-URI: https://github.com/bitcoin/bips/wiki/Comments:BIP-0171
  Status: Closed
  Type: Specification
  Assigned: 2017-03-04
  License: BSD-2-Clause
==Abstract== A common interface for requesting currency exchange rate information from a server. ==Copyright== This BIP is licensed under the BSD 2-clause license. ==Specification== Four requests are defined, which are all made by a GET request to a common URI with parameters encoded in application/x-www-form-urlencoded format. All matching parameters may be specified with multiple comma-separated values, which are to be interpreted as "any of these". Each result is always in JSON format, with a line-feed (never a carriage-return) separating multiple results. Authentication for subscription-based services MAY be supported using standard HTTP authentication. It is recommended to use TLS (HTTPS) and/or Linked Data Signatures, so that MITM attackers cannot deceive the client. To be BIP 171 compatible, servers MUST support at least one currency-pair compared to XBT. All inquiries for bitcoin amounts MUST be specified in XBT, even if the presentation to the end user is in another unit. (FIXME: or should this be satoshis?) Currency-pair tokens are arbitrary Strings no longer than 255 characters, which may include any ASCII [https://tools.ietf.org/html/rfc3986#section-2.3 RFC 3986 unreserved characters] (ie, alphanumerics and the hyphen, underscore, period, and tilde symbols). Currency code(s) used herein are defined as such: * All ISO 4217 codes are valid currency codes. * XBT is defined as 100000000 satoshis (commonly known as 1 BTC). * Strings longer than 3 characters may be used for currencies without an applicable code. (If a shorter code is desired despite this, it may be padded with space(s) to the left until it is 4 characters. Software MAY strip these spaces.) Rate is defined as the amount of quote-currency to be exchanged for one unit of the base-currency. In other words, 1 baseCurrency = rate quoteCurrency. ===Enumerating supported currency-pair tokens=== Parameters: * ''mode'' - Always "list" for this request. * ''quote'' - If provided, the server MAY limit the results to only currency-pairs describing a currency with the given currency code(s). * ''base'' - If provided, the server MAY limit the results to only currency-pairs describing currency rates compared to the given currency code(s). * ''locale'' - If provided, the server MAY limit the results to only currency-pairs supporting the given Unicode CLDR locale(s). Each currency-pair will receive a separate result, a JSON Object, with the following information: * ''cp'' - The currency-pair token. * ''quote'' - The currency code for the quote currency. * ''base'' - The currency code for the base currency. * ''locale'' - If provided, a String with the applicable Unicode CLDR locale. * ''desc'' - Optional description. For example, it could be "Based on Florida BTM prices." or any other short String that provides information useful to the user. SHOULD be shorter than 45 characters. * ''signature'' - Optional. May be used for Linked Data Signatures. Example: Request: http://api.example.tld/?mode=list"e=USD&base=XBT&locale=en_US,en_GB Result: {"cp":"XBTUSD-ver4", "quote":"USD", "base": "XBT", "locale": "en_US", "desc": "Smoothed averages"} {"cp":"2", "quote":"USD", "base": "XBT", "locale": "en_US", "desc": "Updated per-trade"} {"cp":"XBTUSD-european", "quote":"USD", "base": "XBT", "locale": "en_GB"} ===Currency-pair information=== Parameters: * ''mode'' - Always "info" for this request. * ''cp'' - Currency pair(s) for which information is requested. Each currency-pair will receive a separate result, a JSON Object, with the following information: * ''cp'' - The currency-pair token. * ''quote'' - The currency code for the quote currency. * ''base'' - The currency code for the base currency. * ''locale'' - If provided, a String with the applicable Unicode CLDR locale. * ''desc'' - Optional description. For example, it could be "Based on Florida BTM prices." or any other short String that provides information useful to the user. SHOULD be shorter than 45 characters. * ''longdesc'' - Optional description, but may be longer and include newlines. * ''symbol'' - An Array of prefix and suffix for the quote currency. Each may be either a fixed String, an Array of two Strings (negative and positive), or null. Any positive or negative symbols must be included in this prefix/suffix; it MUST NOT be implied otherwise. * ''digits'' - The type of digits to use for the quote currency's numbers. "arabic" should be used for common 0-9 digits. * ''grouping'' - An Array alternating between Numbers representing a series of digits, and Strings used as delimiters. If terminated by a zero, the final grouping is to be repeated continually. For example, the common US locale thousands grouping would be [3, ",", 0] * ''fraction_sep'' - A String to be placed between whole numbers and a fractional amount. * ''fraction_digits'' - Array of absolute minimum (even for whole numbers) number of fractional digits, minimum fractional digits when a fraction exists, and maximum number of fractional digits when absolute precision is not demanded (below which is to be rounded in an implementation-dependent manner). * ''minpoll'' - A Number of seconds indicating a minimum time between polls to the server. Clients should be prudent about not polling too often, even if this number is low. * ''longpoll'' - If provided and true, indicates longpolling is supported by the server. * ''history'' - If provided, indicates the server has historical records going back no earlier than the POSIX timestamp provided as a value. * ''archive'' - If provided, indicates the server no longer has current rates, and has no historical rates more recent than the POSIX timestamp provided as a value. * ''signature'' - Optional. May be used for Linked Data Signatures. Example: Request: http://api.example.tld/?mode=info&cp=XBTUSD-ver4,2 Result: {"cp":"XBTUSD-ver4", "quote":"USD", "base": "XBT", "locale": "en_US", "desc": "Smoothed averages", "longdesc": "USD price quotes as compared to Bitcoin value\n\nRecommended for casual usage", "symbol": [["-$", "$"], null], "digits": "arabic", "grouping": [3, ",", 0], "fraction_sep": ".", "fraction_digits": [0, 2, 2], "minpoll": 300, "longpoll": true, "history": 1457231416} {"cp":"2", "quote":"USD", "base": "XBT", "locale": "en_US", "desc": "Updated per-trade", "longdesc": "Maximum precision USD price quotes as compared to Bitcoin value", "symbol": [["-$", "$"], null], "digits": "arabic", "grouping": [3, ",", 0], "fraction_sep": ".", "fraction_digits": [0, 2, 2], "minpoll": 3600, "longpoll": false, "history": 1467458333.1225} ===Current exchange rate=== Parameters: * ''mode'' - Always "rate" for this request. * ''cp'' - Currency pair(s) for which rate is requested. * ''type'' - Type of exchange rate data being requested. May be "high", "low", "average", "typical", or any other arbitrary name. If omitted, the server may provide any rates it deems appropriate. * ''minrate'', ''maxrate'' - If specified, indicates this request is a longpoll. The server should not send a response until the rate(s) fall below or above (respectively) the provided value. * ''nonce'' - If specified, the server SHOULD return it in each result. Each currency-pair receives a separate result (a JSON Object) with all requested rate types: * ''cp'' - The currency-pair token. * ''time'' - The time (as a POSIX timestamp) the rate information is applicable to (should be approximately the request time). * ''rates'' - A JSON Object with each rate type provided as a key, and a Number as the value specifying the rate. * ''nonce'' - Only if the request specified a nonce, the server SHOULD include it here as a JSON String. * ''signature'' - Optional. May be used for Linked Data Signatures. Example: Request: http://api.example.tld/?mode=rate&cp=XBTUSD-ver4,2&type=typical,high Result: {"cp":"XBTUSD-ver4", "time": 1488767410.5463133, "rates": {"typical": 1349.332215, "high": 1351.2}} {"cp":"2", "time": 1488767410, "rates": {"typical": 1350.111332}} ===Historical exchange rates=== Parameters: * ''mode'' - Always "history" for this request. * ''cp'' - Currency pair(s) for which rate is requested. * ''type'' - Type of exchange rate data being requested. May be "high", "low", "average", "typical", or any other arbitrary name. If omitted, the server may provide any rates it deems appropriate. * ''from'' - POSIX timestamp the results should begin with. * ''to'' - POSIX timestamp the results should end with. If omitted, the present time shall be used. * ''nearest'' - If provided and true, indicates that only the nearest timestamp to "from" must be returned, and a range is not desired. ("to" should be omitted in this case.) * ''ratedelta'', ''timedelta'' - If specified, the server may omit data where the rate or time has not changed since the last provided rate and time. If both are provided, either a significant rate change OR time change should trigger a new record in the results. A result is provided for each currency-pair and timestamp record, in the same format as the current exchange rate request. Records MUST be provided in chronological order, but only within the scope of the applicable currency-pair (ie, it is okay to send the full history for one currency-pair, and then the full history for the next; or to intermix them out of any given order). If there is no exact record for the times specified by "from" and/or "to", a single record before "from" and/or after "to" should also be included. This is not necessary when only the nearest record is requested, or when "to" is omitted (ie, ending at the most recent record). Example: Request: http://api.example.tld/?mode=history&cp=XBTUSD-ver4,2&type=typical&ratedelta=0.1&timedelta=10&from=1488759998&to=1488760090 Result: {"cp":"XBTUSD-ver4", "time": 1488760000, "rates": {"typical": 1300}} {"cp":"XBTUSD-ver4", "time": 1488760010, "rates": {"typical": 1301.1}} {"cp":"XBTUSD-ver4", "time": 1488760020, "rates": {"typical": 1320}} {"cp":"XBTUSD-ver4", "time": 1488760030, "rates": {"typical": 1305}} {"cp":"2", "time": 1488760000.1, "rates": {"typical": 1300}} {"cp":"2", "time": 1488760010.2, "rates": {"typical": 1301.1}} {"cp":"2", "time": 1488760020.2, "rates": {"typical": 1320.111332}} {"cp":"2", "time": 1488760031, "rates": {"typical": 1305.222311}} {"cp":"XBTUSD-ver4", "time": 1488760040, "rates": {"typical": 1303.33}} {"cp":"2", "time": 1488760042, "rates": {"typical": 1303.33}} {"cp":"XBTUSD-ver4", "time": 1488760050, "rates": {"typical": 1305}} {"cp":"2", "time": 1488760052, "rates": {"typical": 1307}} {"cp":"XBTUSD-ver4", "time": 1488760060, "rates": {"typical": 1309}} {"cp":"XBTUSD-ver4", "time": 1488760072, "rates": {"typical": 1308}} {"cp":"2", "time": 1488760062, "rates": {"typical": 1309.55555555}} {"cp":"2", "time": 1488760072, "rates": {"typical": 1308}} {"cp":"XBTUSD-ver4", "time": 1488760082, "rates": {"typical": 1309}} {"cp":"2", "time": 1488760082, "rates": {"typical": 1309.1}} ==Motivation== End users often desire to see fiat currency information in their Bitcoin wallet software. Due to the nature of Bitcoin, there is inherently no authoritative source for exchange rates. There are many independent providers of such information, but they all use different formats for providing it, so wallet software is currently forced to implement dedicated code for each provider. By providing a standard interface for retrieving this information, wallets (and other software) and service providers can implement it once, and become immediately interoperable with all other compatible implementations. ==Rationale== Why are multiple results separated by a line-feed rather than using a JSON Array? * Clients ought to cache historical data, and using a line-feed format allows them to simply append to a cache file. * Parsing JSON typically requires the entire data parsed together as a single memory object. Using simple lines to separate results, however, allows parsing a single result at a time. What if long descriptions require line and paragraph breaks? * Clients should word-wrap long lines, and JSON escapes newlines as "\n" which can be used doubly ("\n\n") for paragraph breaks. ==Backwards compatibility== While this new standard is adopted, software and providers can continue to use and provide their current formats until they are no longer needed. ==Reference implementation== TODO ==See also== * [https://w3c-dvcg.github.io/ld-signatures/ Draft W3c Linked Data Signatures specification] ================================================ FILE: bip-0172.mediawiki ================================================
  BIP: 172
  Layer: Applications
  Title: Define Bitcoin Subunits as Satoshis
  Authors: OceanSlim 
  Comments-Summary: No comments yet.
  Comments-URI: https://github.com/bitcoin/bips/wiki/Comments:BIP-0172
  Status: Draft
  Type: Informational
  Assigned: 2025-05-01
  License: BSD-2-Clause
== Abstract == This BIP proposes to formally define and standardize Bitcoin's smallest indivisible unit (1/100,000,000 of a bitcoin) as "satoshi" (singular) or "satoshis" (plural), with "sats" as the standard abbreviated form. This standardization aims to improve clarity in communication, user interfaces, documentation, and development across the Bitcoin ecosystem. == Motivation == As Bitcoin adoption grows, the need for a clear, standardized terminology for its subunits becomes increasingly important. Currently, there are various terms used to refer to Bitcoin's smallest unit (1/100,000,000 BTC), including "satoshi", "satoshis", "sat", "sats" and sometimes simply expressed as decimal values of bitcoin (0.00000001 BTC). This lack of standardization can lead to: # Confusion for newcomers to the Bitcoin ecosystem # Inconsistent user experiences across different applications and services # Ambiguity in technical documentation and discussions # Potential errors in development and implementation of Bitcoin-related software By formally establishing "satoshi"/"satoshis" as the standard term with "sats" as the recognized abbreviation, we can improve clarity and consistency throughout the ecosystem. == Specification == This BIP formally defines: # The term "satoshi" (singular) or "satoshis" (plural) shall be the standard term for 1/100,000,000 of a bitcoin (0.00000001 BTC). # The abbreviation "sat" (singular) or "sats" (plural) shall be the standard short form for "satoshi"/"satoshis". # The relationship between units shall be expressed as: #* 1 bitcoin (BTC) = 100,000,000 satoshis #* 1 satoshi = 0.00000001 bitcoin # The terms "satoshi" and "sats" are not proper nouns when referring to the unit of currency and should not be capitalized except at the beginning of sentences or in titles. # Bitcoin-related applications, services, documentation, and communications are encouraged to use these standardized terms to promote consistency across the ecosystem. == Accessibility Considerations == To ensure clarity and inclusiveness in user interfaces and assistive technologies, the following recommendations apply: # Pronunciation: #* The abbreviation "sat" should be pronounced as /sæt/, and "sats" (plural) should be pronounced as /sæts/ (rhyming with "cats") by screen readers and voice assistants. #* "Satoshi" (singular) is pronounced /səˈtoʊʃi/. "Satoshis" (plural) is pronounced /səˈtoʊʃiz/. # Singular vs. Plural: Preserve correct pluralization when reading amounts: #* "1 sat" should be read as "one satoshi" (/wʌn səˈtoʊʃi/) #* "100 sats" should be read as "one hundred satoshis" (/wʌn ˈhʌndrəd səˈtoʊʃiz/) # Readable Formats: #* Prefer full terms in accessibility modes (e.g., "satoshis" instead of "sats") #* Group digits to assist parsing (e.g., "12,345" instead of "12345") # Contextual Labels: #* Interfaces should use clear alt-text or aria-labels such as: alt="Transaction fee: 14 satoshis per virtual byte" #* This enables screen readers and other assistive technologies to accurately interpret and communicate the content == Rationale == Satoshi Nakamoto, the creator of Bitcoin, established that one bitcoin would be divisible to eight decimal places, creating 100,000,000 units per bitcoin. The community has organically adopted the term "satoshi" to refer to this smallest unit. As Bitcoin's value has increased, expressing smaller values in fractional bitcoins has become increasingly unwieldy (e.g., 0.00000546 BTC). Using satoshis as the unit of account for smaller values (e.g., 546 sats) is more intuitive and less error-prone for humans. The term "satoshi" and its abbreviation "sats" have already gained widespread adoption within the Bitcoin community. This BIP seeks to formalize this existing convention rather than introduce new terminology. === Analogous to Traditional Currency Systems === The proposed bitcoin/satoshi (or BTC/sat) standard follows the established pattern of major world currencies, which typically have a primary unit and a smaller subunit. Most notably, the United States dollar—the world's primary reserve currency—uses dollars and cents in a two-tier denomination system. This familiar dollars/cents model has proven effective and intuitive for everyday transactions across different scales. The bitcoin/satoshi system mirrors this approach while accounting for Bitcoin's higher divisibility requirements. Furthermore, the phonetic similarity between "sat" and "cent" creates an intuitive bridge for newcomers to understand Bitcoin's smallest unit, making the learning curve less steep for those familiar with traditional currency systems. This natural familiarity leverages existing mental models of how currency denominations work. === Comparison with Alternative Approaches === Two notable proposals related to Bitcoin denomination have been put forward: Our proposal represents a minimally disruptive approach to standardization, formalizing existing common practice rather than introducing new terms (BIP-176) or redefining existing ones (BIP-177). ==== BIP-176: Bits Denomination ==== BIP-176 proposes using "bits" as a standard term for 100 satoshis (or 0.000001 BTC). While this proposal has merit for creating a middle-ground denomination that avoids small decimal places when bitcoin's value is high, our approach differs in that it: * Formalizes existing widely adopted terminology rather than introducing or prioritizing a different unit * Focuses on the fundamental base unit that cannot be subdivided further within the Bitcoin protocol * Maintains the simplicity of a two-tier system (bitcoin and satoshi) rather than adding a third tier ==== BIP-177: Redefine Bitcoin's Base Unit ==== BIP-177 takes a more radical approach by proposing to redefine the term "bitcoin" to refer to what is currently called a "satoshi" (1/100,000,000 of the current bitcoin). While this proposal aims to eliminate decimal points and simplify mental calculations, our approach differs in that it: * Preserves the established meaning of "bitcoin" which has global recognition and avoids potentially confusing redefinition * Maintains compatibility with existing systems, documentation, and user understanding * Achieves similar clarity benefits through standardization without requiring a fundamental redefinition of terms == Backwards Compatibility == This proposal does not affect the technical operation of Bitcoin or its protocol. It is purely a standardization of terminology for human communication and user interfaces. Existing applications that use other terms or conventions can continue to operate but are encouraged to adopt the standardized terms to improve overall ecosystem clarity. == Copyright == This BIP is licensed under the BSD 2-clause license. == Reference Implementation == Not applicable as this is an Informational BIP that standardizes terminology rather than implementing technical changes. == Examples == Before standardization, various formats might be used: * 0.00000100 BTC * 100 satoshi * 100 satoshis * 100 sat * 100 sats After standardization, the preferred formats would be: * 100 satoshis (formal) * 100 sats (abbreviated) == Acknowledgements == Thanks to the entire Bitcoin community who has organically adopted the terms "satoshi" and "sats" over the years. If anyone can point to early references of the term being used in this way please leave a comment so we can amend this BIP to acknowledge it. == References == # Satoshi Nakamoto. "Bitcoin: A Peer-to-Peer Electronic Cash System" (2008) # BIP-176: Bits Denomination (Jimmy Song) == Glossary == * BTC: The current universal ticker symbol for bitcoin, the cryptocurrency. * Satoshi: The smallest unit of bitcoin, equal to 0.00000001 BTC. * Sats: Abbreviation for "satoshis". ================================================ FILE: bip-0173.mediawiki ================================================
  BIP: 173
  Layer: Applications
  Title: Base32 address format for native v0-16 witness outputs
  Authors: Pieter Wuille 
           Greg Maxwell 
  Comments-Summary: No comments yet.
  Comments-URI: https://github.com/bitcoin/bips/wiki/Comments:BIP-0173
  Status: Deployed
  Type: Informational
  Assigned: 2017-03-20
  License: BSD-2-Clause
  Replaces: 142
  Proposed-Replacement: 350
==Introduction== ===Abstract=== This document proposes a checksummed base32 format, "Bech32", and a standard for native segregated witness output addresses using it. ===Copyright=== This BIP is licensed under the 2-clause BSD license. ===Motivation=== For most of its history, Bitcoin has relied on base58 addresses with a truncated double-SHA256 checksum. They were part of the original software and their scope was extended in [https://github.com/bitcoin/bips/blob/master/bip-0013.mediawiki BIP13] for Pay-to-script-hash ([https://github.com/bitcoin/bips/blob/master/bip-0016.mediawiki P2SH]). However, both the character set and the checksum algorithm have limitations: * Base58 needs a lot of space in QR codes, as it cannot use the ''alphanumeric mode''. * The mixed case in base58 makes it inconvenient to reliably write down, type on mobile keyboards, or read out loud. * The double SHA256 checksum is slow and has no error-detection guarantees. * Most of the research on error-detecting codes only applies to character-set sizes that are a [https://en.wikipedia.org/wiki/Prime_power prime power], which 58 is not. * Base58 decoding is complicated and relatively slow. Included in the Segregated Witness proposal are a new class of outputs (witness programs, see [https://github.com/bitcoin/bips/blob/master/bip-0141.mediawiki BIP141]), and two instances of it ("P2WPKH" and "P2WSH", see [https://github.com/bitcoin/bips/blob/master/bip-0143.mediawiki BIP143]). Their functionality is available indirectly to older clients by embedding in P2SH outputs, but for optimal efficiency and security it is best to use it directly. In this document we propose a new address format for native witness outputs (current and future versions). This replaces [https://github.com/bitcoin/bips/blob/master/bip-0142.mediawiki BIP142], and was previously discussed [https://bitcoincore.org/logs/2016-05-zurich-meeting-notes.html#base32 here] (summarized [https://bitcoincore.org/en/meetings/2016/05/20/#error-correcting-codes-for-future-address-types here]). ===Examples=== All examples use public key 0279BE667EF9DCBBAC55A06295CE870B07029BFCDB2DCE28D959F2815B16F81798. The P2WSH examples use key OP_CHECKSIG as script. * Mainnet P2WPKH: bc1qw508d6qejxtdg4y5r3zarvary0c5xw7kv8f3t4 * Testnet P2WPKH: tb1qw508d6qejxtdg4y5r3zarvary0c5xw7kxpjzsx * Mainnet P2WSH: bc1qrp33g0q5c5txsp9arysrx4k6zdkfs4nce4xj0gdcccefvpysxf3qccfmv3 * Testnet P2WSH: tb1qrp33g0q5c5txsp9arysrx4k6zdkfs4nce4xj0gdcccefvpysxf3q0sl5k7 ==Specification== We first describe the general checksummed base32'''Why use base32 at all?''' The lack of mixed case makes it more efficient to read out loud or to put into QR codes. It does come with a 15% length increase, but that does not matter when copy-pasting addresses. format called ''Bech32'' and then define Segregated Witness addresses using it. ===Bech32=== A Bech32'''Why call it Bech32?''' "Bech" contains the characters BCH (the error detection algorithm used) and sounds a bit like "base". string is at most 90 characters long and consists of: * The '''human-readable part''', which is intended to convey the type of data, or anything else that is relevant to the reader. This part MUST contain 1 to 83 US-ASCII characters, with each character having a value in the range [33-126]. HRP validity may be further restricted by specific applications. * The '''separator''', which is always "1". In case "1" is allowed inside the human-readable part, the last one in the string is the separator'''Why include a separator in addresses?''' That way the human-readable part is unambiguously separated from the data part, avoiding potential collisions with other human-readable parts that share a prefix. It also allows us to avoid having character-set restrictions on the human-readable part. The separator is ''1'' because using a non-alphanumeric character would complicate copy-pasting of addresses (with no double-click selection in several applications). Therefore an alphanumeric character outside the normal character set was chosen.. * The '''data part''', which is at least 6 characters long and only consists of alphanumeric characters excluding "1", "b", "i", and "o"'''Why not use an existing character set like [http://www.faqs.org/rfcs/rfc3548.html RFC3548] or [https://philzimmermann.com/docs/human-oriented-base-32-encoding.txt z-base-32]'''? The character set is chosen to minimize ambiguity according to [https://hissa.nist.gov/~black/GTLD/ this] visual similarity data, and the ordering is chosen to minimize the number of pairs of similar characters (according to the same data) that differ in more than 1 bit. As the checksum is chosen to maximize detection capabilities for low numbers of bit errors, this choice improves its performance under some error models.. {| class="wikitable" |- ! !0 !1 !2 !3 !4 !5 !6 !7 |- !+0 |q||p||z||r||y||9||x||8 |- !+8 |g||f||2||t||v||d||w||0 |- !+16 |s||3||j||n||5||4||k||h |- !+24 |c||e||6||m||u||a||7||l |} '''Checksum''' The last six characters of the data part form a checksum and contain no information. Valid strings MUST pass the criteria for validity specified by the Python3 code snippet below. The function bech32_verify_checksum must return true when its arguments are: * hrp: the human-readable part as a string * data: the data part as a list of integers representing the characters after conversion using the table above
def bech32_polymod(values):
  GEN = [0x3b6a57b2, 0x26508e6d, 0x1ea119fa, 0x3d4233dd, 0x2a1462b3]
  chk = 1
  for v in values:
    b = (chk >> 25)
    chk = (chk & 0x1ffffff) << 5 ^ v
    for i in range(5):
      chk ^= GEN[i] if ((b >> i) & 1) else 0
  return chk

def bech32_hrp_expand(s):
  return [ord(x) >> 5 for x in s] + [0] + [ord(x) & 31 for x in s]

def bech32_verify_checksum(hrp, data):
  return bech32_polymod(bech32_hrp_expand(hrp) + data) == 1
This implements a [https://en.wikipedia.org/wiki/BCH_code BCH code] that guarantees detection of '''any error affecting at most 4 characters''' and has less than a 1 in 109 chance of failing to detect more errors. More details about the properties can be found in the Checksum Design appendix. The human-readable part is processed by first feeding the higher bits of each character's US-ASCII value into the checksum calculation followed by a zero and then the lower bits of each'''Why are the high bits of the human-readable part processed first?''' This results in the actually checksummed data being ''[high hrp] 0 [low hrp] [data]''. This means that under the assumption that errors to the human readable part only change the low 5 bits (like changing an alphabetical character into another), errors are restricted to the ''[low hrp] [data]'' part, which is at most 89 characters, and thus all error detection properties (see appendix) remain applicable.. To construct a valid checksum given the human-readable part and (non-checksum) values of the data-part characters, the code below can be used:
def bech32_create_checksum(hrp, data):
  values = bech32_hrp_expand(hrp) + data
  polymod = bech32_polymod(values + [0,0,0,0,0,0]) ^ 1
  return [(polymod >> 5 * (5 - i)) & 31 for i in range(6)]
'''Error correction''' One of the properties of these BCH codes is that they can be used for error correction. An unfortunate side effect of error correction is that it erodes error detection: correction changes invalid inputs into valid inputs, but if more than a few errors were made then the valid input may not be the correct input. Use of an incorrect but valid input can cause funds to be lost irrecoverably. Because of this, implementations SHOULD NOT implement correction beyond potentially suggesting to the user where in the string an error might be found, without suggesting the correction to make. '''Uppercase/lowercase''' The lowercase form is used when determining a character's value for checksum purposes. Encoders MUST always output an all lowercase Bech32 string. If an uppercase version of the encoding result is desired, (e.g.- for presentation purposes, or QR code use), then an uppercasing procedure can be performed external to the encoding process. Decoders MUST NOT accept strings where some characters are uppercase and some are lowercase (such strings are referred to as mixed case strings). For presentation, lowercase is usually preferable, but inside QR codes uppercase SHOULD be used, as those permit the use of ''[http://www.thonky.com/qr-code-tutorial/alphanumeric-mode-encoding alphanumeric mode]'', which is 45% more compact than the normal ''[http://www.thonky.com/qr-code-tutorial/byte-mode-encoding byte mode]''. ===Segwit address format=== A segwit address'''Why not make an address format that is generic for all scriptPubKeys?''' That would lead to confusion about addresses for existing scriptPubKey types. Furthermore, if addresses that do not have a one-to-one mapping with scriptPubKeys (such as ECDH-based addresses) are ever introduced, having a fully generic old address type available would permit reinterpreting the resulting scriptPubKeys using the old address format, with lost funds as a result if bitcoins are sent to them. is a Bech32 encoding of: * The human-readable part "bc"'''Why use 'bc' as human-readable part and not 'btc'?''' 'bc' is shorter. for mainnet, and "tb"'''Why use 'tb' as human-readable part for testnet?''' It was chosen to be of the same length as the mainnet counterpart (to simplify implementations' assumptions about lengths), but still be visually distinct. for testnet. * The data-part values: ** 1 character (representing 5 bits of data): the witness version ** A conversion of the 2-to-40-byte witness program (as defined by [https://github.com/bitcoin/bips/blob/master/bip-0141.mediawiki BIP141]) to base32: *** Start with the bits of the witness program, most significant bit per byte first. *** Re-arrange those bits into groups of 5, and pad with zeroes at the end if needed. *** Translate those bits to characters using the table above. '''Decoding''' Software interpreting a segwit address: * MUST verify that the human-readable part is "bc" for mainnet and "tb" for testnet. * MUST verify that the first decoded data value (the witness version) is between 0 and 16, inclusive. * Convert the rest of the data to bytes: ** Translate the values to 5 bits, most significant bit first. ** Re-arrange those bits into groups of 8 bits. Any incomplete group at the end MUST be 4 bits or less, MUST be all zeroes, and is discarded. ** There MUST be between 2 and 40 groups, which are interpreted as the bytes of the witness program. Decoders SHOULD enforce known-length restrictions on witness programs. For example, BIP141 specifies ''If the version byte is 0, but the witness program is neither 20 nor 32 bytes, the script must fail.'' As a result of the previous rules, addresses are always between 14 and 74 characters long, and their length modulo 8 cannot be 0, 3, or 5. Version 0 witness addresses are always 42 or 62 characters, but implementations MUST allow the use of any version. Implementations should take special care when converting the address to a scriptPubkey, where witness version ''n'' is stored as ''OP_n''. OP_0 is encoded as 0x00, but OP_1 through OP_16 are encoded as 0x51 though 0x60 (81 to 96 in decimal). If a bech32 address is converted to an incorrect scriptPubKey the result will likely be either unspendable or insecure. ===Compatibility=== Only new software will be able to use these addresses, and only for receivers with segwit-enabled new software. In all other cases, P2SH or P2PKH addresses can be used. ==Rationale== ==Reference implementations== * Reference encoder and decoder: ** [https://github.com/sipa/bech32/tree/master/ref/c For C] ** [https://github.com/sipa/bech32/tree/master/ref/c++ For C++] ** [https://github.com/sipa/bech32/tree/master/ref/javascript For JavaScript] ** [https://github.com/sipa/bech32/tree/master/ref/go For Go] ** [https://github.com/sipa/bech32/tree/master/ref/python For Python] ** [https://github.com/sipa/bech32/tree/master/ref/haskell For Haskell] ** [https://github.com/sipa/bech32/tree/master/ref/ruby For Ruby] ** [https://github.com/sipa/bech32/tree/master/ref/rust For Rust] * Fancy decoder that localizes errors: ** [https://github.com/sipa/bech32/tree/master/ecc/javascript For JavaScript] ([http://bitcoin.sipa.be/bech32/demo/demo.html demo website]) ==Registered Human-readable Prefixes== SatoshiLabs maintains a full list of registered human-readable parts for other cryptocurrencies: [https://github.com/satoshilabs/slips/blob/master/slip-0173.md SLIP-0173 : Registered human-readable parts for BIP-0173] ==Appendices== ===Test vectors=== The following strings are valid Bech32: * A12UEL5L * a12uel5l * an83characterlonghumanreadablepartthatcontainsthenumber1andtheexcludedcharactersbio1tt5tgs * abcdef1qpzry9x8gf2tvdw0s3jn54khce6mua7lmqqqxw * 11qqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqc8247j * split1checkupstagehandshakeupstreamerranterredcaperred2y9e3w * ?1ezyfcl WARNING: During conversion to US-ASCII some encoders may set unmappable characters to a valid US-ASCII character, such as '?'. For example:
>>> bech32_encode('\x80'.encode('ascii', 'replace').decode('ascii'), [])
'?1ezyfcl'
The following string are not valid Bech32 (with reason for invalidity): * 0x20 + 1nwldj5: HRP character out of range * 0x7F + 1axkwrx: HRP character out of range * 0x80 + 1eym55h: HRP character out of range * an84characterslonghumanreadablepartthatcontainsthenumber1andtheexcludedcharactersbio1569pvx: overall max length exceeded * pzry9x0s0muk: No separator character * 1pzry9x0s0muk: Empty HRP * x1b4n0q5v: Invalid data character * li1dgmt3: Too short checksum * de1lg7wt + 0xFF: Invalid character in checksum * A1G7SGD8: checksum calculated with uppercase form of HRP * 10a06t8: empty HRP * 1qzzfhee: empty HRP The following list gives valid segwit addresses and the scriptPubKey that they translate to in hex. * BC1QW508D6QEJXTDG4Y5R3ZARVARY0C5XW7KV8F3T4: 0014751e76e8199196d454941c45d1b3a323f1433bd6 * tb1qrp33g0q5c5txsp9arysrx4k6zdkfs4nce4xj0gdcccefvpysxf3q0sl5k7: 00201863143c14c5166804bd19203356da136c985678cd4d27a1b8c6329604903262 * bc1pw508d6qejxtdg4y5r3zarvary0c5xw7kw508d6qejxtdg4y5r3zarvary0c5xw7k7grplx: 5128751e76e8199196d454941c45d1b3a323f1433bd6751e76e8199196d454941c45d1b3a323f1433bd6 * BC1SW50QA3JX3S: 6002751e * bc1zw508d6qejxtdg4y5r3zarvaryvg6kdaj: 5210751e76e8199196d454941c45d1b3a323 * tb1qqqqqp399et2xygdj5xreqhjjvcmzhxw4aywxecjdzew6hylgvsesrxh6hy: 0020000000c4a5cad46221b2a187905e5266362b99d5e91c6ce24d165dab93e86433 The following list gives invalid segwit addresses and the reason for their invalidity. * tc1qw508d6qejxtdg4y5r3zarvary0c5xw7kg3g4ty: Invalid human-readable part * bc1qw508d6qejxtdg4y5r3zarvary0c5xw7kv8f3t5: Invalid checksum * BC13W508D6QEJXTDG4Y5R3ZARVARY0C5XW7KN40WF2: Invalid witness version * bc1rw5uspcuh: Invalid program length * bc10w508d6qejxtdg4y5r3zarvary0c5xw7kw508d6qejxtdg4y5r3zarvary0c5xw7kw5rljs90: Invalid program length * BC1QR508D6QEJXTDG4Y5R3ZARVARYV98GJ9P: Invalid program length for witness version 0 (per BIP141) * tb1qrp33g0q5c5txsp9arysrx4k6zdkfs4nce4xj0gdcccefvpysxf3q0sL5k7: Mixed case * bc1zw508d6qejxtdg4y5r3zarvaryvqyzf3du: zero padding of more than 4 bits * tb1qrp33g0q5c5txsp9arysrx4k6zdkfs4nce4xj0gdcccefvpysxf3pjxtptv: Non-zero padding in 8-to-5 conversion * bc1gmk9yu: Empty data section ===Checksum design=== '''Design choices''' BCH codes can be constructed over any prime-power alphabet and can be chosen to have a good trade-off between size and error-detection capabilities. While most work around BCH codes uses a binary alphabet, that is not a requirement. This makes them more appropriate for our use case than [https://en.wikipedia.org/wiki/Cyclic_redundancy_check CRC codes]. Unlike [https://en.wikipedia.org/wiki/Reed%E2%80%93Solomon_error_correction Reed-Solomon codes], they are not restricted in length to one less than the alphabet size. While they also support efficient error correction, the implementation of just error detection is very simple. We pick 6 checksum characters as a trade-off between length of the addresses and the error-detection capabilities, as 6 characters is the lowest number sufficient for a random failure chance below 1 per billion. For the length of data we're interested in protecting (up to 71 bytes for a potential future 40-byte witness program), BCH codes can be constructed that guarantee detecting up to 4 errors. '''Selected properties''' Many of these codes perform badly when dealing with more errors than they are designed to detect, but not all. For that reason, we consider codes that are designed to detect only 3 errors as well as 4 errors, and analyse how well they perform in practice. The specific code chosen here is the result of: * Starting with an exhaustive list of 159605 BCH codes designed to detect 3 or 4 errors up to length 93, 151, 165, 341, 1023, and 1057. * From those, requiring the detection of 4 errors up to length 71, resulting in 28825 remaining codes. * From those, choosing the codes with the best worst-case window for 5-character errors, resulting in 310 remaining codes. * From those, picking the code with the lowest chance for not detecting small numbers of ''bit'' errors. As a naive search would require over 6.5 * 1019 checksum evaluations, a collision-search approach was used for analysis. The code can be found [https://github.com/sipa/ezbase32/ here]. '''Properties''' The following table summarizes the chances for detection failure (as multiples of 1 in 109). {| class="wikitable" |- !colspan="2" | Window length !colspan="6" | Number of wrong characters |- !Length !Description !≤4 !5 !6 !7 !8 !≥9 |- | 8 || Longest detecting 6 errors || colspan="3" | 0 || 1.127 || 0.909 || n/a |- | 18 || Longest detecting 5 errors || colspan="2" | 0 || 0.965 || 0.929 || 0.932 || 0.931 |- | 19 || Worst case for 6 errors || 0 || 0.093 || 0.972 || 0.928 || colspan="2" | 0.931 |- | 39 || Length for a P2WPKH address || 0 || 0.756 || 0.935 || 0.932 || colspan="2" | 0.931 |- | 59 || Length for a P2WSH address || 0 || 0.805 || 0.933 || colspan="3" | 0.931 |- | 71 || Length for a 40-byte program address || 0 || 0.830 || 0.934 || colspan="3" | 0.931 |- | 89 || Longest detecting 4 errors || 0 || 0.867 || 0.933 || colspan="3" | 0.931 |} This means that when 5 changed characters occur randomly distributed in the 39 characters of a P2WPKH address, there is a chance of ''0.756 per billion'' that it will go undetected. When those 5 changes occur randomly within a 19-character window, that chance goes down to ''0.093 per billion''. As the number of errors goes up, the chance converges towards ''1 in 230'' = ''0.931 per billion''. Even though the chosen code performs reasonably well up to 1023 characters, other designs are preferable for lengths above 89 characters (excluding the separator). ==Acknowledgements== This document is inspired by the [https://rusty.ozlabs.org/?p=578 address proposal] by Rusty Russell, the [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2014-February/004402.html base32] proposal by Mark Friedenbach, and had input from Luke Dashjr, Johnson Lau, Eric Lombrozo, Peter Todd, and various other reviewers. ==Disclosures (added 2024)== Due to an oversight in the design of bech32, this checksum scheme is not always robust against [[https://gist.github.com/sipa/a9845b37c1b298a7301c33a04090b2eb|the insertion and deletion of fewer than 5 consecutive characters]]. Due to this weakness, [[bip-0350.mediawiki|BIP-350]] proposes using the scheme described in this BIP only for Native Segwit v0 outputs. ================================================ FILE: bip-0174/build.sh ================================================ #!/bin/bash pdflatex -output-format=pdf coinjoin-workflow.tex && \ inkscape --with-gui --export-text-to-path \ --export-plain-svg=coinjoin-workflow.svg coinjoin-workflow.pdf && \ pdflatex -output-format=pdf multisig-workflow.tex && \ inkscape --with-gui --export-text-to-path \ --export-plain-svg=multisig-workflow.svg multisig-workflow.pdf && \ echo '"success"' ================================================ FILE: bip-0174/coinjoin-workflow.tex ================================================ % using the PGF/TikZ package with pdflatex \documentclass{standalone} \usepackage[utf8]{inputenc} \usepackage[T1]{fontenc} %~ \usepackage[english]{babel} \usepackage[none]{hyphenat}% prevent hyphenation \usepackage{lmodern} \renewcommand*\familydefault{\sfdefault} \usepackage{tikz} \usetikzlibrary{shapes,arrows.meta} \tikzset{>=latex} \begin{document} % \sffamily{} \tikzstyle{block_center} = [rectangle, draw=black, thick, fill=white, text width=12em, text centered, minimum height=5em] \tikzstyle{block_rounded} = [rectangle, draw=black, thick, fill=white, text width=8em, text centered, minimum height=5em, rounded corners] \begin{tikzpicture}[auto] % outlining the flowchart on a grid \matrix[column sep=3ex,row sep=3ex]{ \node [block_center] (0alice1) {Alice creates a PSBT with only her inputs with UTXOs filled in.\\Sends it to Bob.}; & \node [block_center] (1bob1) {Bob adds his inputs and fills in his UTXOs.}; & \node [block_center] (2carol1) {Carol adds her inputs, fills in her UTXOs, adds signatures, and finalizes her inputs.}; \\ \node [block_rounded] (5alice2) {Alice extracts the network serialized transaction and broadcasts it.}; & \node [block_center] (4alice1) {Alice signs the transaction, adds her signatures, and finalizes her inputs.}; & \node [block_center] (3bob2) {Bob signs the transaction, adds his signatures, and finalizes his inputs.}; \\ };% end matrix % connecting nodes with paths \draw [ultra thick, draw=black, -{Stealth[length=8pt]}] (0alice1) edge (1bob1) (1bob1) edge (2carol1) (2carol1) edge (3bob2) (3bob2) edge (4alice1) (4alice1) edge (5alice2); \draw [thin, white, -{Stealth[color=black, fill=white, length=8pt]}] (0alice1) edge (1bob1) (1bob1) edge (2carol1) (2carol1) edge (3bob2) (3bob2) edge (4alice1) (4alice1) edge (5alice2); \end{tikzpicture} \end{document} ================================================ FILE: bip-0174/multisig-workflow.tex ================================================ % using the PGF/TikZ package with pdflatex \documentclass{standalone} \usepackage[utf8]{inputenc} \usepackage[T1]{fontenc} %~ \usepackage[english]{babel} \usepackage[none]{hyphenat}% prevent hyphenation \usepackage{lmodern} \renewcommand*\familydefault{\sfdefault} \usepackage{tikz} \usetikzlibrary{shapes,arrows.meta} \tikzset{>=latex} %\pgfdeclarelayer{bg} % declare background layer %\pgfsetlayers{bg,main} % set order of layers \newcommand{\h}{\hspace{1em}} \begin{document} % \sffamily{} \tikzstyle{block_center} = [rectangle, draw=black, thick, fill=white, text width=10.5em, text centered, minimum height=1em] \tikzstyle{block_rounded} = [rectangle, draw=black, thick, fill=white, text width=8em, text centered, minimum height=5em, rounded corners] \begin{tikzpicture}[auto] % outlining the flowchart on a grid \matrix[column sep=3ex,row sep=2.5ex]{ \h & \node [block_center] (R1) {Alice, Bob and Carol wish to spend from a 2-of-3 Multisig.}; & \h \\ \h & \node [block_center] (R2) {Alice uses a full node to create a PSBT with all input UTXOs filled in.}; & \h \\ \h & \node [block_center] (R3) {PSBT distributed.}; & \h \\ \node [block_center] (R4C1) {Alice signs the PSBT with her wallet.}; & \node [block_center] (R4C2) {Bob signs the PSBT with his SPV wallet.}; & \node [block_center] (R4C3) {Carol signs the PSBT with a completely offline signing machine.}; \\ %~ \h & \node (blind) & \h \\ \h & \node [block_center] (R5) {PSBTs are returned to Alice.}; & \h \\ \h & \node [block_center] (R6) {Alices combines the PSBTs. All inputs now have 3 signatures.}; & \h \\ \h & \node [block_center] (R7) {Alice finalizes the PSBT by creating each input's final scriptSig. One signature for each input is dropped.}; & \h \\ \h & \node [block_rounded] (stop) {Alice extracts the network serialized transaction and broadcasts it to the network.}; & \h \\ };% end matrix % connecting nodes with paths % \begin{pgfonlayer}{bg} \draw [ultra thick, draw=black, -{Stealth[length=8pt]}] (R1) edge (R2) (R2) edge (R3) (R3) -| (R4C1) (R3) edge (R4C2) (R5) edge (R6) (R6) edge (R7) (R7) edge (stop); \draw [thin, white, -{Stealth[color=black, fill=white, length=8pt]}] (R1) edge (R2) (R2) edge (R3) (R3) -| (R4C1) (R3) edge (R4C2) (R5) edge (R6) (R6) edge (R7) (R7) edge (stop); % circumvent missing arrow \draw [ultra thick, draw=black, -{Stealth[length=8pt]}] (R4C1) |-+(0,-2.2em)-| (R5) (R4C2) edge (R5) (R4C3) |-+(0,-2.2em)-| (R5) (R3) -| (R4C3); \draw [thin, white, -{Stealth[color=black, fill=white, length=8pt]}] (R4C1) |-+(0,-2.2em)-| (R5) (R4C2) edge (R5) (R4C3) |-+(0,-2.2em)-| (R5) (R3) -| (R4C3); % \end{pgfonlayer} \end{tikzpicture} \end{document} ================================================ FILE: bip-0174.mediawiki ================================================
  BIP: 174
  Layer: Applications
  Title: Partially Signed Bitcoin Transaction Format
  Authors: Ava Chow 
  Comments-Summary: No comments yet.
  Comments-URI: https://github.com/bitcoin/bips/wiki/Comments:BIP-0174
  Status: Deployed
  Type: Specification
  Assigned: 2017-07-12
  License: BSD-2-Clause
==Introduction== ===Abstract=== This document proposes a binary transaction format which contains the information necessary for a signer to produce signatures for the transaction and holds the signatures for an input while the input does not have a complete set of signatures. The signer can be offline as all necessary information will be provided in the transaction. The generic format is described here in addition to the specification for version 0 of this format. ===Copyright=== This BIP is licensed under the 2-clause BSD license. ===Motivation=== Creating unsigned or partially signed transactions to be passed around to multiple signers is currently implementation dependent, making it hard for people who use different wallet software from being able to easily do so. One of the goals of this document is to create a standard and extensible format that can be used between clients to allow people to pass around the same transaction to sign and combine their signatures. The format is also designed to be easily extended for future use which is harder to do with existing transaction formats. Signing transactions also requires users to have access to the UTXOs being spent. This transaction format will allow offline signers such as air-gapped wallets and hardware wallets to be able to sign transactions without needing direct access to the UTXO set and without risk of being defrauded. ==Specification== The Partially Signed Bitcoin Transaction (PSBT) format consists of key-value maps. Each map consists of a sequence of key-value records, terminated by a 0x00 byte '''Why is the separator here 0x00 instead of 0xff?''' The separator here is used to distinguish between each chunk of data. A separator of 0x00 would mean that the unserializer can read it as a key length of 0, which would never occur with actual keys. It can thus be used as a separator and allow for easier unserializer implementation.. := * * := 0x70 0x73 0x62 0x74 0xFF := * 0x00 := * 0x00 := * 0x00 := := := Where: ; : A [https://en.bitcoin.it/wiki/Protocol_documentation#Variable_length_integer compact size] unsigned integer representing the type. This compact size unsigned integer must be minimally encoded, i.e. if the value can be represented using one byte, it must be represented as one byte. There can be multiple entries with the same within a specific , but the must be unique. ; : The compact size unsigned integer containing the combined length of and ; : The compact size unsigned integer containing the length of (which must be exactly this many bytes). ; : Magic bytes which are ASCII for psbt '''Why use 4 bytes for psbt?''' The transaction format needed to start with a 5 byte header which uniquely identifies it. The first bytes were chosen to be the ASCII for psbt because that stands for Partially Signed Bitcoin Transaction. followed by a separator of 0xFF'''Why Use a separator after the magic bytes?''' The separator is part of the 5 byte header for PSBT. This byte is a separator of 0xff because this will cause any non-PSBT unserializer to fail to properly unserialize the PSBT as a normal transaction. Likewise, since the 5 byte header is fixed, no transaction in the non-PSBT format will be able to be unserialized by a PSBT unserializer.. This integer must be serialized in most significant byte order. The currently defined global types are as follows: {| ! Name ! ! ! Description ! ! Description ! Versions Requiring Inclusion ! Versions Requiring Exclusion ! Versions Allowing Inclusion ! Parent BIP |- | Unsigned Transaction | PSBT_GLOBAL_UNSIGNED_TX = 0x00 | None | No key data | | The transaction in network serialization. The scriptSigs and witnesses for each input must be empty. The transaction must be in the old serialization format (without witnesses). | 0 | 2 | 0 | 174 |- | Extended Public Key | PSBT_GLOBAL_XPUB = 0x01 | | The 78 byte serialized extended public key as defined by BIP 32. Extended public keys are those that can be used to derive public keys used in the inputs and outputs of this transaction. It should be the public key at the highest hardened derivation index so that the unhardened child keys used in the transaction can be derived. | <4 byte fingerprint> <32-bit little endian uint path element>* | The master key fingerprint as defined by BIP 32 concatenated with the derivation path of the public key. The derivation path is represented as 32-bit little endian unsigned integer indexes concatenated with each other. The number of 32 bit unsigned integer indexes must match the depth provided in the extended public key. | | | 0, 2 | 174 |- | Transaction Version | PSBT_GLOBAL_TX_VERSION = 0x02 | None | No key data | <32-bit little endian int version> | The 32-bit little endian signed integer representing the version number of the transaction being created. Note that this is not the same as the PSBT version number specified by the PSBT_GLOBAL_VERSION field. | 2 | 0 | 2 | [[bip-0370.mediawiki|370]] |- | Fallback Locktime | PSBT_GLOBAL_FALLBACK_LOCKTIME = 0x03 | None | No key data | <32-bit little endian uint locktime> | The 32-bit little endian unsigned integer representing the transaction locktime to use if no inputs specify a required locktime. | | 0 | 2 | [[bip-0370.mediawiki|370]] |- | Input Count | PSBT_GLOBAL_INPUT_COUNT = 0x04 | None | No key data | | Compact size unsigned integer representing the number of inputs in this PSBT. | 2 | 0 | 2 | [[bip-0370.mediawiki|370]] |- | Output Count | PSBT_GLOBAL_OUTPUT_COUNT = 0x05 | None | No key data | | Compact size unsigned integer representing the number of outputs in this PSBT. | 2 | 0 | 2 | [[bip-0370.mediawiki|370]] |- | Transaction Modifiable Flags | PSBT_GLOBAL_TX_MODIFIABLE = 0x06 | None | No key data | <8-bit uint flags> | An 8 bit little endian unsigned integer as a bitfield for various transaction modification flags. Bit 0 is the Inputs Modifiable Flag and indicates whether inputs can be modified. Bit 1 is the Outputs Modifiable Flag and indicates whether outputs can be modified. Bit 2 is the Has SIGHASH_SINGLE flag and indicates whether the transaction has a SIGHASH_SINGLE signature who's input and output pairing must be preserved. Bit 2 essentially indicates that the Constructor must iterate the inputs to determine whether and how to add an input. | | 0 | 2 | [[bip-0370.mediawiki|370]] |- | Silent Payment Global ECDH Share | PSBT_GLOBAL_SP_ECDH_SHARE = 0x07 | <33 byte scan key> | The scan key that this ECDH share is for. | <33 byte share> | An ECDH share for a scan key. The ECDH shared is computed with ''a * B_scan'', where ''a'' is the sum of all private keys of all eligible inputs, and ''B_scan'' is the scan key of a recipient. | | 0 | 2 | [[bip-0375.mediawiki|375]] |- | Silent Payment Global DLEQ Proof | PSBT_GLOBAL_SP_DLEQ = 0x08 | <33 byte scan key> | The scan key that this proof covers. | <64-byte proof> | A BIP374 DLEQ proof computed for the matching ECDH share. | | 0 | 2 | [[bip-0375.mediawiki|375]] |- | PSBT Version Number | PSBT_GLOBAL_VERSION = 0xFB | None | No key data | <32-bit little endian uint version> | The 32-bit little endian unsigned integer representing the version number of this PSBT. If omitted, the version number is 0. | | | 0, 2 | 174 |- | Proprietary Use Type | PSBT_GLOBAL_PROPRIETARY = 0xFC | | Compact size unsigned integer of the length of the identifier, followed by identifier prefix, followed by a compact size unsigned integer subtype, followed by the key data itself. | | Any value data as defined by the proprietary type user. | | | 0, 2 | 174 |} The currently defined per-input types are defined as follows: {| ! Name ! ! ! Description ! ! Description ! Versions Requiring Inclusion ! Versions Requiring Exclusion ! Versions Allowing Inclusion ! Parent BIP |- | Non-Witness UTXO | PSBT_IN_NON_WITNESS_UTXO = 0x00 | None | No key data | | The transaction in network serialization format the current input spends from. This should be present for inputs that spend non-segwit outputs and can be present for inputs that spend segwit outputs. An input can have both PSBT_IN_NON_WITNESS_UTXO and PSBT_IN_WITNESS_UTXO. '''Why can both UTXO types be provided?''' Many wallets began requiring the full previous transaction (i.e. PSBT_IN_NON_WITNESS_UTXO) for segwit inputs when PSBT was already in use. In order to be compatible with software which were expecting PSBT_IN_WITNESS_UTXO, both UTXO types must be allowed. | | | 0, 2 | 174 |- | Witness UTXO | PSBT_IN_WITNESS_UTXO = 0x01 | None | No key data | <64-bit little endian int amount> | The entire transaction output in network serialization which the current input spends from. This should only be present for inputs which spend segwit outputs, including P2SH embedded ones. An input can have both PSBT_IN_NON_WITNESS_UTXO and PSBT_IN_WITNESS_UTXO | | | 0, 2 | 174 |- | Partial Signature | PSBT_IN_PARTIAL_SIG = 0x02 | | The public key which corresponds to this signature. | | The signature as would be pushed to the stack from a scriptSig or witness. The signature should be a valid ECDSA signature corresponding to the pubkey that would return true when verified and not a value that would return false or be invalid otherwise (such as a NULLDUMMY). | | | 0, 2 | 174 |- | Sighash Type | PSBT_IN_SIGHASH_TYPE = 0x03 | None | No key data | <32-bit little endian uint sighash type> | The 32-bit unsigned integer specifying the sighash type to be used for this input. Signatures for this input must use the sighash type, finalizers must fail to finalize inputs which have signatures that do not match the specified sighash type. Signers who cannot produce signatures with the sighash type must not provide a signature. | | | 0, 2 | 174 |- | Redeem Script | PSBT_IN_REDEEM_SCRIPT = 0x04 | None | No key data | | The redeemScript for this input if it has one. | | | 0, 2 | 174 |- | Witness Script | PSBT_IN_WITNESS_SCRIPT = 0x05 | None | No key data | | The witnessScript for this input if it has one. | | | 0, 2 | 174 |- | BIP 32 Derivation Path | PSBT_IN_BIP32_DERIVATION = 0x06 | | The public key | <4 byte fingerprint> <32-bit little endian uint path element>* | The master key fingerprint as defined by BIP 32 concatenated with the derivation path of the public key. The derivation path is represented as 32 bit unsigned integer indexes concatenated with each other. Public keys are those that will be needed to sign this input. | | | 0, 2 | 174 |- | Finalized scriptSig | PSBT_IN_FINAL_SCRIPTSIG = 0x07 | None | No key data | | The Finalized scriptSig contains a fully constructed scriptSig with signatures and any other scripts necessary for the input to pass validation. | | | 0, 2 | 174 |- | Finalized scriptWitness | PSBT_IN_FINAL_SCRIPTWITNESS = 0x08 | None | No key data | | The Finalized scriptWitness contains a fully constructed scriptWitness with signatures and any other scripts necessary for the input to pass validation. | | | 0, 2 | 174 |- | Proof-of-reserves commitment | PSBT_IN_POR_COMMITMENT = 0x09 | None | No key data | | The UTF-8 encoded commitment message string for the proof-of-reserves. See [[bip-0127.mediawiki|BIP 127]] for more information. | | | 0, 2 | [[bip-0127.mediawiki|127]] |- | RIPEMD160 preimage | PSBT_IN_RIPEMD160 = 0x0a | <20-byte hash> | The resulting hash of the preimage | | The hash preimage, encoded as a byte vector, which must equal the key when run through the RIPEMD160 algorithm | | | 0, 2 | 174 |- | SHA256 preimage | PSBT_IN_SHA256 = 0x0b | <32-byte hash> | The resulting hash of the preimage | | The hash preimage, encoded as a byte vector, which must equal the key when run through the SHA256 algorithm | | | 0, 2 | 174 |- | HASH160 preimage | PSBT_IN_HASH160 = 0x0c | <20-byte hash> | The resulting hash of the preimage | | The hash preimage, encoded as a byte vector, which must equal the key when run through the SHA256 algorithm followed by the RIPEMD160 algorithm | | | 0, 2 | 174 |- | HASH256 preimage | PSBT_IN_HASH256 = 0x0d | <32-byte hash> | The resulting hash of the preimage | | The hash preimage, encoded as a byte vector, which must equal the key when run through the SHA256 algorithm twice | | | 0, 2 | 174 |- | Previous TXID | PSBT_IN_PREVIOUS_TXID = 0x0e | None | No key data | <32 byte txid> | 32 byte txid in standard byte order, not display byte order, of the previous transaction whose output at PSBT_IN_OUTPUT_INDEX is being spent. | 2 | 0 | 2 | [[bip-0370.mediawiki|370]] |- | Spent Output Index | PSBT_IN_OUTPUT_INDEX = 0x0f | None | No key data | <32-bit little endian uint index> | 32 bit little endian integer representing the index of the output being spent in the transaction with the txid of PSBT_IN_PREVIOUS_TXID. | 2 | 0 | 2 | [[bip-0370.mediawiki|370]] |- | Sequence Number | PSBT_IN_SEQUENCE = 0x10 | None | No key data | <32-bit little endian uint sequence> | The 32 bit unsigned little endian integer for the sequence number of this input. If omitted, the sequence number is assumed to be the final sequence number (0xffffffff). | | 0 | 2 | [[bip-0370.mediawiki|370]] |- | Required Time-based Locktime | PSBT_IN_REQUIRED_TIME_LOCKTIME = 0x11 | None | No key data | <32-bit little endian uint locktime> | 32 bit unsigned little endian integer greater than or equal to 500000000 representing the minimum Unix timestamp that this input requires to be set as the transaction's lock time. | | 0 | 2 | [[bip-0370.mediawiki|370]] |- | Required Height-based Locktime | PSBT_IN_REQUIRED_HEIGHT_LOCKTIME = 0x12 | None | No key data | <32-bit uint locktime> | 32 bit unsigned little endian integer less than 500000000 representing the minimum block height that this input requires to be set as the transaction's lock time. | | 0 | 2 | [[bip-0370.mediawiki|370]] |- | Taproot Key Spend Signature | PSBT_IN_TAP_KEY_SIG = 0x13 | None | No key data | <64 or 65 byte signature> | The 64 or 65 byte Schnorr signature for key path spending a Taproot output. Finalizers should remove this field after PSBT_IN_FINAL_SCRIPTWITNESS is constructed. | | | 0, 2 | [[bip-0371.mediawiki|371]] |- | Taproot Script Spend Signature | PSBT_IN_TAP_SCRIPT_SIG = 0x14 | <32 byte xonlypubkey> | A 32 byte X-only public key involved in a leaf script concatenated with the 32 byte hash of the leaf it is part of. | <64 or 65 byte signature> | The 64 or 65 byte Schnorr signature for this pubkey and leaf combination. Finalizers should remove this field after PSBT_IN_FINAL_SCRIPTWITNESS is constructed. | | | 0, 2 | [[bip-0371.mediawiki|371]] |- | Taproot Leaf Script | PSBT_IN_TAP_LEAF_SCRIPT = 0x15 | | The control block for this leaf as specified in BIP 341. The control block contains the merkle tree path to this leaf. | <8-bit uint leaf version> | The script for this leaf as would be provided in the witness stack followed by the single byte leaf version. Note that the leaves included in this field should be those that the signers of this input are expected to be able to sign for. Finalizers should remove this field after PSBT_IN_FINAL_SCRIPTWITNESS is constructed. | | | 0, 2 | [[bip-0371.mediawiki|371]] |- | Taproot Key BIP 32 Derivation Path | PSBT_IN_TAP_BIP32_DERIVATION = 0x16 | <32 byte xonlypubkey> | A 32 byte X-only public key involved in this input. It may be the output key, the internal key, or a key present in a leaf script. | <32 byte leaf hash>* <4 byte fingerprint> <32-bit little endian uint path element>* | A compact size unsigned integer representing the number of leaf hashes, followed by a list of leaf hashes, followed by the 4 byte master key fingerprint concatenated with the derivation path of the public key. The derivation path is represented as 32-bit little endian unsigned integer indexes concatenated with each other. Public keys are those needed to spend this output. The leaf hashes are of the leaves which involve this public key. The internal key does not have leaf hashes, so can be indicated with a hashes len of 0. Finalizers should remove this field after PSBT_IN_FINAL_SCRIPTWITNESS is constructed. | | | 0, 2 | [[bip-0371.mediawiki|371]] |- | Taproot Internal Key | PSBT_IN_TAP_INTERNAL_KEY = 0x17 | None | No key data | <32 byte xonlypubkey> | The X-only pubkey used as the internal key in this output. Finalizers should remove this field after PSBT_IN_FINAL_SCRIPTWITNESS is constructed. | | | 0, 2 | [[bip-0371.mediawiki|371]] |- | Taproot Merkle Root | PSBT_IN_TAP_MERKLE_ROOT = 0x18 | None | No key data | <32-byte hash> | The 32 byte Merkle root hash. Finalizers should remove this field after PSBT_IN_FINAL_SCRIPTWITNESS is constructed. | | | 0, 2 | [[bip-0371.mediawiki|371]] |- | MuSig2 Participant Public Keys | PSBT_IN_MUSIG2_PARTICIPANT_PUBKEYS = 0x1a | <33 byte aggregate pubkey (compressed)> | The MuSig2 aggregate public key (compressed) from the KeyAgg algorithm. This key may or may not be in the script directly (as x-only). It may instead be a parent public key from which the public keys in the script were derived. | <33 byte participant pubkey (compressed)>* | A list of the compressed public keys of the participants in the MuSig2 aggregate key in the order required for aggregation. If sorting was done, then the keys must be in the sorted order. | | | 0, 2 | [[bip-0373.mediawiki|373]] |- | MuSig2 Public Nonce | PSBT_IN_MUSIG2_PUB_NONCE = 0x1b | <33 byte participant pubkey (compressed)> <33 byte aggregate pubkey (compressed)> <32 byte hash or omitted> | The compressed public key of the participant providing this nonce, followed by the compressed aggregate public key the participant is providing the nonce for, followed by the BIP 341 tapleaf hash of the Taproot leaf script that will be signed. If the aggregate key is the taproot internal key or the taproot output key, then the tapleaf hash must be omitted. The compressed participant public key must be the key found in the script and not the aggregate public key that it was derived from, if it was derived from an aggregate key. | <66 byte public nonce> | The public nonce produced by the NonceGen algorithm. | | | 0, 2 | [[bip-0373.mediawiki|373]] |- | MuSig2 Participant Partial Signature | PSBT_IN_MUSIG2_PARTIAL_SIG = 0x1c | <33 byte participant pubkey (compressed)> <33 byte aggregate pubkey (compressed)> <32 byte hash or omitted> | The compressed public key of the participant providing this partial signature, followed by the compressed public key the participant is providing the signature for, followed by the BIP 341 tapleaf hash of the Taproot leaf script that will be signed. If the aggregate key is the Taproot internal key or the Taproot output key, then the tapleaf hash must be omitted. Note that the compressed participant public key must be be the key found in the script and not the aggregate public key that it was derived from, if it was derived from an aggregate key. | <32 byte partial signature> | The partial signature produced by the Sign algorithm. | | | 0, 2 | [[bip-0373.mediawiki|373]] |- | Silent Payment Input ECDH Share | PSBT_IN_SP_ECDH_SHARE = 0x1d | <33 byte scan key> | The scan key that this ECDH share is for. | <33 byte share> | An ECDH share for a scan key. The ECDH shared is computed with ''a * B_scan'', where ''a'' is the private key of the corresponding prevout public key, and ''B_scan'' is the scan key of a recipient. | | 0 | 2 | [[bip-0375.mediawiki|375]] |- | Silent Payment Input DLEQ Proof | PSBT_IN_SP_DLEQ = 0x1e | <33 byte scan key> | The scan key that this proof covers. | <64-byte proof> | A BIP374 DLEQ proof computed for the matching ECDH share. | | 0 | 2 | [[bip-0375.mediawiki|375]] |- | Proprietary Use Type | PSBT_IN_PROPRIETARY = 0xFC | | Compact size unsigned integer of the length of the identifier, followed by identifier prefix, followed by a compact size unsigned integer subtype, followed by the key data itself. | | Any value data as defined by the proprietary type user. | | | 0, 2 | 174 |} The currently defined per-output '''Why do we need per-output data?''' Per-output data allows signers to verify that the outputs are going to the intended recipient. The output data can also be use by signers to determine which outputs are change outputs and verify that the change is returning to the correct place. types are defined as follows: {| ! Name ! ! ! Description ! ! Description ! Versions Requiring Inclusion ! Versions Requiring Exclusion ! Versions Allowing Inclusion ! Parent BIP |- | Redeem Script | PSBT_OUT_REDEEM_SCRIPT = 0x00 | None | No key data | | The redeemScript for this output if it has one. | | | 0, 2 | 174 |- | Witness Script | PSBT_OUT_WITNESS_SCRIPT = 0x01 | None | No key data | | The witnessScript for this output if it has one. | | | 0, 2 | 174 |- | BIP 32 Derivation Path | PSBT_OUT_BIP32_DERIVATION = 0x02 | | The public key | <4 byte fingerprint> <32-bit little endian uint path element>* | The master key fingerprint concatenated with the derivation path of the public key. The derivation path is represented as 32-bit little endian unsigned integer indexes concatenated with each other. Public keys are those needed to spend this output. | | | 0, 2 | 174 |- | Output Amount | PSBT_OUT_AMOUNT = 0x03 | None | No key data | <64-bit int amount> | 64 bit signed little endian integer representing the output's amount in satoshis. | 2 | 0 | 2 | [[bip-0370.mediawiki|370]] |- | Output Script | PSBT_OUT_SCRIPT = 0x04 | None | No key data | | The script for this output, also known as the scriptPubKey. Must be omitted in PSBTv0. Must be provided in PSBTv2 if not sending to a BIP352 silent payment address, otherwise may be omitted. | | 0 | 2 | [[bip-0370.mediawiki|370]], [[bip-0375.mediawiki|375]] |- | Taproot Internal Key | PSBT_OUT_TAP_INTERNAL_KEY = 0x05 | None | No key data | <32 byte xonlypubkey> | The X-only pubkey used as the internal key in this output. | | | 0, 2 | [[bip-0371.mediawiki|371]] |- | Taproot Tree | PSBT_OUT_TAP_TREE = 0x06 | None | No key data | {<8-bit uint depth> <8-bit uint leaf version> }* | One or more tuples representing the depth, leaf version, and script for a leaf in the Taproot tree, allowing the entire tree to be reconstructed. The tuples must be in depth first search order so that the tree is correctly reconstructed. Each tuple is an 8-bit unsigned integer representing the depth in the Taproot tree for this script, an 8-bit unsigned integer representing the leaf version, the length of the script as a compact size unsigned integer, and the script itself. | | | 0, 2 | [[bip-0371.mediawiki|371]] |- | Taproot Key BIP 32 Derivation Path | PSBT_OUT_TAP_BIP32_DERIVATION = 0x07 | <32 byte xonlypubkey> | A 32 byte X-only public key involved in this output. It may be the output key, the internal key, or a key present in a leaf script. | <32 byte leaf hash>* <4 byte fingerprint> <32-bit little endian uint path element>* | A compact size unsigned integer representing the number of leaf hashes, followed by a list of leaf hashes, followed by the 4 byte master key fingerprint concatenated with the derivation path of the public key. The derivation path is represented as 32-bit little endian unsigned integer indexes concatenated with each other. Public keys are those needed to spend this output. The leaf hashes are of the leaves which involve this public key. The internal key does not have leaf hashes, so can be indicated with a hashes len of 0. Finalizers should remove this field after PSBT_IN_FINAL_SCRIPTWITNESS is constructed. | | | 0, 2 | [[bip-0371.mediawiki|371]] |- | MuSig2 Participant Public Keys | PSBT_OUT_MUSIG2_PARTICIPANT_PUBKEYS = 0x08 | <33 byte aggregate pubkey (compressed)> | The MuSig2 compressed aggregate public key from the KeyAgg algorithm. This key may or may not be in the script directly. It may instead be a parent public key from which the public keys in the script were derived. | <33 byte participant pubkey (compressed)>* | A list of the compressed public keys of the participants in the MuSig2 aggregate key in the order required for aggregation. If sorting was done, then the keys must be in the sorted order. | | | 0, 2 | [[bip-0373.mediawiki|373]] |- | Silent Payment Data | PSBT_OUT_SP_V0_INFO = 0x09 | None | No key data | <33 byte scan key> <33 byte spend key> | The scan and spend public keys from the silent payments address. | | 0 | 2 | [[bip-0375.mediawiki|375]] |- | Silent Payment Label | PSBT_OUT_SP_V0_LABEL = 0x0a | None | No key data | <32-bit little endian uint label> | The label to use to compute the spend key of the silent payments address to verify change. | | 0 | 2 | [[bip-0375.mediawiki|375]] |- | BIP 353 DNSSEC proof | PSBT_OUT_DNSSEC_PROOF = 0x35 | None | No key data | <1-byte-length-prefixed BIP 353 human-readable name> | A BIP 353 human-readable name (without the ₿ prefix), prefixed by a 1-byte length. Followed by an [[https://www.rfc-editor.org/rfc/rfc9102.html#name-dnssec-authentication-chain|RFC 9102 DNSSEC AuthenticationChain]] (i.e. a series of DNS Resource Records in no particular order) providing a DNSSEC proof to a BIP 353 DNS TXT record. | | | 0, 2 | [[bip-0353.mediawiki|353]] |- | Proprietary Use Type | PSBT_OUT_PROPRIETARY = 0xFC | | Compact size unsigned integer of the length of the identifier, followed by identifier prefix, followed by a compact size unsigned integer subtype, followed by the key data itself. | | Any value data as defined by the proprietary type user. | | | 0, 2 | 174 |} Types can be skipped when they are unnecessary. For example, if an input is a witness input, then it should not have a Non-Witness UTXO key-value pair. If the signer encounters key-value pairs that it does not understand, it must pass those key-value pairs through when re-serializing the transaction. All keys must have the data that they specify. If any key or value does not match the specified format for that type, the PSBT must be considered invalid. For example, any key that has no data except for the type specifier must only have the type specifier in the key. ===Handling Duplicated Keys=== Keys within each scope should never be duplicated; all keys in the format are unique. PSBTs containing duplicate keys are invalid. However implementers will still need to handle events where keys are duplicated when combining transactions with duplicated fields. In this event, the software may choose whichever value it wishes.'''Why can the values be arbitrarily chosen?''' When there are duplicated keys, the values that can be chosen will either be valid or invalid. If the values are invalid, a signer would simply produce an invalid signature and the final transaction itself would be invalid. If the values are valid, then it does not matter which is chosen as either way the transaction is still valid. ===Proprietary Use Type=== For all global, per-input, and per-output maps, the type 0xFC is reserved for proprietary use. The proprietary use type requires keys that follow the type with a compact size unsigned integer representing the length of the string identifier, followed by the string identifier, then a subtype, and finally any key data. The identifier can be any variable length string that software can use to identify whether the particular data in the proprietary type can be used by it. It can also be the empty string although this is not recommended. The subtype is defined by the proprietary type user and can mean whatever they want it to mean. The subtype must also be a compact size unsigned integer in the same form as the normal types. The key data and value data are defined by the proprietary type user. The proprietary use type is for private use by individuals and organizations who wish to use PSBT in their processes. It is useful when there are additional data that they need attached to a PSBT but such data are not useful or available for the general public. The proprietary use type is not to be used by any public specification and there is no expectation that any publicly available software be able to understand any specific meanings of it and the subtypes. This type must be used for internal processes only. ==Version 0== Partially Signed Bitcoin Transactions version 0 is the first version of the PSBT format. Version 0 PSBTs must either omit PSBT_GLOBAL_VERSION or include it and set it to 0. Version 0 PSBTs must include PSBT_GLOBAL_UNSIGNED_TX, if omitted, the PSBT is invalid. ==Roles== Using the transaction format involves many different roles. Multiple roles can be handled by a single entity, but each role is specialized in what it should be capable of doing. ===Creator=== The Creator creates a new PSBT. It must create an unsigned transaction and place it in the PSBT. The Creator must create empty input and output fields. ===Updater=== The Updater must only accept a PSBT. The Updater adds information to the PSBT that it has access to. If it has the UTXO for an input, it should add it to the PSBT. The Updater should also add redeemScripts, witnessScripts, and BIP 32 derivation paths to the input and output data if it knows them. A single entity is likely to be both a Creator and Updater. ===Signer=== The Signer must only accept a PSBT. The Signer must only use the UTXOs provided in the PSBT to produce signatures for inputs. Before signing a non-witness input, the Signer must verify that the TXID of the non-witness UTXO matches the TXID specified in the unsigned transaction. Before signing a witness input, the Signer must verify that the witnessScript (if provided) matches the hash specified in the UTXO or the redeemScript, and the redeemScript (if provided) matches the hash in the UTXO. The Signer may choose to fail to sign a segwit input if a non-witness UTXO is not provided. '''Why would non-witness UTXOs be provided for segwit inputs?''' The sighash algorithm for Segwit specified in BIP 143 is known to have an issue where an attacker could trick a user to sending Bitcoin to fees if they are able to convince the user to sign a malicious transaction multiple times. This is possible because the amounts in PSBT_IN_WITNESS_UTXO of other segwit inputs can be modified without effecting the signature for a particular input. In order to prevent this kind of attack, many wallets are requiring that the full previous transaction (i.e. PSBT_IN_NON_WITNESS_UTXO) be provided to ensure that the amounts of other inputs are not being tampered with. The Signer should not need any additional data sources, as all necessary information is provided in the PSBT format. The Signer must only add data to a PSBT. Any signatures created by the Signer must be added as a "Partial Signature" key-value pair for the respective input it relates to. If a Signer cannot sign a transaction, it must not add a Partial Signature. The Signer can additionally compute the addresses and values being sent, and the transaction fee, optionally showing this data to the user as a confirmation of intent and the consequences of signing the PSBT. Signers do not need to sign for all possible input types. For example, a signer may choose to only sign Segwit inputs. A single entity is likely to be both a Signer and an Updater as it can update a PSBT with necessary information prior to signing it. ====Data Signers Check For==== For a Signer to only produce valid signatures for what it expects to sign, it must check that the following conditions are true: * If a non-witness UTXO is provided, its hash must match the hash specified in the prevout * If a witness UTXO is provided, no non-witness signature may be created * If a redeemScript is provided, the scriptPubKey must be for that redeemScript * If a witnessScript is provided, the scriptPubKey or the redeemScript must be for that witnessScript * If a sighash type is provided, the signer must check that the sighash is acceptable. If unacceptable, they must fail. * If a sighash type is not provided, the signer should sign using SIGHASH_ALL, but may use any sighash type they wish. =====Simple Signer Algorithm===== A simple signer can use the following algorithm to determine what and how to sign
sign_witness(script_code, i):
    for key, sighash_type in psbt.inputs[i].items:
        if sighash_type == None:
            sighash_type = SIGHASH_ALL
        if IsMine(key) and IsAcceptable(sighash_type):
            sign(witness_sighash(script_code, i, input))

sign_non_witness(script_code, i):
    for key, sighash_type in psbt.inputs[i].items:
        if sighash_type == None:
            sighash_type = SIGHASH_ALL
        if IsMine(key) and IsAcceptable(sighash_type):
            sign(non_witness_sighash(script_code, i, input))

for input, i in enumerate(psbt.inputs):
    if witness_utxo.exists:
        if redeemScript.exists:
            assert(witness_utxo.scriptPubKey == P2SH(redeemScript))
            script = redeemScript
        else:
            script = witness_utxo.scriptPubKey
        if IsP2WPKH(script):
            sign_witness(P2PKH(script[2:22]), i)
        else if IsP2WSH(script):
            assert(script == P2WSH(witnessScript))
            sign_witness(witnessScript, i)
    else if non_witness_utxo.exists:
        assert(sha256d(non_witness_utxo) == psbt.tx.input[i].prevout.hash)
        if redeemScript.exists:
            assert(non_witness_utxo.vout[psbt.tx.input[i].prevout.n].scriptPubKey == P2SH(redeemScript))
            sign_non_witness(redeemScript, i)
        else:
            sign_non_witness(non_witness_utxo.vout[psbt.tx.input[i].prevout.n].scriptPubKey, i)
    else:
        assert False
====Change Detection==== Signers may wish to display the inputs and outputs to users for extra verification. In such displays, signers may wish to identify which outputs are change outputs in order to omit them to avoid additional user confusion. In order to detect change, a signer can use the BIP 32 derivation paths provided in inputs and outputs as well as the extended public keys provided globally. For a single key output, a signer can observe whether the master fingerprint for the public key for that output belongs to itself. If it does, it can then derive the public key at the specified derivation path and check whether that key is the one present in that output. For outputs involving multiple keys, a signer can first examine the inputs that it is signing. It should determine the general pattern of the script and internally produce a representation of the policy that the script represents. Such a policy can include things like how many keys are present, what order they are in, how many signers are necessary, which signers are required, etc. The signer can then use the BIP 32 derivation paths for each of the pubkeys to find which global extended public key is the one that can derive that particular public key. To do so, the signer would extract the derivation path to the highest hardened index and use that to lookup the public key with that index and master fingerprint. The signer would construct this script policy with extended public keys for all of the inputs and outputs. Change outputs would then be identified as being the outputs which have the same script policy as the inputs that are being signed. ===Combiner=== The Combiner can accept 1 or many PSBTs. The Combiner must merge them into one PSBT (if possible), or fail. The resulting PSBT must contain all of the key-value pairs from each of the PSBTs. The Combiner must remove any duplicate key-value pairs, in accordance with the specification. It can pick arbitrarily when conflicts occur. A Combiner must not combine two different PSBTs. PSBTs can be uniquely identified by 0x00 global transaction typed key-value pair. For every type that a Combiner understands, it may refuse to combine PSBTs if it detects that there will be inconsistencies or conflicts for that type in the combined PSBT. The Combiner does not need to know how to interpret scripts in order to combine PSBTs. It can do so without understanding scripts or the network serialization format. In general, the result of a Combiner combining two PSBTs from independent participants A and B should be functionally equivalent to a result obtained from processing the original PSBT by A and then B in a sequence. Or, for participants performing fA(psbt) and fB(psbt): Combine(fA(psbt), fB(psbt)) == fA(fB(psbt)) == fB(fA(psbt)) ===Input Finalizer=== The Input Finalizer must only accept a PSBT. For each input, the Input Finalizer determines if the input has enough data to pass validation. If it does, it must construct the 0x07 Finalized scriptSig and 0x08 Finalized scriptWitness and place them into the input key-value map. If scriptSig is empty for an input, 0x07 should remain unset rather than assigned an empty array. Likewise, if no scriptWitness exists for an input, 0x08 should remain unset rather than assigned an empty array. All other data except the UTXO and unknown fields in the input key-value map should be cleared from the PSBT. The UTXO should be kept to allow Transaction Extractors to verify the final network serialized transaction. ===Transaction Extractor=== The Transaction Extractor must only accept a PSBT. It checks whether all inputs have complete scriptSigs and scriptWitnesses by checking for the presence of 0x07 Finalized scriptSig and 0x08 Finalized scriptWitness typed records. If they do, the Transaction Extractor should construct complete scriptSigs and scriptWitnesses and encode them into network serialized transactions. Otherwise the Extractor must not modify the PSBT. The Extractor should produce a fully valid, network serialized transaction if all inputs are complete. The Transaction Extractor does not need to know how to interpret scripts in order to extract the network serialized transaction. However it may be able to in order to validate the network serialized transaction at the same time. A single entity is likely to be both a Transaction Extractor and an Input Finalizer. ==Encoding== A PSBT can be represented in two ways: in binary (as a file) or as a Base64 string using the encoding described in [https://tools.ietf.org/html/rfc4648#section-4 RFC4648]. Binary PSBT files should use the .psbt file extension. A MIME type name will be added to this document once one has been registered. ==Extensibility== The Partially Signed Transaction format can be extended in the future by adding new types for key-value pairs. Backwards compatibility will still be maintained as those new types will be ignored and passed-through by signers which do not know about them. ===Version Numbers=== The Version number field exists only as a safeguard in the event that a backwards incompatible change is introduced to PSBT. If a parser encounters a version number it does not recognize, it should exit immediately as this indicates that the PSBT will contain types that it does not know about and cannot be ignored. Current PSBTs are Version 0. Any PSBT that does not have the version field is version 0. It is not expected that any backwards incompatible change will be introduced to PSBT, so it is not expected that the version field will ever actually be seen. Updaters and combiners that need to add a version number to a PSBT should use the highest version number required. For example, if a combiner sees two PSBTs for the same transaction, one with version 0, and the other with version 1, then it should combine them and produce a PSBT with version 1. If an updater is updating a PSBT and needs to add a field that is only available in version 1, then it should set the PSBT version number to 1 unless a version higher than that is already specified. ===Procedure For New Fields=== New fields should first be proposed on the bitcoin-dev mailing list. If a field requires significant description as to its usage, it should be accompanied by a separate BIP. The field must be added to the field listing tables in the Specification section. Although some PSBT version 0 implementations encode types as uint8_t rather than compact size, it is still safe to add >0xFD fields to PSBT 0, because these old parsers ignore unknown fields, and is prefixed by its length. ===Procedure For New Versions=== New PSBT versions must be described in a separate BIP. The BIP may reference this BIP and any components of PSBT version 0 that are retained in the new version. Any new fields described in the new version must be added to the field listing tables in the Specification section. ==Compatibility== This transaction format is designed so that it is unable to be properly unserialized by normal transaction unserializers. Likewise, a normal transaction will not be able to be unserialized by an unserializer for the PSBT format. ==Examples== ===Manual CoinJoin Workflow=== ===2-of-3 Multisig Workflow=== ==Test Vectors== The following are invalid PSBTs: * Case: Network transaction, not PSBT format ** Bytes in Hex:
0200000001268171371edff285e937adeea4b37b78000c0566cbb3ad64641713ca42171bf6000000006a473044022070b2245123e6bf474d60c5b50c043d4c691a5d2435f09a34a7662a9dc251790a022001329ca9dacf280bdf30740ec0390422422c81cb45839457aeb76fc12edd95b3012102657d118d3357b8e0f4c2cd46db7b39f6d9c38d9a70abcb9b2de5dc8dbfe4ce31feffffff02d3dff505000000001976a914d0c59903c5bac2868760e90fd521a4665aa7652088ac00e1f5050000000017a9143545e6e33b832c47050f24d3eeb93c9c03948bc787b32e1300
** Base64 String:
AgAAAAEmgXE3Ht/yhek3re6ks3t4AAwFZsuzrWRkFxPKQhcb9gAAAABqRzBEAiBwsiRRI+a/R01gxbUMBD1MaRpdJDXwmjSnZiqdwlF5CgIgATKcqdrPKAvfMHQOwDkEIkIsgctFg5RXrrdvwS7dlbMBIQJlfRGNM1e44PTCzUbbezn22cONmnCry5st5dyNv+TOMf7///8C09/1BQAAAAAZdqkU0MWZA8W6woaHYOkP1SGkZlqnZSCIrADh9QUAAAAAF6kUNUXm4zuDLEcFDyTT7rk8nAOUi8eHsy4TAA==
* Case: PSBT missing outputs ** Bytes in Hex:
70736274ff0100750200000001268171371edff285e937adeea4b37b78000c0566cbb3ad64641713ca42171bf60000000000feffffff02d3dff505000000001976a914d0c59903c5bac2868760e90fd521a4665aa7652088ac00e1f5050000000017a9143545e6e33b832c47050f24d3eeb93c9c03948bc787b32e1300000100fda5010100000000010289a3c71eab4d20e0371bbba4cc698fa295c9463afa2e397f8533ccb62f9567e50100000017160014be18d152a9b012039daf3da7de4f53349eecb985ffffffff86f8aa43a71dff1448893a530a7237ef6b4608bbb2dd2d0171e63aec6a4890b40100000017160014fe3e9ef1a745e974d902c4355943abcb34bd5353ffffffff0200c2eb0b000000001976a91485cff1097fd9e008bb34af709c62197b38978a4888ac72fef84e2c00000017a914339725ba21efd62ac753a9bcd067d6c7a6a39d05870247304402202712be22e0270f394f568311dc7ca9a68970b8025fdd3b240229f07f8a5f3a240220018b38d7dcd314e734c9276bd6fb40f673325bc4baa144c800d2f2f02db2765c012103d2e15674941bad4a996372cb87e1856d3652606d98562fe39c5e9e7e413f210502483045022100d12b852d85dcd961d2f5f4ab660654df6eedcc794c0c33ce5cc309ffb5fce58d022067338a8e0e1725c197fb1a88af59f51e44e4255b20167c8684031c05d1f2592a01210223b72beef0965d10be0778efecd61fcac6f79a4ea169393380734464f84f2ab30000000000
** Base64 String:
cHNidP8BAHUCAAAAASaBcTce3/KF6Tet7qSze3gADAVmy7OtZGQXE8pCFxv2AAAAAAD+////AtPf9QUAAAAAGXapFNDFmQPFusKGh2DpD9UhpGZap2UgiKwA4fUFAAAAABepFDVF5uM7gyxHBQ8k0+65PJwDlIvHh7MuEwAAAQD9pQEBAAAAAAECiaPHHqtNIOA3G7ukzGmPopXJRjr6Ljl/hTPMti+VZ+UBAAAAFxYAFL4Y0VKpsBIDna89p95PUzSe7LmF/////4b4qkOnHf8USIk6UwpyN+9rRgi7st0tAXHmOuxqSJC0AQAAABcWABT+Pp7xp0XpdNkCxDVZQ6vLNL1TU/////8CAMLrCwAAAAAZdqkUhc/xCX/Z4Ai7NK9wnGIZeziXikiIrHL++E4sAAAAF6kUM5cluiHv1irHU6m80GfWx6ajnQWHAkcwRAIgJxK+IuAnDzlPVoMR3HyppolwuAJf3TskAinwf4pfOiQCIAGLONfc0xTnNMkna9b7QPZzMlvEuqFEyADS8vAtsnZcASED0uFWdJQbrUqZY3LLh+GFbTZSYG2YVi/jnF6efkE/IQUCSDBFAiEA0SuFLYXc2WHS9fSrZgZU327tzHlMDDPOXMMJ/7X85Y0CIGczio4OFyXBl/saiK9Z9R5E5CVbIBZ8hoQDHAXR8lkqASECI7cr7vCWXRC+B3jv7NYfysb3mk6haTkzgHNEZPhPKrMAAAAAAA==
* Case: PSBT where one input has a filled scriptSig in the unsigned tx ** Bytes in Hex:
70736274ff0100fd0a010200000002ab0949a08c5af7c49b8212f417e2f15ab3f5c33dcf153821a8139f877a5b7be4000000006a47304402204759661797c01b036b25928948686218347d89864b719e1f7fcf57d1e511658702205309eabf56aa4d8891ffd111fdf1336f3a29da866d7f8486d75546ceedaf93190121035cdc61fc7ba971c0b501a646a2a83b102cb43881217ca682dc86e2d73fa88292feffffffab0949a08c5af7c49b8212f417e2f15ab3f5c33dcf153821a8139f877a5b7be40100000000feffffff02603bea0b000000001976a914768a40bbd740cbe81d988e71de2a4d5c71396b1d88ac8e240000000000001976a9146f4620b553fa095e721b9ee0efe9fa039cca459788ac00000000000001012000e1f5050000000017a9143545e6e33b832c47050f24d3eeb93c9c03948bc787010416001485d13537f2e265405a34dbafa9e3dda01fb82308000000
** Base64 String:
cHNidP8BAP0KAQIAAAACqwlJoIxa98SbghL0F+LxWrP1wz3PFTghqBOfh3pbe+QAAAAAakcwRAIgR1lmF5fAGwNrJZKJSGhiGDR9iYZLcZ4ff89X0eURZYcCIFMJ6r9Wqk2Ikf/REf3xM286KdqGbX+EhtdVRs7tr5MZASEDXNxh/HupccC1AaZGoqg7ECy0OIEhfKaC3Ibi1z+ogpL+////qwlJoIxa98SbghL0F+LxWrP1wz3PFTghqBOfh3pbe+QBAAAAAP7///8CYDvqCwAAAAAZdqkUdopAu9dAy+gdmI5x3ipNXHE5ax2IrI4kAAAAAAAAGXapFG9GILVT+glechue4O/p+gOcykWXiKwAAAAAAAABASAA4fUFAAAAABepFDVF5uM7gyxHBQ8k0+65PJwDlIvHhwEEFgAUhdE1N/LiZUBaNNuvqePdoB+4IwgAAAA=
* Case: PSBT where inputs and outputs are provided but without an unsigned tx ** Bytes in Hex:
70736274ff000100fda5010100000000010289a3c71eab4d20e0371bbba4cc698fa295c9463afa2e397f8533ccb62f9567e50100000017160014be18d152a9b012039daf3da7de4f53349eecb985ffffffff86f8aa43a71dff1448893a530a7237ef6b4608bbb2dd2d0171e63aec6a4890b40100000017160014fe3e9ef1a745e974d902c4355943abcb34bd5353ffffffff0200c2eb0b000000001976a91485cff1097fd9e008bb34af709c62197b38978a4888ac72fef84e2c00000017a914339725ba21efd62ac753a9bcd067d6c7a6a39d05870247304402202712be22e0270f394f568311dc7ca9a68970b8025fdd3b240229f07f8a5f3a240220018b38d7dcd314e734c9276bd6fb40f673325bc4baa144c800d2f2f02db2765c012103d2e15674941bad4a996372cb87e1856d3652606d98562fe39c5e9e7e413f210502483045022100d12b852d85dcd961d2f5f4ab660654df6eedcc794c0c33ce5cc309ffb5fce58d022067338a8e0e1725c197fb1a88af59f51e44e4255b20167c8684031c05d1f2592a01210223b72beef0965d10be0778efecd61fcac6f79a4ea169393380734464f84f2ab30000000000
** Base64 String:
cHNidP8AAQD9pQEBAAAAAAECiaPHHqtNIOA3G7ukzGmPopXJRjr6Ljl/hTPMti+VZ+UBAAAAFxYAFL4Y0VKpsBIDna89p95PUzSe7LmF/////4b4qkOnHf8USIk6UwpyN+9rRgi7st0tAXHmOuxqSJC0AQAAABcWABT+Pp7xp0XpdNkCxDVZQ6vLNL1TU/////8CAMLrCwAAAAAZdqkUhc/xCX/Z4Ai7NK9wnGIZeziXikiIrHL++E4sAAAAF6kUM5cluiHv1irHU6m80GfWx6ajnQWHAkcwRAIgJxK+IuAnDzlPVoMR3HyppolwuAJf3TskAinwf4pfOiQCIAGLONfc0xTnNMkna9b7QPZzMlvEuqFEyADS8vAtsnZcASED0uFWdJQbrUqZY3LLh+GFbTZSYG2YVi/jnF6efkE/IQUCSDBFAiEA0SuFLYXc2WHS9fSrZgZU327tzHlMDDPOXMMJ/7X85Y0CIGczio4OFyXBl/saiK9Z9R5E5CVbIBZ8hoQDHAXR8lkqASECI7cr7vCWXRC+B3jv7NYfysb3mk6haTkzgHNEZPhPKrMAAAAAAA==
* Case: PSBT with duplicate keys in an input ** Bytes in Hex:
70736274ff0100750200000001268171371edff285e937adeea4b37b78000c0566cbb3ad64641713ca42171bf60000000000feffffff02d3dff505000000001976a914d0c59903c5bac2868760e90fd521a4665aa7652088ac00e1f5050000000017a9143545e6e33b832c47050f24d3eeb93c9c03948bc787b32e1300000100fda5010100000000010289a3c71eab4d20e0371bbba4cc698fa295c9463afa2e397f8533ccb62f9567e50100000017160014be18d152a9b012039daf3da7de4f53349eecb985ffffffff86f8aa43a71dff1448893a530a7237ef6b4608bbb2dd2d0171e63aec6a4890b40100000017160014fe3e9ef1a745e974d902c4355943abcb34bd5353ffffffff0200c2eb0b000000001976a91485cff1097fd9e008bb34af709c62197b38978a4888ac72fef84e2c00000017a914339725ba21efd62ac753a9bcd067d6c7a6a39d05870247304402202712be22e0270f394f568311dc7ca9a68970b8025fdd3b240229f07f8a5f3a240220018b38d7dcd314e734c9276bd6fb40f673325bc4baa144c800d2f2f02db2765c012103d2e15674941bad4a996372cb87e1856d3652606d98562fe39c5e9e7e413f210502483045022100d12b852d85dcd961d2f5f4ab660654df6eedcc794c0c33ce5cc309ffb5fce58d022067338a8e0e1725c197fb1a88af59f51e44e4255b20167c8684031c05d1f2592a01210223b72beef0965d10be0778efecd61fcac6f79a4ea169393380734464f84f2ab30000000001003f0200000001ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0000000000ffffffff010000000000000000036a010000000000000000
** Base64 String:
cHNidP8BAHUCAAAAASaBcTce3/KF6Tet7qSze3gADAVmy7OtZGQXE8pCFxv2AAAAAAD+////AtPf9QUAAAAAGXapFNDFmQPFusKGh2DpD9UhpGZap2UgiKwA4fUFAAAAABepFDVF5uM7gyxHBQ8k0+65PJwDlIvHh7MuEwAAAQD9pQEBAAAAAAECiaPHHqtNIOA3G7ukzGmPopXJRjr6Ljl/hTPMti+VZ+UBAAAAFxYAFL4Y0VKpsBIDna89p95PUzSe7LmF/////4b4qkOnHf8USIk6UwpyN+9rRgi7st0tAXHmOuxqSJC0AQAAABcWABT+Pp7xp0XpdNkCxDVZQ6vLNL1TU/////8CAMLrCwAAAAAZdqkUhc/xCX/Z4Ai7NK9wnGIZeziXikiIrHL++E4sAAAAF6kUM5cluiHv1irHU6m80GfWx6ajnQWHAkcwRAIgJxK+IuAnDzlPVoMR3HyppolwuAJf3TskAinwf4pfOiQCIAGLONfc0xTnNMkna9b7QPZzMlvEuqFEyADS8vAtsnZcASED0uFWdJQbrUqZY3LLh+GFbTZSYG2YVi/jnF6efkE/IQUCSDBFAiEA0SuFLYXc2WHS9fSrZgZU327tzHlMDDPOXMMJ/7X85Y0CIGczio4OFyXBl/saiK9Z9R5E5CVbIBZ8hoQDHAXR8lkqASECI7cr7vCWXRC+B3jv7NYfysb3mk6haTkzgHNEZPhPKrMAAAAAAQA/AgAAAAH//////////////////////////////////////////wAAAAAA/////wEAAAAAAAAAAANqAQAAAAAAAAAA
* Case: PSBT with invalid global transaction typed key ** Bytes in Hex:
70736274ff020001550200000001279a2323a5dfb51fc45f220fa58b0fc13e1e3342792a85d7e36cd6333b5cbc390000000000ffffffff01a05aea0b000000001976a914ffe9c0061097cc3b636f2cb0460fa4fc427d2b4588ac0000000000010120955eea0b0000000017a9146345200f68d189e1adc0df1c4d16ea8f14c0dbeb87220203b1341ccba7683b6af4f1238cd6e97e7167d569fac47f1e48d47541844355bd4646304302200424b58effaaa694e1559ea5c93bbfd4a89064224055cdf070b6771469442d07021f5c8eb0fea6516d60b8acb33ad64ede60e8785bfb3aa94b99bdf86151db9a9a010104220020771fd18ad459666dd49f3d564e3dbc42f4c84774e360ada16816a8ed488d5681010547522103b1341ccba7683b6af4f1238cd6e97e7167d569fac47f1e48d47541844355bd462103de55d1e1dac805e3f8a58c1fbf9b94c02f3dbaafe127fefca4995f26f82083bd52ae220603b1341ccba7683b6af4f1238cd6e97e7167d569fac47f1e48d47541844355bd4610b4a6ba67000000800000008004000080220603de55d1e1dac805e3f8a58c1fbf9b94c02f3dbaafe127fefca4995f26f82083bd10b4a6ba670000008000000080050000800000
** Base64 String:
cHNidP8CAAFVAgAAAAEnmiMjpd+1H8RfIg+liw/BPh4zQnkqhdfjbNYzO1y8OQAAAAAA/////wGgWuoLAAAAABl2qRT/6cAGEJfMO2NvLLBGD6T8Qn0rRYisAAAAAAABASCVXuoLAAAAABepFGNFIA9o0YnhrcDfHE0W6o8UwNvrhyICA7E0HMunaDtq9PEjjNbpfnFn1Wn6xH8eSNR1QYRDVb1GRjBDAiAEJLWO/6qmlOFVnqXJO7/UqJBkIkBVzfBwtncUaUQtBwIfXI6w/qZRbWC4rLM61k7eYOh4W/s6qUuZvfhhUduamgEBBCIAIHcf0YrUWWZt1J89Vk49vEL0yEd042CtoWgWqO1IjVaBAQVHUiEDsTQcy6doO2r08SOM1ul+cWfVafrEfx5I1HVBhENVvUYhA95V0eHayAXj+KWMH7+blMAvPbqv4Sf+/KSZXyb4IIO9Uq4iBgOxNBzLp2g7avTxI4zW6X5xZ9Vp+sR/HkjUdUGEQ1W9RhC0prpnAAAAgAAAAIAEAACAIgYD3lXR4drIBeP4pYwfv5uUwC89uq/hJ/78pJlfJvggg70QtKa6ZwAAAIAAAACABQAAgAAA
* Case: PSBT with invalid input witness utxo typed key ** Bytes in Hex:
70736274ff0100550200000001279a2323a5dfb51fc45f220fa58b0fc13e1e3342792a85d7e36cd6333b5cbc390000000000ffffffff01a05aea0b000000001976a914ffe9c0061097cc3b636f2cb0460fa4fc427d2b4588ac000000000002010020955eea0b0000000017a9146345200f68d189e1adc0df1c4d16ea8f14c0dbeb87220203b1341ccba7683b6af4f1238cd6e97e7167d569fac47f1e48d47541844355bd4646304302200424b58effaaa694e1559ea5c93bbfd4a89064224055cdf070b6771469442d07021f5c8eb0fea6516d60b8acb33ad64ede60e8785bfb3aa94b99bdf86151db9a9a010104220020771fd18ad459666dd49f3d564e3dbc42f4c84774e360ada16816a8ed488d5681010547522103b1341ccba7683b6af4f1238cd6e97e7167d569fac47f1e48d47541844355bd462103de55d1e1dac805e3f8a58c1fbf9b94c02f3dbaafe127fefca4995f26f82083bd52ae220603b1341ccba7683b6af4f1238cd6e97e7167d569fac47f1e48d47541844355bd4610b4a6ba67000000800000008004000080220603de55d1e1dac805e3f8a58c1fbf9b94c02f3dbaafe127fefca4995f26f82083bd10b4a6ba670000008000000080050000800000
** Base64 String:
cHNidP8BAFUCAAAAASeaIyOl37UfxF8iD6WLD8E+HjNCeSqF1+Ns1jM7XLw5AAAAAAD/////AaBa6gsAAAAAGXapFP/pwAYQl8w7Y28ssEYPpPxCfStFiKwAAAAAAAIBACCVXuoLAAAAABepFGNFIA9o0YnhrcDfHE0W6o8UwNvrhyICA7E0HMunaDtq9PEjjNbpfnFn1Wn6xH8eSNR1QYRDVb1GRjBDAiAEJLWO/6qmlOFVnqXJO7/UqJBkIkBVzfBwtncUaUQtBwIfXI6w/qZRbWC4rLM61k7eYOh4W/s6qUuZvfhhUduamgEBBCIAIHcf0YrUWWZt1J89Vk49vEL0yEd042CtoWgWqO1IjVaBAQVHUiEDsTQcy6doO2r08SOM1ul+cWfVafrEfx5I1HVBhENVvUYhA95V0eHayAXj+KWMH7+blMAvPbqv4Sf+/KSZXyb4IIO9Uq4iBgOxNBzLp2g7avTxI4zW6X5xZ9Vp+sR/HkjUdUGEQ1W9RhC0prpnAAAAgAAAAIAEAACAIgYD3lXR4drIBeP4pYwfv5uUwC89uq/hJ/78pJlfJvggg70QtKa6ZwAAAIAAAACABQAAgAAA
* Case: PSBT with invalid pubkey length for input partial signature typed key ** Bytes in Hex:
70736274ff0100550200000001279a2323a5dfb51fc45f220fa58b0fc13e1e3342792a85d7e36cd6333b5cbc390000000000ffffffff01a05aea0b000000001976a914ffe9c0061097cc3b636f2cb0460fa4fc427d2b4588ac0000000000010120955eea0b0000000017a9146345200f68d189e1adc0df1c4d16ea8f14c0dbeb87210203b1341ccba7683b6af4f1238cd6e97e7167d569fac47f1e48d47541844355bd46304302200424b58effaaa694e1559ea5c93bbfd4a89064224055cdf070b6771469442d07021f5c8eb0fea6516d60b8acb33ad64ede60e8785bfb3aa94b99bdf86151db9a9a010104220020771fd18ad459666dd49f3d564e3dbc42f4c84774e360ada16816a8ed488d5681010547522103b1341ccba7683b6af4f1238cd6e97e7167d569fac47f1e48d47541844355bd462103de55d1e1dac805e3f8a58c1fbf9b94c02f3dbaafe127fefca4995f26f82083bd52ae220603b1341ccba7683b6af4f1238cd6e97e7167d569fac47f1e48d47541844355bd4610b4a6ba67000000800000008004000080220603de55d1e1dac805e3f8a58c1fbf9b94c02f3dbaafe127fefca4995f26f82083bd10b4a6ba670000008000000080050000800000
** Base64 String:
cHNidP8BAFUCAAAAASeaIyOl37UfxF8iD6WLD8E+HjNCeSqF1+Ns1jM7XLw5AAAAAAD/////AaBa6gsAAAAAGXapFP/pwAYQl8w7Y28ssEYPpPxCfStFiKwAAAAAAAEBIJVe6gsAAAAAF6kUY0UgD2jRieGtwN8cTRbqjxTA2+uHIQIDsTQcy6doO2r08SOM1ul+cWfVafrEfx5I1HVBhENVvUYwQwIgBCS1jv+qppThVZ6lyTu/1KiQZCJAVc3wcLZ3FGlELQcCH1yOsP6mUW1guKyzOtZO3mDoeFv7OqlLmb34YVHbmpoBAQQiACB3H9GK1FlmbdSfPVZOPbxC9MhHdONgraFoFqjtSI1WgQEFR1IhA7E0HMunaDtq9PEjjNbpfnFn1Wn6xH8eSNR1QYRDVb1GIQPeVdHh2sgF4/iljB+/m5TALz26r+En/vykmV8m+CCDvVKuIgYDsTQcy6doO2r08SOM1ul+cWfVafrEfx5I1HVBhENVvUYQtKa6ZwAAAIAAAACABAAAgCIGA95V0eHayAXj+KWMH7+blMAvPbqv4Sf+/KSZXyb4IIO9ELSmumcAAACAAAAAgAUAAIAAAA==
* Case: PSBT with invalid redeemscript typed key ** Bytes in Hex:
70736274ff0100550200000001279a2323a5dfb51fc45f220fa58b0fc13e1e3342792a85d7e36cd6333b5cbc390000000000ffffffff01a05aea0b000000001976a914ffe9c0061097cc3b636f2cb0460fa4fc427d2b4588ac0000000000010120955eea0b0000000017a9146345200f68d189e1adc0df1c4d16ea8f14c0dbeb87220203b1341ccba7683b6af4f1238cd6e97e7167d569fac47f1e48d47541844355bd4646304302200424b58effaaa694e1559ea5c93bbfd4a89064224055cdf070b6771469442d07021f5c8eb0fea6516d60b8acb33ad64ede60e8785bfb3aa94b99bdf86151db9a9a01020400220020771fd18ad459666dd49f3d564e3dbc42f4c84774e360ada16816a8ed488d5681010547522103b1341ccba7683b6af4f1238cd6e97e7167d569fac47f1e48d47541844355bd462103de55d1e1dac805e3f8a58c1fbf9b94c02f3dbaafe127fefca4995f26f82083bd52ae220603b1341ccba7683b6af4f1238cd6e97e7167d569fac47f1e48d47541844355bd4610b4a6ba67000000800000008004000080220603de55d1e1dac805e3f8a58c1fbf9b94c02f3dbaafe127fefca4995f26f82083bd10b4a6ba670000008000000080050000800000
** Base64 String:
cHNidP8BAFUCAAAAASeaIyOl37UfxF8iD6WLD8E+HjNCeSqF1+Ns1jM7XLw5AAAAAAD/////AaBa6gsAAAAAGXapFP/pwAYQl8w7Y28ssEYPpPxCfStFiKwAAAAAAAEBIJVe6gsAAAAAF6kUY0UgD2jRieGtwN8cTRbqjxTA2+uHIgIDsTQcy6doO2r08SOM1ul+cWfVafrEfx5I1HVBhENVvUZGMEMCIAQktY7/qqaU4VWepck7v9SokGQiQFXN8HC2dxRpRC0HAh9cjrD+plFtYLisszrWTt5g6Hhb+zqpS5m9+GFR25qaAQIEACIAIHcf0YrUWWZt1J89Vk49vEL0yEd042CtoWgWqO1IjVaBAQVHUiEDsTQcy6doO2r08SOM1ul+cWfVafrEfx5I1HVBhENVvUYhA95V0eHayAXj+KWMH7+blMAvPbqv4Sf+/KSZXyb4IIO9Uq4iBgOxNBzLp2g7avTxI4zW6X5xZ9Vp+sR/HkjUdUGEQ1W9RhC0prpnAAAAgAAAAIAEAACAIgYD3lXR4drIBeP4pYwfv5uUwC89uq/hJ/78pJlfJvggg70QtKa6ZwAAAIAAAACABQAAgAAA
* Case: PSBT with invalid witnessscript typed key ** Bytes in Hex:
70736274ff0100550200000001279a2323a5dfb51fc45f220fa58b0fc13e1e3342792a85d7e36cd6333b5cbc390000000000ffffffff01a05aea0b000000001976a914ffe9c0061097cc3b636f2cb0460fa4fc427d2b4588ac0000000000010120955eea0b0000000017a9146345200f68d189e1adc0df1c4d16ea8f14c0dbeb87220203b1341ccba7683b6af4f1238cd6e97e7167d569fac47f1e48d47541844355bd4646304302200424b58effaaa694e1559ea5c93bbfd4a89064224055cdf070b6771469442d07021f5c8eb0fea6516d60b8acb33ad64ede60e8785bfb3aa94b99bdf86151db9a9a010104220020771fd18ad459666dd49f3d564e3dbc42f4c84774e360ada16816a8ed488d568102050047522103b1341ccba7683b6af4f1238cd6e97e7167d569fac47f1e48d47541844355bd462103de55d1e1dac805e3f8a58c1fbf9b94c02f3dbaafe127fefca4995f26f82083bd52ae220603b1341ccba7683b6af4f1238cd6e97e7167d569fac47f1e48d47541844355bd4610b4a6ba67000000800000008004000080220603de55d1e1dac805e3f8a58c1fbf9b94c02f3dbaafe127fefca4995f26f82083bd10b4a6ba670000008000000080050000800000
** Base64 String:
cHNidP8BAFUCAAAAASeaIyOl37UfxF8iD6WLD8E+HjNCeSqF1+Ns1jM7XLw5AAAAAAD/////AaBa6gsAAAAAGXapFP/pwAYQl8w7Y28ssEYPpPxCfStFiKwAAAAAAAEBIJVe6gsAAAAAF6kUY0UgD2jRieGtwN8cTRbqjxTA2+uHIgIDsTQcy6doO2r08SOM1ul+cWfVafrEfx5I1HVBhENVvUZGMEMCIAQktY7/qqaU4VWepck7v9SokGQiQFXN8HC2dxRpRC0HAh9cjrD+plFtYLisszrWTt5g6Hhb+zqpS5m9+GFR25qaAQEEIgAgdx/RitRZZm3Unz1WTj28QvTIR3TjYK2haBao7UiNVoECBQBHUiEDsTQcy6doO2r08SOM1ul+cWfVafrEfx5I1HVBhENVvUYhA95V0eHayAXj+KWMH7+blMAvPbqv4Sf+/KSZXyb4IIO9Uq4iBgOxNBzLp2g7avTxI4zW6X5xZ9Vp+sR/HkjUdUGEQ1W9RhC0prpnAAAAgAAAAIAEAACAIgYD3lXR4drIBeP4pYwfv5uUwC89uq/hJ/78pJlfJvggg70QtKa6ZwAAAIAAAACABQAAgAAA
* Case: PSBT with invalid pubkey in input BIP 32 derivation paths typed key ** Bytes in Hex:
70736274ff0100550200000001279a2323a5dfb51fc45f220fa58b0fc13e1e3342792a85d7e36cd6333b5cbc390000000000ffffffff01a05aea0b000000001976a914ffe9c0061097cc3b636f2cb0460fa4fc427d2b4588ac0000000000010120955eea0b0000000017a9146345200f68d189e1adc0df1c4d16ea8f14c0dbeb87220203b1341ccba7683b6af4f1238cd6e97e7167d569fac47f1e48d47541844355bd4646304302200424b58effaaa694e1559ea5c93bbfd4a89064224055cdf070b6771469442d07021f5c8eb0fea6516d60b8acb33ad64ede60e8785bfb3aa94b99bdf86151db9a9a010104220020771fd18ad459666dd49f3d564e3dbc42f4c84774e360ada16816a8ed488d5681010547522103b1341ccba7683b6af4f1238cd6e97e7167d569fac47f1e48d47541844355bd462103de55d1e1dac805e3f8a58c1fbf9b94c02f3dbaafe127fefca4995f26f82083bd52ae210603b1341ccba7683b6af4f1238cd6e97e7167d569fac47f1e48d47541844355bd10b4a6ba67000000800000008004000080220603de55d1e1dac805e3f8a58c1fbf9b94c02f3dbaafe127fefca4995f26f82083bd10b4a6ba670000008000000080050000800000
** Base64 String:
cHNidP8BAFUCAAAAASeaIyOl37UfxF8iD6WLD8E+HjNCeSqF1+Ns1jM7XLw5AAAAAAD/////AaBa6gsAAAAAGXapFP/pwAYQl8w7Y28ssEYPpPxCfStFiKwAAAAAAAEBIJVe6gsAAAAAF6kUY0UgD2jRieGtwN8cTRbqjxTA2+uHIgIDsTQcy6doO2r08SOM1ul+cWfVafrEfx5I1HVBhENVvUZGMEMCIAQktY7/qqaU4VWepck7v9SokGQiQFXN8HC2dxRpRC0HAh9cjrD+plFtYLisszrWTt5g6Hhb+zqpS5m9+GFR25qaAQEEIgAgdx/RitRZZm3Unz1WTj28QvTIR3TjYK2haBao7UiNVoEBBUdSIQOxNBzLp2g7avTxI4zW6X5xZ9Vp+sR/HkjUdUGEQ1W9RiED3lXR4drIBeP4pYwfv5uUwC89uq/hJ/78pJlfJvggg71SriEGA7E0HMunaDtq9PEjjNbpfnFn1Wn6xH8eSNR1QYRDVb0QtKa6ZwAAAIAAAACABAAAgCIGA95V0eHayAXj+KWMH7+blMAvPbqv4Sf+/KSZXyb4IIO9ELSmumcAAACAAAAAgAUAAIAAAA==
* Case: PSBT with invalid non-witness utxo typed key ** Bytes in Hex:
70736274ff01009a020000000258e87a21b56daf0c23be8e7070456c336f7cbaa5c8757924f545887bb2abdd750000000000ffffffff838d0427d0ec650a68aa46bb0b098aea4422c071b2ca78352a077959d07cea1d0100000000ffffffff0270aaf00800000000160014d85c2b71d0060b09c9886aeb815e50991dda124d00e1f5050000000016001400aea9a2e5f0f876a588df5546e8742d1d87008f0000000000020000bb0200000001aad73931018bd25f84ae400b68848be09db706eac2ac18298babee71ab656f8b0000000048473044022058f6fc7c6a33e1b31548d481c826c015bd30135aad42cd67790dab66d2ad243b02204a1ced2604c6735b6393e5b41691dd78b00f0c5942fb9f751856faa938157dba01feffffff0280f0fa020000000017a9140fb9463421696b82c833af241c78c17ddbde493487d0f20a270100000017a91429ca74f8a08f81999428185c97b5d852e4063f6187650000000107da00473044022074018ad4180097b873323c0015720b3684cc8123891048e7dbcd9b55ad679c99022073d369b740e3eb53dcefa33823c8070514ca55a7dd9544f157c167913261118c01483045022100f61038b308dc1da865a34852746f015772934208c6d24454393cd99bdf2217770220056e675a675a6d0a02b85b14e5e29074d8a25a9b5760bea2816f661910a006ea01475221029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f2102dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d752ae0001012000c2eb0b0000000017a914b7f5faf40e3d40a5a459b1db3535f2b72fa921e8870107232200208c2353173743b595dfb4a07b72ba8e42e3797da74e87fe7d9d7497e3b20289030108da0400473044022062eb7a556107a7c73f45ac4ab5a1dddf6f7075fb1275969a7f383efff784bcb202200c05dbb7470dbf2f08557dd356c7325c1ed30913e996cd3840945db12228da5f01473044022065f45ba5998b59a27ffe1a7bed016af1f1f90d54b3aa8f7450aa5f56a25103bd02207f724703ad1edb96680b284b56d4ffcb88f7fb759eabbe08aa30f29b851383d20147522103089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc21023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7352ae00220203a9a4c37f5996d3aa25dbac6b570af0650394492942460b354753ed9eeca5877110d90c6a4f000000800000008004000080002202027f6399757d2eff55a136ad02c684b1838b6556e5f1b6b34282a94b6b5005109610d90c6a4f00000080000000800500008000
** Base64 String:
cHNidP8BAJoCAAAAAljoeiG1ba8MI76OcHBFbDNvfLqlyHV5JPVFiHuyq911AAAAAAD/////g40EJ9DsZQpoqka7CwmK6kQiwHGyyng1Kgd5WdB86h0BAAAAAP////8CcKrwCAAAAAAWABTYXCtx0AYLCcmIauuBXlCZHdoSTQDh9QUAAAAAFgAUAK6pouXw+HaliN9VRuh0LR2HAI8AAAAAAAIAALsCAAAAAarXOTEBi9JfhK5AC2iEi+CdtwbqwqwYKYur7nGrZW+LAAAAAEhHMEQCIFj2/HxqM+GzFUjUgcgmwBW9MBNarULNZ3kNq2bSrSQ7AiBKHO0mBMZzW2OT5bQWkd14sA8MWUL7n3UYVvqpOBV9ugH+////AoDw+gIAAAAAF6kUD7lGNCFpa4LIM68kHHjBfdveSTSH0PIKJwEAAAAXqRQpynT4oI+BmZQoGFyXtdhS5AY/YYdlAAAAAQfaAEcwRAIgdAGK1BgAl7hzMjwAFXILNoTMgSOJEEjn282bVa1nnJkCIHPTabdA4+tT3O+jOCPIBwUUylWn3ZVE8VfBZ5EyYRGMAUgwRQIhAPYQOLMI3B2oZaNIUnRvAVdyk0IIxtJEVDk82ZvfIhd3AiAFbmdaZ1ptCgK4WxTl4pB02KJam1dgvqKBb2YZEKAG6gFHUiEClYO/Oa4KYJdHrRma3dY0+mEIVZ1sXNObTCGD8auW4H8hAtq2H/SaFNtqfQKwzR+7ePxLGDErW05U2uTbovv+9TbXUq4AAQEgAMLrCwAAAAAXqRS39fr0Dj1ApaRZsds1NfK3L6kh6IcBByMiACCMI1MXN0O1ld+0oHtyuo5C43l9p06H/n2ddJfjsgKJAwEI2gQARzBEAiBi63pVYQenxz9FrEq1od3fb3B1+xJ1lpp/OD7/94S8sgIgDAXbt0cNvy8IVX3TVscyXB7TCRPpls04QJRdsSIo2l8BRzBEAiBl9FulmYtZon/+GnvtAWrx8fkNVLOqj3RQql9WolEDvQIgf3JHA60e25ZoCyhLVtT/y4j3+3Weq74IqjDym4UTg9IBR1IhAwidwQx6xttU+RMpr2FzM9s4jOrQwjH3IzedG5kDCwLcIQI63ZBPPW3PWd25BrDe4jUpt/+57VDl6GFRkmhgIh8Oc1KuACICA6mkw39ZltOqJdusa1cK8GUDlEkpQkYLNUdT7Z7spYdxENkMak8AAACAAAAAgAQAAIAAIgICf2OZdX0u/1WhNq0CxoSxg4tlVuXxtrNCgqlLa1AFEJYQ2QxqTwAAAIAAAACABQAAgAA=
* Case: PSBT with invalid final scriptsig typed key ** Bytes in Hex:
70736274ff01009a020000000258e87a21b56daf0c23be8e7070456c336f7cbaa5c8757924f545887bb2abdd750000000000ffffffff838d0427d0ec650a68aa46bb0b098aea4422c071b2ca78352a077959d07cea1d0100000000ffffffff0270aaf00800000000160014d85c2b71d0060b09c9886aeb815e50991dda124d00e1f5050000000016001400aea9a2e5f0f876a588df5546e8742d1d87008f00000000000100bb0200000001aad73931018bd25f84ae400b68848be09db706eac2ac18298babee71ab656f8b0000000048473044022058f6fc7c6a33e1b31548d481c826c015bd30135aad42cd67790dab66d2ad243b02204a1ced2604c6735b6393e5b41691dd78b00f0c5942fb9f751856faa938157dba01feffffff0280f0fa020000000017a9140fb9463421696b82c833af241c78c17ddbde493487d0f20a270100000017a91429ca74f8a08f81999428185c97b5d852e4063f618765000000020700da00473044022074018ad4180097b873323c0015720b3684cc8123891048e7dbcd9b55ad679c99022073d369b740e3eb53dcefa33823c8070514ca55a7dd9544f157c167913261118c01483045022100f61038b308dc1da865a34852746f015772934208c6d24454393cd99bdf2217770220056e675a675a6d0a02b85b14e5e29074d8a25a9b5760bea2816f661910a006ea01475221029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f2102dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d752ae0001012000c2eb0b0000000017a914b7f5faf40e3d40a5a459b1db3535f2b72fa921e8870107232200208c2353173743b595dfb4a07b72ba8e42e3797da74e87fe7d9d7497e3b20289030108da0400473044022062eb7a556107a7c73f45ac4ab5a1dddf6f7075fb1275969a7f383efff784bcb202200c05dbb7470dbf2f08557dd356c7325c1ed30913e996cd3840945db12228da5f01473044022065f45ba5998b59a27ffe1a7bed016af1f1f90d54b3aa8f7450aa5f56a25103bd02207f724703ad1edb96680b284b56d4ffcb88f7fb759eabbe08aa30f29b851383d20147522103089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc21023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7352ae00220203a9a4c37f5996d3aa25dbac6b570af0650394492942460b354753ed9eeca5877110d90c6a4f000000800000008004000080002202027f6399757d2eff55a136ad02c684b1838b6556e5f1b6b34282a94b6b5005109610d90c6a4f00000080000000800500008000
** Base64 String:
cHNidP8BAJoCAAAAAljoeiG1ba8MI76OcHBFbDNvfLqlyHV5JPVFiHuyq911AAAAAAD/////g40EJ9DsZQpoqka7CwmK6kQiwHGyyng1Kgd5WdB86h0BAAAAAP////8CcKrwCAAAAAAWABTYXCtx0AYLCcmIauuBXlCZHdoSTQDh9QUAAAAAFgAUAK6pouXw+HaliN9VRuh0LR2HAI8AAAAAAAEAuwIAAAABqtc5MQGL0l+ErkALaISL4J23BurCrBgpi6vucatlb4sAAAAASEcwRAIgWPb8fGoz4bMVSNSByCbAFb0wE1qtQs1neQ2rZtKtJDsCIEoc7SYExnNbY5PltBaR3XiwDwxZQvufdRhW+qk4FX26Af7///8CgPD6AgAAAAAXqRQPuUY0IWlrgsgzryQceMF9295JNIfQ8gonAQAAABepFCnKdPigj4GZlCgYXJe12FLkBj9hh2UAAAACBwDaAEcwRAIgdAGK1BgAl7hzMjwAFXILNoTMgSOJEEjn282bVa1nnJkCIHPTabdA4+tT3O+jOCPIBwUUylWn3ZVE8VfBZ5EyYRGMAUgwRQIhAPYQOLMI3B2oZaNIUnRvAVdyk0IIxtJEVDk82ZvfIhd3AiAFbmdaZ1ptCgK4WxTl4pB02KJam1dgvqKBb2YZEKAG6gFHUiEClYO/Oa4KYJdHrRma3dY0+mEIVZ1sXNObTCGD8auW4H8hAtq2H/SaFNtqfQKwzR+7ePxLGDErW05U2uTbovv+9TbXUq4AAQEgAMLrCwAAAAAXqRS39fr0Dj1ApaRZsds1NfK3L6kh6IcBByMiACCMI1MXN0O1ld+0oHtyuo5C43l9p06H/n2ddJfjsgKJAwEI2gQARzBEAiBi63pVYQenxz9FrEq1od3fb3B1+xJ1lpp/OD7/94S8sgIgDAXbt0cNvy8IVX3TVscyXB7TCRPpls04QJRdsSIo2l8BRzBEAiBl9FulmYtZon/+GnvtAWrx8fkNVLOqj3RQql9WolEDvQIgf3JHA60e25ZoCyhLVtT/y4j3+3Weq74IqjDym4UTg9IBR1IhAwidwQx6xttU+RMpr2FzM9s4jOrQwjH3IzedG5kDCwLcIQI63ZBPPW3PWd25BrDe4jUpt/+57VDl6GFRkmhgIh8Oc1KuACICA6mkw39ZltOqJdusa1cK8GUDlEkpQkYLNUdT7Z7spYdxENkMak8AAACAAAAAgAQAAIAAIgICf2OZdX0u/1WhNq0CxoSxg4tlVuXxtrNCgqlLa1AFEJYQ2QxqTwAAAIAAAACABQAAgAA=
* Case: PSBT with invalid final script witness typed key ** Bytes in Hex:
70736274ff01009a020000000258e87a21b56daf0c23be8e7070456c336f7cbaa5c8757924f545887bb2abdd750000000000ffffffff838d0427d0ec650a68aa46bb0b098aea4422c071b2ca78352a077959d07cea1d0100000000ffffffff0270aaf00800000000160014d85c2b71d0060b09c9886aeb815e50991dda124d00e1f5050000000016001400aea9a2e5f0f876a588df5546e8742d1d87008f00000000000100bb0200000001aad73931018bd25f84ae400b68848be09db706eac2ac18298babee71ab656f8b0000000048473044022058f6fc7c6a33e1b31548d481c826c015bd30135aad42cd67790dab66d2ad243b02204a1ced2604c6735b6393e5b41691dd78b00f0c5942fb9f751856faa938157dba01feffffff0280f0fa020000000017a9140fb9463421696b82c833af241c78c17ddbde493487d0f20a270100000017a91429ca74f8a08f81999428185c97b5d852e4063f6187650000000107da00473044022074018ad4180097b873323c0015720b3684cc8123891048e7dbcd9b55ad679c99022073d369b740e3eb53dcefa33823c8070514ca55a7dd9544f157c167913261118c01483045022100f61038b308dc1da865a34852746f015772934208c6d24454393cd99bdf2217770220056e675a675a6d0a02b85b14e5e29074d8a25a9b5760bea2816f661910a006ea01475221029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f2102dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d752ae0001012000c2eb0b0000000017a914b7f5faf40e3d40a5a459b1db3535f2b72fa921e8870107232200208c2353173743b595dfb4a07b72ba8e42e3797da74e87fe7d9d7497e3b2028903020800da0400473044022062eb7a556107a7c73f45ac4ab5a1dddf6f7075fb1275969a7f383efff784bcb202200c05dbb7470dbf2f08557dd356c7325c1ed30913e996cd3840945db12228da5f01473044022065f45ba5998b59a27ffe1a7bed016af1f1f90d54b3aa8f7450aa5f56a25103bd02207f724703ad1edb96680b284b56d4ffcb88f7fb759eabbe08aa30f29b851383d20147522103089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc21023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7352ae00220203a9a4c37f5996d3aa25dbac6b570af0650394492942460b354753ed9eeca5877110d90c6a4f000000800000008004000080002202027f6399757d2eff55a136ad02c684b1838b6556e5f1b6b34282a94b6b5005109610d90c6a4f00000080000000800500008000
** Base64 String:
cHNidP8BAJoCAAAAAljoeiG1ba8MI76OcHBFbDNvfLqlyHV5JPVFiHuyq911AAAAAAD/////g40EJ9DsZQpoqka7CwmK6kQiwHGyyng1Kgd5WdB86h0BAAAAAP////8CcKrwCAAAAAAWABTYXCtx0AYLCcmIauuBXlCZHdoSTQDh9QUAAAAAFgAUAK6pouXw+HaliN9VRuh0LR2HAI8AAAAAAAEAuwIAAAABqtc5MQGL0l+ErkALaISL4J23BurCrBgpi6vucatlb4sAAAAASEcwRAIgWPb8fGoz4bMVSNSByCbAFb0wE1qtQs1neQ2rZtKtJDsCIEoc7SYExnNbY5PltBaR3XiwDwxZQvufdRhW+qk4FX26Af7///8CgPD6AgAAAAAXqRQPuUY0IWlrgsgzryQceMF9295JNIfQ8gonAQAAABepFCnKdPigj4GZlCgYXJe12FLkBj9hh2UAAAABB9oARzBEAiB0AYrUGACXuHMyPAAVcgs2hMyBI4kQSOfbzZtVrWecmQIgc9Npt0Dj61Pc76M4I8gHBRTKVafdlUTxV8FnkTJhEYwBSDBFAiEA9hA4swjcHahlo0hSdG8BV3KTQgjG0kRUOTzZm98iF3cCIAVuZ1pnWm0KArhbFOXikHTYolqbV2C+ooFvZhkQoAbqAUdSIQKVg785rgpgl0etGZrd1jT6YQhVnWxc05tMIYPxq5bgfyEC2rYf9JoU22p9ArDNH7t4/EsYMStbTlTa5Nui+/71NtdSrgABASAAwusLAAAAABepFLf1+vQOPUClpFmx2zU18rcvqSHohwEHIyIAIIwjUxc3Q7WV37Sge3K6jkLjeX2nTof+fZ10l+OyAokDAggA2gQARzBEAiBi63pVYQenxz9FrEq1od3fb3B1+xJ1lpp/OD7/94S8sgIgDAXbt0cNvy8IVX3TVscyXB7TCRPpls04QJRdsSIo2l8BRzBEAiBl9FulmYtZon/+GnvtAWrx8fkNVLOqj3RQql9WolEDvQIgf3JHA60e25ZoCyhLVtT/y4j3+3Weq74IqjDym4UTg9IBR1IhAwidwQx6xttU+RMpr2FzM9s4jOrQwjH3IzedG5kDCwLcIQI63ZBPPW3PWd25BrDe4jUpt/+57VDl6GFRkmhgIh8Oc1KuACICA6mkw39ZltOqJdusa1cK8GUDlEkpQkYLNUdT7Z7spYdxENkMak8AAACAAAAAgAQAAIAAIgICf2OZdX0u/1WhNq0CxoSxg4tlVuXxtrNCgqlLa1AFEJYQ2QxqTwAAAIAAAACABQAAgAA=
* Case: PSBT with invalid pubkey in output BIP 32 derivation paths typed key ** Bytes in Hex:
70736274ff01009a020000000258e87a21b56daf0c23be8e7070456c336f7cbaa5c8757924f545887bb2abdd750000000000ffffffff838d0427d0ec650a68aa46bb0b098aea4422c071b2ca78352a077959d07cea1d0100000000ffffffff0270aaf00800000000160014d85c2b71d0060b09c9886aeb815e50991dda124d00e1f5050000000016001400aea9a2e5f0f876a588df5546e8742d1d87008f00000000000100bb0200000001aad73931018bd25f84ae400b68848be09db706eac2ac18298babee71ab656f8b0000000048473044022058f6fc7c6a33e1b31548d481c826c015bd30135aad42cd67790dab66d2ad243b02204a1ced2604c6735b6393e5b41691dd78b00f0c5942fb9f751856faa938157dba01feffffff0280f0fa020000000017a9140fb9463421696b82c833af241c78c17ddbde493487d0f20a270100000017a91429ca74f8a08f81999428185c97b5d852e4063f6187650000000107da00473044022074018ad4180097b873323c0015720b3684cc8123891048e7dbcd9b55ad679c99022073d369b740e3eb53dcefa33823c8070514ca55a7dd9544f157c167913261118c01483045022100f61038b308dc1da865a34852746f015772934208c6d24454393cd99bdf2217770220056e675a675a6d0a02b85b14e5e29074d8a25a9b5760bea2816f661910a006ea01475221029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f2102dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d752ae0001012000c2eb0b0000000017a914b7f5faf40e3d40a5a459b1db3535f2b72fa921e8870107232200208c2353173743b595dfb4a07b72ba8e42e3797da74e87fe7d9d7497e3b20289030108da0400473044022062eb7a556107a7c73f45ac4ab5a1dddf6f7075fb1275969a7f383efff784bcb202200c05dbb7470dbf2f08557dd356c7325c1ed30913e996cd3840945db12228da5f01473044022065f45ba5998b59a27ffe1a7bed016af1f1f90d54b3aa8f7450aa5f56a25103bd02207f724703ad1edb96680b284b56d4ffcb88f7fb759eabbe08aa30f29b851383d20147522103089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc21023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7352ae00210203a9a4c37f5996d3aa25dbac6b570af0650394492942460b354753ed9eeca58710d90c6a4f000000800000008004000080002202027f6399757d2eff55a136ad02c684b1838b6556e5f1b6b34282a94b6b5005109610d90c6a4f00000080000000800500008000
** Base64 String:
cHNidP8BAJoCAAAAAljoeiG1ba8MI76OcHBFbDNvfLqlyHV5JPVFiHuyq911AAAAAAD/////g40EJ9DsZQpoqka7CwmK6kQiwHGyyng1Kgd5WdB86h0BAAAAAP////8CcKrwCAAAAAAWABTYXCtx0AYLCcmIauuBXlCZHdoSTQDh9QUAAAAAFgAUAK6pouXw+HaliN9VRuh0LR2HAI8AAAAAAAEAuwIAAAABqtc5MQGL0l+ErkALaISL4J23BurCrBgpi6vucatlb4sAAAAASEcwRAIgWPb8fGoz4bMVSNSByCbAFb0wE1qtQs1neQ2rZtKtJDsCIEoc7SYExnNbY5PltBaR3XiwDwxZQvufdRhW+qk4FX26Af7///8CgPD6AgAAAAAXqRQPuUY0IWlrgsgzryQceMF9295JNIfQ8gonAQAAABepFCnKdPigj4GZlCgYXJe12FLkBj9hh2UAAAABB9oARzBEAiB0AYrUGACXuHMyPAAVcgs2hMyBI4kQSOfbzZtVrWecmQIgc9Npt0Dj61Pc76M4I8gHBRTKVafdlUTxV8FnkTJhEYwBSDBFAiEA9hA4swjcHahlo0hSdG8BV3KTQgjG0kRUOTzZm98iF3cCIAVuZ1pnWm0KArhbFOXikHTYolqbV2C+ooFvZhkQoAbqAUdSIQKVg785rgpgl0etGZrd1jT6YQhVnWxc05tMIYPxq5bgfyEC2rYf9JoU22p9ArDNH7t4/EsYMStbTlTa5Nui+/71NtdSrgABASAAwusLAAAAABepFLf1+vQOPUClpFmx2zU18rcvqSHohwEHIyIAIIwjUxc3Q7WV37Sge3K6jkLjeX2nTof+fZ10l+OyAokDAQjaBABHMEQCIGLrelVhB6fHP0WsSrWh3d9vcHX7EnWWmn84Pv/3hLyyAiAMBdu3Rw2/LwhVfdNWxzJcHtMJE+mWzThAlF2xIijaXwFHMEQCIGX0W6WZi1mif/4ae+0BavHx+Q1Us6qPdFCqX1aiUQO9AiB/ckcDrR7blmgLKEtW1P/LiPf7dZ6rvgiqMPKbhROD0gFHUiEDCJ3BDHrG21T5EymvYXMz2ziM6tDCMfcjN50bmQMLAtwhAjrdkE89bc9Z3bkGsN7iNSm3/7ntUOXoYVGSaGAiHw5zUq4AIQIDqaTDf1mW06ol26xrVwrwZQOUSSlCRgs1R1PtnuylhxDZDGpPAAAAgAAAAIAEAACAACICAn9jmXV9Lv9VoTatAsaEsYOLZVbl8bazQoKpS2tQBRCWENkMak8AAACAAAAAgAUAAIAA
* Case: PSBT with invalid input sighash type typed key ** Bytes in Hex:
70736274ff0100730200000001301ae986e516a1ec8ac5b4bc6573d32f83b465e23ad76167d68b38e730b4dbdb0000000000ffffffff02747b01000000000017a91403aa17ae882b5d0d54b25d63104e4ffece7b9ea2876043993b0000000017a914b921b1ba6f722e4bfa83b6557a3139986a42ec8387000000000001011f00ca9a3b00000000160014d2d94b64ae08587eefc8eeb187c601e939f9037c0203000100000000010016001462e9e982fff34dd8239610316b090cd2a3b747cb000100220020876bad832f1d168015ed41232a9ea65a1815d9ef13c0ef8759f64b5b2b278a65010125512103b7ce23a01c5b4bf00a642537cdfabb315b668332867478ef51309d2bd57f8a8751ae00
** Base64 String:
cHNidP8BAHMCAAAAATAa6YblFqHsisW0vGVz0y+DtGXiOtdhZ9aLOOcwtNvbAAAAAAD/////AnR7AQAAAAAAF6kUA6oXrogrXQ1Usl1jEE5P/s57nqKHYEOZOwAAAAAXqRS5IbG6b3IuS/qDtlV6MTmYakLsg4cAAAAAAAEBHwDKmjsAAAAAFgAU0tlLZK4IWH7vyO6xh8YB6Tn5A3wCAwABAAAAAAEAFgAUYunpgv/zTdgjlhAxawkM0qO3R8sAAQAiACCHa62DLx0WgBXtQSMqnqZaGBXZ7xPA74dZ9ktbKyeKZQEBJVEhA7fOI6AcW0vwCmQlN836uzFbZoMyhnR471EwnSvVf4qHUa4A
* Case: PSBT with invalid output redeemScript typed key ** Bytes in Hex:
70736274ff0100730200000001301ae986e516a1ec8ac5b4bc6573d32f83b465e23ad76167d68b38e730b4dbdb0000000000ffffffff02747b01000000000017a91403aa17ae882b5d0d54b25d63104e4ffece7b9ea2876043993b0000000017a914b921b1ba6f722e4bfa83b6557a3139986a42ec8387000000000001011f00ca9a3b00000000160014d2d94b64ae08587eefc8eeb187c601e939f9037c0002000016001462e9e982fff34dd8239610316b090cd2a3b747cb000100220020876bad832f1d168015ed41232a9ea65a1815d9ef13c0ef8759f64b5b2b278a65010125512103b7ce23a01c5b4bf00a642537cdfabb315b668332867478ef51309d2bd57f8a8751ae00
** Base64 String:
cHNidP8BAHMCAAAAATAa6YblFqHsisW0vGVz0y+DtGXiOtdhZ9aLOOcwtNvbAAAAAAD/////AnR7AQAAAAAAF6kUA6oXrogrXQ1Usl1jEE5P/s57nqKHYEOZOwAAAAAXqRS5IbG6b3IuS/qDtlV6MTmYakLsg4cAAAAAAAEBHwDKmjsAAAAAFgAU0tlLZK4IWH7vyO6xh8YB6Tn5A3wAAgAAFgAUYunpgv/zTdgjlhAxawkM0qO3R8sAAQAiACCHa62DLx0WgBXtQSMqnqZaGBXZ7xPA74dZ9ktbKyeKZQEBJVEhA7fOI6AcW0vwCmQlN836uzFbZoMyhnR471EwnSvVf4qHUa4A
* Case: PSBT with invalid output witnessScript typed key ** Bytes in Hex:
70736274ff0100730200000001301ae986e516a1ec8ac5b4bc6573d32f83b465e23ad76167d68b38e730b4dbdb0000000000ffffffff02747b01000000000017a91403aa17ae882b5d0d54b25d63104e4ffece7b9ea2876043993b0000000017a914b921b1ba6f722e4bfa83b6557a3139986a42ec8387000000000001011f00ca9a3b00000000160014d2d94b64ae08587eefc8eeb187c601e939f9037c00010016001462e9e982fff34dd8239610316b090cd2a3b747cb000100220020876bad832f1d168015ed41232a9ea65a1815d9ef13c0ef8759f64b5b2b278a6521010025512103b7ce23a01c5b4bf00a642537cdfabb315b668332867478ef51309d06d57f8a8751ae00
** Base64 String:
cHNidP8BAHMCAAAAATAa6YblFqHsisW0vGVz0y+DtGXiOtdhZ9aLOOcwtNvbAAAAAAD/////AnR7AQAAAAAAF6kUA6oXrogrXQ1Usl1jEE5P/s57nqKHYEOZOwAAAAAXqRS5IbG6b3IuS/qDtlV6MTmYakLsg4cAAAAAAAEBHwDKmjsAAAAAFgAU0tlLZK4IWH7vyO6xh8YB6Tn5A3wAAQAWABRi6emC//NN2COWEDFrCQzSo7dHywABACIAIIdrrYMvHRaAFe1BIyqeploYFdnvE8Dvh1n2S1srJ4plIQEAJVEhA7fOI6AcW0vwCmQlN836uzFbZoMyhnR471EwnQbVf4qHUa4A
* Case: PSBT with unsigned tx serialized with witness serialization format ** Bytes in Hex:
70736274ff01007802000000000101268171371edff285e937adeea4b37b78000c0566cbb3ad64641713ca42171bf60000000000feffffff02d3dff505000000001976a914d0c59903c5bac2868760e90fd521a4665aa7652088ac00e1f5050000000017a9143545e6e33b832c47050f24d3eeb93c9c03948bc78700b32e1300000100fda5010100000000010289a3c71eab4d20e0371bbba4cc698fa295c9463afa2e397f8533ccb62f9567e50100000017160014be18d152a9b012039daf3da7de4f53349eecb985ffffffff86f8aa43a71dff1448893a530a7237ef6b4608bbb2dd2d0171e63aec6a4890b40100000017160014fe3e9ef1a745e974d902c4355943abcb34bd5353ffffffff0200c2eb0b000000001976a91485cff1097fd9e008bb34af709c62197b38978a4888ac72fef84e2c00000017a914339725ba21efd62ac753a9bcd067d6c7a6a39d05870247304402202712be22e0270f394f568311dc7ca9a68970b8025fdd3b240229f07f8a5f3a240220018b38d7dcd314e734c9276bd6fb40f673325bc4baa144c800d2f2f02db2765c012103d2e15674941bad4a996372cb87e1856d3652606d98562fe39c5e9e7e413f210502483045022100d12b852d85dcd961d2f5f4ab660654df6eedcc794c0c33ce5cc309ffb5fce58d022067338a8e0e1725c197fb1a88af59f51e44e4255b20167c8684031c05d1f2592a01210223b72beef0965d10be0778efecd61fcac6f79a4ea169393380734464f84f2ab300000000000000
** Base64 String:
cHNidP8BAHgCAAAAAAEBJoFxNx7f8oXpN63upLN7eAAMBWbLs61kZBcTykIXG/YAAAAAAP7///8C09/1BQAAAAAZdqkU0MWZA8W6woaHYOkP1SGkZlqnZSCIrADh9QUAAAAAF6kUNUXm4zuDLEcFDyTT7rk8nAOUi8eHALMuEwAAAQD9pQEBAAAAAAECiaPHHqtNIOA3G7ukzGmPopXJRjr6Ljl/hTPMti+VZ+UBAAAAFxYAFL4Y0VKpsBIDna89p95PUzSe7LmF/////4b4qkOnHf8USIk6UwpyN+9rRgi7st0tAXHmOuxqSJC0AQAAABcWABT+Pp7xp0XpdNkCxDVZQ6vLNL1TU/////8CAMLrCwAAAAAZdqkUhc/xCX/Z4Ai7NK9wnGIZeziXikiIrHL++E4sAAAAF6kUM5cluiHv1irHU6m80GfWx6ajnQWHAkcwRAIgJxK+IuAnDzlPVoMR3HyppolwuAJf3TskAinwf4pfOiQCIAGLONfc0xTnNMkna9b7QPZzMlvEuqFEyADS8vAtsnZcASED0uFWdJQbrUqZY3LLh+GFbTZSYG2YVi/jnF6efkE/IQUCSDBFAiEA0SuFLYXc2WHS9fSrZgZU327tzHlMDDPOXMMJ/7X85Y0CIGczio4OFyXBl/saiK9Z9R5E5CVbIBZ8hoQDHAXR8lkqASECI7cr7vCWXRC+B3jv7NYfysb3mk6haTkzgHNEZPhPKrMAAAAAAAAA
* Case: PSBT with an invalid value data due to its size being not the stated size ** Bytes in Hex:
70736274ff0100337401ff0700010000000100ff01000a73317428ff0000000001ff010301000001000000000000000076010000004100090000000000
** Base64 String:
cHNidP8BADN0Af8HAAEAAAABAP8BAApzMXQo/wAAAAAB/wEDAQAAAQAAAAAAAAAAdgEAAABBAAkAAAAAAA==
The following are valid PSBTs: * Case: PSBT with one P2PKH input. Outputs are empty ** Bytes in Hex:
70736274ff0100750200000001268171371edff285e937adeea4b37b78000c0566cbb3ad64641713ca42171bf60000000000feffffff02d3dff505000000001976a914d0c59903c5bac2868760e90fd521a4665aa7652088ac00e1f5050000000017a9143545e6e33b832c47050f24d3eeb93c9c03948bc787b32e1300000100fda5010100000000010289a3c71eab4d20e0371bbba4cc698fa295c9463afa2e397f8533ccb62f9567e50100000017160014be18d152a9b012039daf3da7de4f53349eecb985ffffffff86f8aa43a71dff1448893a530a7237ef6b4608bbb2dd2d0171e63aec6a4890b40100000017160014fe3e9ef1a745e974d902c4355943abcb34bd5353ffffffff0200c2eb0b000000001976a91485cff1097fd9e008bb34af709c62197b38978a4888ac72fef84e2c00000017a914339725ba21efd62ac753a9bcd067d6c7a6a39d05870247304402202712be22e0270f394f568311dc7ca9a68970b8025fdd3b240229f07f8a5f3a240220018b38d7dcd314e734c9276bd6fb40f673325bc4baa144c800d2f2f02db2765c012103d2e15674941bad4a996372cb87e1856d3652606d98562fe39c5e9e7e413f210502483045022100d12b852d85dcd961d2f5f4ab660654df6eedcc794c0c33ce5cc309ffb5fce58d022067338a8e0e1725c197fb1a88af59f51e44e4255b20167c8684031c05d1f2592a01210223b72beef0965d10be0778efecd61fcac6f79a4ea169393380734464f84f2ab300000000000000
** Base64 String:
cHNidP8BAHUCAAAAASaBcTce3/KF6Tet7qSze3gADAVmy7OtZGQXE8pCFxv2AAAAAAD+////AtPf9QUAAAAAGXapFNDFmQPFusKGh2DpD9UhpGZap2UgiKwA4fUFAAAAABepFDVF5uM7gyxHBQ8k0+65PJwDlIvHh7MuEwAAAQD9pQEBAAAAAAECiaPHHqtNIOA3G7ukzGmPopXJRjr6Ljl/hTPMti+VZ+UBAAAAFxYAFL4Y0VKpsBIDna89p95PUzSe7LmF/////4b4qkOnHf8USIk6UwpyN+9rRgi7st0tAXHmOuxqSJC0AQAAABcWABT+Pp7xp0XpdNkCxDVZQ6vLNL1TU/////8CAMLrCwAAAAAZdqkUhc/xCX/Z4Ai7NK9wnGIZeziXikiIrHL++E4sAAAAF6kUM5cluiHv1irHU6m80GfWx6ajnQWHAkcwRAIgJxK+IuAnDzlPVoMR3HyppolwuAJf3TskAinwf4pfOiQCIAGLONfc0xTnNMkna9b7QPZzMlvEuqFEyADS8vAtsnZcASED0uFWdJQbrUqZY3LLh+GFbTZSYG2YVi/jnF6efkE/IQUCSDBFAiEA0SuFLYXc2WHS9fSrZgZU327tzHlMDDPOXMMJ/7X85Y0CIGczio4OFyXBl/saiK9Z9R5E5CVbIBZ8hoQDHAXR8lkqASECI7cr7vCWXRC+B3jv7NYfysb3mk6haTkzgHNEZPhPKrMAAAAAAAAA
* Case: PSBT with one P2PKH input and one P2SH-P2WPKH input. First input is signed and finalized. Outputs are empty ** Bytes in Hex:
70736274ff0100a00200000002ab0949a08c5af7c49b8212f417e2f15ab3f5c33dcf153821a8139f877a5b7be40000000000feffffffab0949a08c5af7c49b8212f417e2f15ab3f5c33dcf153821a8139f877a5b7be40100000000feffffff02603bea0b000000001976a914768a40bbd740cbe81d988e71de2a4d5c71396b1d88ac8e240000000000001976a9146f4620b553fa095e721b9ee0efe9fa039cca459788ac000000000001076a47304402204759661797c01b036b25928948686218347d89864b719e1f7fcf57d1e511658702205309eabf56aa4d8891ffd111fdf1336f3a29da866d7f8486d75546ceedaf93190121035cdc61fc7ba971c0b501a646a2a83b102cb43881217ca682dc86e2d73fa882920001012000e1f5050000000017a9143545e6e33b832c47050f24d3eeb93c9c03948bc787010416001485d13537f2e265405a34dbafa9e3dda01fb82308000000
** Base64 String:
cHNidP8BAKACAAAAAqsJSaCMWvfEm4IS9Bfi8Vqz9cM9zxU4IagTn4d6W3vkAAAAAAD+////qwlJoIxa98SbghL0F+LxWrP1wz3PFTghqBOfh3pbe+QBAAAAAP7///8CYDvqCwAAAAAZdqkUdopAu9dAy+gdmI5x3ipNXHE5ax2IrI4kAAAAAAAAGXapFG9GILVT+glechue4O/p+gOcykWXiKwAAAAAAAEHakcwRAIgR1lmF5fAGwNrJZKJSGhiGDR9iYZLcZ4ff89X0eURZYcCIFMJ6r9Wqk2Ikf/REf3xM286KdqGbX+EhtdVRs7tr5MZASEDXNxh/HupccC1AaZGoqg7ECy0OIEhfKaC3Ibi1z+ogpIAAQEgAOH1BQAAAAAXqRQ1RebjO4MsRwUPJNPuuTycA5SLx4cBBBYAFIXRNTfy4mVAWjTbr6nj3aAfuCMIAAAA
* Case: PSBT with one P2PKH input which has a non-final scriptSig and has a sighash type specified. Outputs are empty ** Bytes in Hex:
70736274ff0100750200000001268171371edff285e937adeea4b37b78000c0566cbb3ad64641713ca42171bf60000000000feffffff02d3dff505000000001976a914d0c59903c5bac2868760e90fd521a4665aa7652088ac00e1f5050000000017a9143545e6e33b832c47050f24d3eeb93c9c03948bc787b32e1300000100fda5010100000000010289a3c71eab4d20e0371bbba4cc698fa295c9463afa2e397f8533ccb62f9567e50100000017160014be18d152a9b012039daf3da7de4f53349eecb985ffffffff86f8aa43a71dff1448893a530a7237ef6b4608bbb2dd2d0171e63aec6a4890b40100000017160014fe3e9ef1a745e974d902c4355943abcb34bd5353ffffffff0200c2eb0b000000001976a91485cff1097fd9e008bb34af709c62197b38978a4888ac72fef84e2c00000017a914339725ba21efd62ac753a9bcd067d6c7a6a39d05870247304402202712be22e0270f394f568311dc7ca9a68970b8025fdd3b240229f07f8a5f3a240220018b38d7dcd314e734c9276bd6fb40f673325bc4baa144c800d2f2f02db2765c012103d2e15674941bad4a996372cb87e1856d3652606d98562fe39c5e9e7e413f210502483045022100d12b852d85dcd961d2f5f4ab660654df6eedcc794c0c33ce5cc309ffb5fce58d022067338a8e0e1725c197fb1a88af59f51e44e4255b20167c8684031c05d1f2592a01210223b72beef0965d10be0778efecd61fcac6f79a4ea169393380734464f84f2ab30000000001030401000000000000
** Base64 String:
cHNidP8BAHUCAAAAASaBcTce3/KF6Tet7qSze3gADAVmy7OtZGQXE8pCFxv2AAAAAAD+////AtPf9QUAAAAAGXapFNDFmQPFusKGh2DpD9UhpGZap2UgiKwA4fUFAAAAABepFDVF5uM7gyxHBQ8k0+65PJwDlIvHh7MuEwAAAQD9pQEBAAAAAAECiaPHHqtNIOA3G7ukzGmPopXJRjr6Ljl/hTPMti+VZ+UBAAAAFxYAFL4Y0VKpsBIDna89p95PUzSe7LmF/////4b4qkOnHf8USIk6UwpyN+9rRgi7st0tAXHmOuxqSJC0AQAAABcWABT+Pp7xp0XpdNkCxDVZQ6vLNL1TU/////8CAMLrCwAAAAAZdqkUhc/xCX/Z4Ai7NK9wnGIZeziXikiIrHL++E4sAAAAF6kUM5cluiHv1irHU6m80GfWx6ajnQWHAkcwRAIgJxK+IuAnDzlPVoMR3HyppolwuAJf3TskAinwf4pfOiQCIAGLONfc0xTnNMkna9b7QPZzMlvEuqFEyADS8vAtsnZcASED0uFWdJQbrUqZY3LLh+GFbTZSYG2YVi/jnF6efkE/IQUCSDBFAiEA0SuFLYXc2WHS9fSrZgZU327tzHlMDDPOXMMJ/7X85Y0CIGczio4OFyXBl/saiK9Z9R5E5CVbIBZ8hoQDHAXR8lkqASECI7cr7vCWXRC+B3jv7NYfysb3mk6haTkzgHNEZPhPKrMAAAAAAQMEAQAAAAAAAA==
* Case: PSBT with one P2PKH input and one P2SH-P2WPKH input both with non-final scriptSigs. P2SH-P2WPKH input's redeemScript is available. Outputs filled. ** Bytes in Hex:
70736274ff0100a00200000002ab0949a08c5af7c49b8212f417e2f15ab3f5c33dcf153821a8139f877a5b7be40000000000feffffffab0949a08c5af7c49b8212f417e2f15ab3f5c33dcf153821a8139f877a5b7be40100000000feffffff02603bea0b000000001976a914768a40bbd740cbe81d988e71de2a4d5c71396b1d88ac8e240000000000001976a9146f4620b553fa095e721b9ee0efe9fa039cca459788ac00000000000100df0200000001268171371edff285e937adeea4b37b78000c0566cbb3ad64641713ca42171bf6000000006a473044022070b2245123e6bf474d60c5b50c043d4c691a5d2435f09a34a7662a9dc251790a022001329ca9dacf280bdf30740ec0390422422c81cb45839457aeb76fc12edd95b3012102657d118d3357b8e0f4c2cd46db7b39f6d9c38d9a70abcb9b2de5dc8dbfe4ce31feffffff02d3dff505000000001976a914d0c59903c5bac2868760e90fd521a4665aa7652088ac00e1f5050000000017a9143545e6e33b832c47050f24d3eeb93c9c03948bc787b32e13000001012000e1f5050000000017a9143545e6e33b832c47050f24d3eeb93c9c03948bc787010416001485d13537f2e265405a34dbafa9e3dda01fb8230800220202ead596687ca806043edc3de116cdf29d5e9257c196cd055cf698c8d02bf24e9910b4a6ba670000008000000080020000800022020394f62be9df19952c5587768aeb7698061ad2c4a25c894f47d8c162b4d7213d0510b4a6ba6700000080010000800200008000
** Base64 String:
cHNidP8BAKACAAAAAqsJSaCMWvfEm4IS9Bfi8Vqz9cM9zxU4IagTn4d6W3vkAAAAAAD+////qwlJoIxa98SbghL0F+LxWrP1wz3PFTghqBOfh3pbe+QBAAAAAP7///8CYDvqCwAAAAAZdqkUdopAu9dAy+gdmI5x3ipNXHE5ax2IrI4kAAAAAAAAGXapFG9GILVT+glechue4O/p+gOcykWXiKwAAAAAAAEA3wIAAAABJoFxNx7f8oXpN63upLN7eAAMBWbLs61kZBcTykIXG/YAAAAAakcwRAIgcLIkUSPmv0dNYMW1DAQ9TGkaXSQ18Jo0p2YqncJReQoCIAEynKnazygL3zB0DsA5BCJCLIHLRYOUV663b8Eu3ZWzASECZX0RjTNXuOD0ws1G23s59tnDjZpwq8ubLeXcjb/kzjH+////AtPf9QUAAAAAGXapFNDFmQPFusKGh2DpD9UhpGZap2UgiKwA4fUFAAAAABepFDVF5uM7gyxHBQ8k0+65PJwDlIvHh7MuEwAAAQEgAOH1BQAAAAAXqRQ1RebjO4MsRwUPJNPuuTycA5SLx4cBBBYAFIXRNTfy4mVAWjTbr6nj3aAfuCMIACICAurVlmh8qAYEPtw94RbN8p1eklfBls0FXPaYyNAr8k6ZELSmumcAAACAAAAAgAIAAIAAIgIDlPYr6d8ZlSxVh3aK63aYBhrSxKJciU9H2MFitNchPQUQtKa6ZwAAAIABAACAAgAAgAA=
* Case: PSBT with one P2SH-P2WSH input of a 2-of-2 multisig, redeemScript, witnessScript, and keypaths are available. Contains one signature. ** Bytes in Hex:
70736274ff0100550200000001279a2323a5dfb51fc45f220fa58b0fc13e1e3342792a85d7e36cd6333b5cbc390000000000ffffffff01a05aea0b000000001976a914ffe9c0061097cc3b636f2cb0460fa4fc427d2b4588ac0000000000010120955eea0b0000000017a9146345200f68d189e1adc0df1c4d16ea8f14c0dbeb87220203b1341ccba7683b6af4f1238cd6e97e7167d569fac47f1e48d47541844355bd4646304302200424b58effaaa694e1559ea5c93bbfd4a89064224055cdf070b6771469442d07021f5c8eb0fea6516d60b8acb33ad64ede60e8785bfb3aa94b99bdf86151db9a9a010104220020771fd18ad459666dd49f3d564e3dbc42f4c84774e360ada16816a8ed488d5681010547522103b1341ccba7683b6af4f1238cd6e97e7167d569fac47f1e48d47541844355bd462103de55d1e1dac805e3f8a58c1fbf9b94c02f3dbaafe127fefca4995f26f82083bd52ae220603b1341ccba7683b6af4f1238cd6e97e7167d569fac47f1e48d47541844355bd4610b4a6ba67000000800000008004000080220603de55d1e1dac805e3f8a58c1fbf9b94c02f3dbaafe127fefca4995f26f82083bd10b4a6ba670000008000000080050000800000
** Base64 String:
cHNidP8BAFUCAAAAASeaIyOl37UfxF8iD6WLD8E+HjNCeSqF1+Ns1jM7XLw5AAAAAAD/////AaBa6gsAAAAAGXapFP/pwAYQl8w7Y28ssEYPpPxCfStFiKwAAAAAAAEBIJVe6gsAAAAAF6kUY0UgD2jRieGtwN8cTRbqjxTA2+uHIgIDsTQcy6doO2r08SOM1ul+cWfVafrEfx5I1HVBhENVvUZGMEMCIAQktY7/qqaU4VWepck7v9SokGQiQFXN8HC2dxRpRC0HAh9cjrD+plFtYLisszrWTt5g6Hhb+zqpS5m9+GFR25qaAQEEIgAgdx/RitRZZm3Unz1WTj28QvTIR3TjYK2haBao7UiNVoEBBUdSIQOxNBzLp2g7avTxI4zW6X5xZ9Vp+sR/HkjUdUGEQ1W9RiED3lXR4drIBeP4pYwfv5uUwC89uq/hJ/78pJlfJvggg71SriIGA7E0HMunaDtq9PEjjNbpfnFn1Wn6xH8eSNR1QYRDVb1GELSmumcAAACAAAAAgAQAAIAiBgPeVdHh2sgF4/iljB+/m5TALz26r+En/vykmV8m+CCDvRC0prpnAAAAgAAAAIAFAACAAAA=
* Case: PSBT with one P2WSH input of a 2-of-2 multisig. witnessScript, keypaths, and global xpubs are available. Contains no signatures. Outputs filled. ** Bytes in Hex:
70736274ff01005202000000019dfc6628c26c5899fe1bd3dc338665bfd55d7ada10f6220973df2d386dec12760100000000ffffffff01f03dcd1d000000001600147b3a00bfdc14d27795c2b74901d09da6ef133579000000004f01043587cf02da3fd0088000000097048b1ad0445b1ec8275517727c87b4e4ebc18a203ffa0f94c01566bd38e9000351b743887ee1d40dc32a6043724f2d6459b3b5a4d73daec8fbae0472f3bc43e20cd90c6a4fae000080000000804f01043587cf02da3fd00880000001b90452427139cd78c2cff2444be353cd58605e3e513285e528b407fae3f6173503d30a5e97c8adbc557dac2ad9a7e39c1722ebac69e668b6f2667cc1d671c83cab0cd90c6a4fae000080010000800001012b0065cd1d000000002200202c5486126c4978079a814e13715d65f36459e4d6ccaded266d0508645bafa6320105475221029da12cdb5b235692b91536afefe5c91c3ab9473d8e43b533836ab456299c88712103372b34234ed7cf9c1fea5d05d441557927be9542b162eb02e1ab2ce80224c00b52ae2206029da12cdb5b235692b91536afefe5c91c3ab9473d8e43b533836ab456299c887110d90c6a4fae0000800000008000000000220603372b34234ed7cf9c1fea5d05d441557927be9542b162eb02e1ab2ce80224c00b10d90c6a4fae0000800100008000000000002202039eff1f547a1d5f92dfa2ba7af6ac971a4bd03ba4a734b03156a256b8ad3a1ef910ede45cc500000080000000800100008000
** Base64 String:
cHNidP8BAFICAAAAAZ38ZijCbFiZ/hvT3DOGZb/VXXraEPYiCXPfLTht7BJ2AQAAAAD/////AfA9zR0AAAAAFgAUezoAv9wU0neVwrdJAdCdpu8TNXkAAAAATwEENYfPAto/0AiAAAAAlwSLGtBEWx7IJ1UXcnyHtOTrwYogP/oPlMAVZr046QADUbdDiH7h1A3DKmBDck8tZFmztaTXPa7I+64EcvO8Q+IM2QxqT64AAIAAAACATwEENYfPAto/0AiAAAABuQRSQnE5zXjCz/JES+NTzVhgXj5RMoXlKLQH+uP2FzUD0wpel8itvFV9rCrZp+OcFyLrrGnmaLbyZnzB1nHIPKsM2QxqT64AAIABAACAAAEBKwBlzR0AAAAAIgAgLFSGEmxJeAeagU4TcV1l82RZ5NbMre0mbQUIZFuvpjIBBUdSIQKdoSzbWyNWkrkVNq/v5ckcOrlHPY5DtTODarRWKZyIcSEDNys0I07Xz5wf6l0F1EFVeSe+lUKxYusC4ass6AIkwAtSriIGAp2hLNtbI1aSuRU2r+/lyRw6uUc9jkO1M4NqtFYpnIhxENkMak+uAACAAAAAgAAAAAAiBgM3KzQjTtfPnB/qXQXUQVV5J76VQrFi6wLhqyzoAiTACxDZDGpPrgAAgAEAAIAAAAAAACICA57/H1R6HV+S36K6evaslxpL0DukpzSwMVaiVritOh75EO3kXMUAAACAAAAAgAEAAIAA
* Case: PSBT with unknown types in the inputs. ** Bytes in Hex:
70736274ff01003f0200000001ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0000000000ffffffff010000000000000000036a010000000000000af00102030405060708090f0102030405060708090a0b0c0d0e0f0000
** Base64 String:
cHNidP8BAD8CAAAAAf//////////////////////////////////////////AAAAAAD/////AQAAAAAAAAAAA2oBAAAAAAAACvABAgMEBQYHCAkPAQIDBAUGBwgJCgsMDQ4PAAA=
* Case: PSBT with `PSBT_GLOBAL_XPUB`. ** Bytes in Hex:
70736274ff01009d0100000002710ea76ab45c5cb6438e607e59cc037626981805ae9e0dfd9089012abb0be5350100000000ffffffff190994d6a8b3c8c82ccbcfb2fba4106aa06639b872a8d447465c0d42588d6d670000000000ffffffff0200e1f505000000001976a914b6bc2c0ee5655a843d79afedd0ccc3f7dd64340988ac605af405000000001600141188ef8e4ce0449eaac8fb141cbf5a1176e6a088000000004f010488b21e039e530cac800000003dbc8a5c9769f031b17e77fea1518603221a18fd18f2b9a54c6c8c1ac75cbc3502f230584b155d1c7f1cd45120a653c48d650b431b67c5b2c13f27d7142037c1691027569c503100008000000080000000800001011f00e1f5050000000016001433b982f91b28f160c920b4ab95e58ce50dda3a4a220203309680f33c7de38ea6a47cd4ecd66f1f5a49747c6ffb8808ed09039243e3ad5c47304402202d704ced830c56a909344bd742b6852dccd103e963bae92d38e75254d2bb424502202d86c437195df46c0ceda084f2a291c3da2d64070f76bf9b90b195e7ef28f77201220603309680f33c7de38ea6a47cd4ecd66f1f5a49747c6ffb8808ed09039243e3ad5c1827569c5031000080000000800000008000000000010000000001011f00e1f50500000000160014388fb944307eb77ef45197d0b0b245e079f011de220202c777161f73d0b7c72b9ee7bde650293d13f095bc7656ad1f525da5fd2e10b11047304402204cb1fb5f869c942e0e26100576125439179ae88dca8a9dc3ba08f7953988faa60220521f49ca791c27d70e273c9b14616985909361e25be274ea200d7e08827e514d01220602c777161f73d0b7c72b9ee7bde650293d13f095bc7656ad1f525da5fd2e10b1101827569c5031000080000000800000008000000000000000000000220202d20ca502ee289686d21815bd43a80637b0698e1fbcdbe4caed445f6c1a0a90ef1827569c50310000800000008000000080000000000400000000
** Base64 String:
cHNidP8BAJ0BAAAAAnEOp2q0XFy2Q45gflnMA3YmmBgFrp4N/ZCJASq7C+U1AQAAAAD/////GQmU1qizyMgsy8+y+6QQaqBmObhyqNRHRlwNQliNbWcAAAAAAP////8CAOH1BQAAAAAZdqkUtrwsDuVlWoQ9ea/t0MzD991kNAmIrGBa9AUAAAAAFgAUEYjvjkzgRJ6qyPsUHL9aEXbmoIgAAAAATwEEiLIeA55TDKyAAAAAPbyKXJdp8DGxfnf+oVGGAyIaGP0Y8rmlTGyMGsdcvDUC8jBYSxVdHH8c1FEgplPEjWULQxtnxbLBPyfXFCA3wWkQJ1acUDEAAIAAAACAAAAAgAABAR8A4fUFAAAAABYAFDO5gvkbKPFgySC0q5XljOUN2jpKIgIDMJaA8zx9446mpHzU7NZvH1pJdHxv+4gI7QkDkkPjrVxHMEQCIC1wTO2DDFapCTRL10K2hS3M0QPpY7rpLTjnUlTSu0JFAiAthsQ3GV30bAztoITyopHD2i1kBw92v5uQsZXn7yj3cgEiBgMwloDzPH3jjqakfNTs1m8fWkl0fG/7iAjtCQOSQ+OtXBgnVpxQMQAAgAAAAIAAAACAAAAAAAEAAAAAAQEfAOH1BQAAAAAWABQ4j7lEMH63fvRRl9CwskXgefAR3iICAsd3Fh9z0LfHK57nveZQKT0T8JW8dlatH1Jdpf0uELEQRzBEAiBMsftfhpyULg4mEAV2ElQ5F5rojcqKncO6CPeVOYj6pgIgUh9JynkcJ9cOJzybFGFphZCTYeJb4nTqIA1+CIJ+UU0BIgYCx3cWH3PQt8crnue95lApPRPwlbx2Vq0fUl2l/S4QsRAYJ1acUDEAAIAAAACAAAAAgAAAAAAAAAAAAAAiAgLSDKUC7iiWhtIYFb1DqAY3sGmOH7zb5MrtRF9sGgqQ7xgnVpxQMQAAgAAAAIAAAACAAAAAAAQAAAAA
* Case: PSBT with global unsigned tx that has 0 inputs and 0 outputs ** Bytes in Hex:
70736274ff01000a0000000000000000000000
** Base64 String:
cHNidP8BAAoAAAAAAAAAAAAAAA==
* Case: PSBT with 0 inputs ** Bytes in Hex:
70736274ff01004c020000000002d3dff505000000001976a914d0c59903c5bac2868760e90fd521a4665aa7652088ac00e1f5050000000017a9143545e6e33b832c47050f24d3eeb93c9c03948bc787b32e1300000000
** Base64 String:
cHNidP8BAEwCAAAAAALT3/UFAAAAABl2qRTQxZkDxbrChodg6Q/VIaRmWqdlIIisAOH1BQAAAAAXqRQ1RebjO4MsRwUPJNPuuTycA5SLx4ezLhMAAAAA
Fails Signer checks * Case: A Witness UTXO is provided for a non-witness input ** Bytes in Hex:
70736274ff0100a00200000002ab0949a08c5af7c49b8212f417e2f15ab3f5c33dcf153821a8139f877a5b7be40000000000feffffffab0949a08c5af7c49b8212f417e2f15ab3f5c33dcf153821a8139f877a5b7be40100000000feffffff02603bea0b000000001976a914768a40bbd740cbe81d988e71de2a4d5c71396b1d88ac8e240000000000001976a9146f4620b553fa095e721b9ee0efe9fa039cca459788ac0000000000010122d3dff505000000001976a914d48ed3110b94014cb114bd32d6f4d066dc74256b88ac0001012000e1f5050000000017a9143545e6e33b832c47050f24d3eeb93c9c03948bc787010416001485d13537f2e265405a34dbafa9e3dda01fb8230800220202ead596687ca806043edc3de116cdf29d5e9257c196cd055cf698c8d02bf24e9910b4a6ba670000008000000080020000800022020394f62be9df19952c5587768aeb7698061ad2c4a25c894f47d8c162b4d7213d0510b4a6ba6700000080010000800200008000
** Base64 String:
cHNidP8BAKACAAAAAqsJSaCMWvfEm4IS9Bfi8Vqz9cM9zxU4IagTn4d6W3vkAAAAAAD+////qwlJoIxa98SbghL0F+LxWrP1wz3PFTghqBOfh3pbe+QBAAAAAP7///8CYDvqCwAAAAAZdqkUdopAu9dAy+gdmI5x3ipNXHE5ax2IrI4kAAAAAAAAGXapFG9GILVT+glechue4O/p+gOcykWXiKwAAAAAAAEBItPf9QUAAAAAGXapFNSO0xELlAFMsRS9Mtb00GbcdCVriKwAAQEgAOH1BQAAAAAXqRQ1RebjO4MsRwUPJNPuuTycA5SLx4cBBBYAFIXRNTfy4mVAWjTbr6nj3aAfuCMIACICAurVlmh8qAYEPtw94RbN8p1eklfBls0FXPaYyNAr8k6ZELSmumcAAACAAAAAgAIAAIAAIgIDlPYr6d8ZlSxVh3aK63aYBhrSxKJciU9H2MFitNchPQUQtKa6ZwAAAIABAACAAgAAgAA=
* Case: redeemScript with non-witness UTXO does not match the scriptPubKey ** Bytes in Hex:
70736274ff01009a020000000258e87a21b56daf0c23be8e7070456c336f7cbaa5c8757924f545887bb2abdd750000000000ffffffff838d0427d0ec650a68aa46bb0b098aea4422c071b2ca78352a077959d07cea1d0100000000ffffffff0270aaf00800000000160014d85c2b71d0060b09c9886aeb815e50991dda124d00e1f5050000000016001400aea9a2e5f0f876a588df5546e8742d1d87008f00000000000100bb0200000001aad73931018bd25f84ae400b68848be09db706eac2ac18298babee71ab656f8b0000000048473044022058f6fc7c6a33e1b31548d481c826c015bd30135aad42cd67790dab66d2ad243b02204a1ced2604c6735b6393e5b41691dd78b00f0c5942fb9f751856faa938157dba01feffffff0280f0fa020000000017a9140fb9463421696b82c833af241c78c17ddbde493487d0f20a270100000017a91429ca74f8a08f81999428185c97b5d852e4063f618765000000220202dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d7483045022100f61038b308dc1da865a34852746f015772934208c6d24454393cd99bdf2217770220056e675a675a6d0a02b85b14e5e29074d8a25a9b5760bea2816f661910a006ea01010304010000000104475221029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f2102dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d752af2206029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f10d90c6a4f000000800000008000000080220602dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d710d90c6a4f0000008000000080010000800001012000c2eb0b0000000017a914b7f5faf40e3d40a5a459b1db3535f2b72fa921e8872202023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e73473044022065f45ba5998b59a27ffe1a7bed016af1f1f90d54b3aa8f7450aa5f56a25103bd02207f724703ad1edb96680b284b56d4ffcb88f7fb759eabbe08aa30f29b851383d2010103040100000001042200208c2353173743b595dfb4a07b72ba8e42e3797da74e87fe7d9d7497e3b2028903010547522103089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc21023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7352ae2206023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7310d90c6a4f000000800000008003000080220603089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc10d90c6a4f00000080000000800200008000220203a9a4c37f5996d3aa25dbac6b570af0650394492942460b354753ed9eeca5877110d90c6a4f000000800000008004000080002202027f6399757d2eff55a136ad02c684b1838b6556e5f1b6b34282a94b6b5005109610d90c6a4f00000080000000800500008000
** Base64 String:
cHNidP8BAJoCAAAAAljoeiG1ba8MI76OcHBFbDNvfLqlyHV5JPVFiHuyq911AAAAAAD/////g40EJ9DsZQpoqka7CwmK6kQiwHGyyng1Kgd5WdB86h0BAAAAAP////8CcKrwCAAAAAAWABTYXCtx0AYLCcmIauuBXlCZHdoSTQDh9QUAAAAAFgAUAK6pouXw+HaliN9VRuh0LR2HAI8AAAAAAAEAuwIAAAABqtc5MQGL0l+ErkALaISL4J23BurCrBgpi6vucatlb4sAAAAASEcwRAIgWPb8fGoz4bMVSNSByCbAFb0wE1qtQs1neQ2rZtKtJDsCIEoc7SYExnNbY5PltBaR3XiwDwxZQvufdRhW+qk4FX26Af7///8CgPD6AgAAAAAXqRQPuUY0IWlrgsgzryQceMF9295JNIfQ8gonAQAAABepFCnKdPigj4GZlCgYXJe12FLkBj9hh2UAAAAiAgLath/0mhTban0CsM0fu3j8SxgxK1tOVNrk26L7/vU210gwRQIhAPYQOLMI3B2oZaNIUnRvAVdyk0IIxtJEVDk82ZvfIhd3AiAFbmdaZ1ptCgK4WxTl4pB02KJam1dgvqKBb2YZEKAG6gEBAwQBAAAAAQRHUiEClYO/Oa4KYJdHrRma3dY0+mEIVZ1sXNObTCGD8auW4H8hAtq2H/SaFNtqfQKwzR+7ePxLGDErW05U2uTbovv+9TbXUq8iBgKVg785rgpgl0etGZrd1jT6YQhVnWxc05tMIYPxq5bgfxDZDGpPAAAAgAAAAIAAAACAIgYC2rYf9JoU22p9ArDNH7t4/EsYMStbTlTa5Nui+/71NtcQ2QxqTwAAAIAAAACAAQAAgAABASAAwusLAAAAABepFLf1+vQOPUClpFmx2zU18rcvqSHohyICAjrdkE89bc9Z3bkGsN7iNSm3/7ntUOXoYVGSaGAiHw5zRzBEAiBl9FulmYtZon/+GnvtAWrx8fkNVLOqj3RQql9WolEDvQIgf3JHA60e25ZoCyhLVtT/y4j3+3Weq74IqjDym4UTg9IBAQMEAQAAAAEEIgAgjCNTFzdDtZXftKB7crqOQuN5fadOh/59nXSX47ICiQMBBUdSIQMIncEMesbbVPkTKa9hczPbOIzq0MIx9yM3nRuZAwsC3CECOt2QTz1tz1nduQaw3uI1Kbf/ue1Q5ehhUZJoYCIfDnNSriIGAjrdkE89bc9Z3bkGsN7iNSm3/7ntUOXoYVGSaGAiHw5zENkMak8AAACAAAAAgAMAAIAiBgMIncEMesbbVPkTKa9hczPbOIzq0MIx9yM3nRuZAwsC3BDZDGpPAAAAgAAAAIACAACAACICA6mkw39ZltOqJdusa1cK8GUDlEkpQkYLNUdT7Z7spYdxENkMak8AAACAAAAAgAQAAIAAIgICf2OZdX0u/1WhNq0CxoSxg4tlVuXxtrNCgqlLa1AFEJYQ2QxqTwAAAIAAAACABQAAgAA=
* Case: redeemScript with witness UTXO does not match the scriptPubKey ** Bytes in Hex:
70736274ff01009a020000000258e87a21b56daf0c23be8e7070456c336f7cbaa5c8757924f545887bb2abdd750000000000ffffffff838d0427d0ec650a68aa46bb0b098aea4422c071b2ca78352a077959d07cea1d0100000000ffffffff0270aaf00800000000160014d85c2b71d0060b09c9886aeb815e50991dda124d00e1f5050000000016001400aea9a2e5f0f876a588df5546e8742d1d87008f00000000000100bb0200000001aad73931018bd25f84ae400b68848be09db706eac2ac18298babee71ab656f8b0000000048473044022058f6fc7c6a33e1b31548d481c826c015bd30135aad42cd67790dab66d2ad243b02204a1ced2604c6735b6393e5b41691dd78b00f0c5942fb9f751856faa938157dba01feffffff0280f0fa020000000017a9140fb9463421696b82c833af241c78c17ddbde493487d0f20a270100000017a91429ca74f8a08f81999428185c97b5d852e4063f618765000000220202dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d7483045022100f61038b308dc1da865a34852746f015772934208c6d24454393cd99bdf2217770220056e675a675a6d0a02b85b14e5e29074d8a25a9b5760bea2816f661910a006ea01010304010000000104475221029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f2102dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d752ae2206029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f10d90c6a4f000000800000008000000080220602dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d710d90c6a4f0000008000000080010000800001012000c2eb0b0000000017a914b7f5faf40e3d40a5a459b1db3535f2b72fa921e8872202023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e73473044022065f45ba5998b59a27ffe1a7bed016af1f1f90d54b3aa8f7450aa5f56a25103bd02207f724703ad1edb96680b284b56d4ffcb88f7fb759eabbe08aa30f29b851383d2010103040100000001042200208c2353173743b595dfb4a07b72ba8e42e3797da74e87fe7d9d7497e3b2028900010547522103089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc21023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7352ae2206023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7310d90c6a4f000000800000008003000080220603089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc10d90c6a4f00000080000000800200008000220203a9a4c37f5996d3aa25dbac6b570af0650394492942460b354753ed9eeca5877110d90c6a4f000000800000008004000080002202027f6399757d2eff55a136ad02c684b1838b6556e5f1b6b34282a94b6b5005109610d90c6a4f00000080000000800500008000
** Base64 String:
cHNidP8BAJoCAAAAAljoeiG1ba8MI76OcHBFbDNvfLqlyHV5JPVFiHuyq911AAAAAAD/////g40EJ9DsZQpoqka7CwmK6kQiwHGyyng1Kgd5WdB86h0BAAAAAP////8CcKrwCAAAAAAWABTYXCtx0AYLCcmIauuBXlCZHdoSTQDh9QUAAAAAFgAUAK6pouXw+HaliN9VRuh0LR2HAI8AAAAAAAEAuwIAAAABqtc5MQGL0l+ErkALaISL4J23BurCrBgpi6vucatlb4sAAAAASEcwRAIgWPb8fGoz4bMVSNSByCbAFb0wE1qtQs1neQ2rZtKtJDsCIEoc7SYExnNbY5PltBaR3XiwDwxZQvufdRhW+qk4FX26Af7///8CgPD6AgAAAAAXqRQPuUY0IWlrgsgzryQceMF9295JNIfQ8gonAQAAABepFCnKdPigj4GZlCgYXJe12FLkBj9hh2UAAAAiAgLath/0mhTban0CsM0fu3j8SxgxK1tOVNrk26L7/vU210gwRQIhAPYQOLMI3B2oZaNIUnRvAVdyk0IIxtJEVDk82ZvfIhd3AiAFbmdaZ1ptCgK4WxTl4pB02KJam1dgvqKBb2YZEKAG6gEBAwQBAAAAAQRHUiEClYO/Oa4KYJdHrRma3dY0+mEIVZ1sXNObTCGD8auW4H8hAtq2H/SaFNtqfQKwzR+7ePxLGDErW05U2uTbovv+9TbXUq4iBgKVg785rgpgl0etGZrd1jT6YQhVnWxc05tMIYPxq5bgfxDZDGpPAAAAgAAAAIAAAACAIgYC2rYf9JoU22p9ArDNH7t4/EsYMStbTlTa5Nui+/71NtcQ2QxqTwAAAIAAAACAAQAAgAABASAAwusLAAAAABepFLf1+vQOPUClpFmx2zU18rcvqSHohyICAjrdkE89bc9Z3bkGsN7iNSm3/7ntUOXoYVGSaGAiHw5zRzBEAiBl9FulmYtZon/+GnvtAWrx8fkNVLOqj3RQql9WolEDvQIgf3JHA60e25ZoCyhLVtT/y4j3+3Weq74IqjDym4UTg9IBAQMEAQAAAAEEIgAgjCNTFzdDtZXftKB7crqOQuN5fadOh/59nXSX47ICiQABBUdSIQMIncEMesbbVPkTKa9hczPbOIzq0MIx9yM3nRuZAwsC3CECOt2QTz1tz1nduQaw3uI1Kbf/ue1Q5ehhUZJoYCIfDnNSriIGAjrdkE89bc9Z3bkGsN7iNSm3/7ntUOXoYVGSaGAiHw5zENkMak8AAACAAAAAgAMAAIAiBgMIncEMesbbVPkTKa9hczPbOIzq0MIx9yM3nRuZAwsC3BDZDGpPAAAAgAAAAIACAACAACICA6mkw39ZltOqJdusa1cK8GUDlEkpQkYLNUdT7Z7spYdxENkMak8AAACAAAAAgAQAAIAAIgICf2OZdX0u/1WhNq0CxoSxg4tlVuXxtrNCgqlLa1AFEJYQ2QxqTwAAAIAAAACABQAAgAA=
* Case: witnessScript with witness UTXO does not match the redeemScript ** Bytes in Hex:
70736274ff01009a020000000258e87a21b56daf0c23be8e7070456c336f7cbaa5c8757924f545887bb2abdd750000000000ffffffff838d0427d0ec650a68aa46bb0b098aea4422c071b2ca78352a077959d07cea1d0100000000ffffffff0270aaf00800000000160014d85c2b71d0060b09c9886aeb815e50991dda124d00e1f5050000000016001400aea9a2e5f0f876a588df5546e8742d1d87008f00000000000100bb0200000001aad73931018bd25f84ae400b68848be09db706eac2ac18298babee71ab656f8b0000000048473044022058f6fc7c6a33e1b31548d481c826c015bd30135aad42cd67790dab66d2ad243b02204a1ced2604c6735b6393e5b41691dd78b00f0c5942fb9f751856faa938157dba01feffffff0280f0fa020000000017a9140fb9463421696b82c833af241c78c17ddbde493487d0f20a270100000017a91429ca74f8a08f81999428185c97b5d852e4063f618765000000220202dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d7483045022100f61038b308dc1da865a34852746f015772934208c6d24454393cd99bdf2217770220056e675a675a6d0a02b85b14e5e29074d8a25a9b5760bea2816f661910a006ea01010304010000000104475221029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f2102dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d752ae2206029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f10d90c6a4f000000800000008000000080220602dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d710d90c6a4f0000008000000080010000800001012000c2eb0b0000000017a914b7f5faf40e3d40a5a459b1db3535f2b72fa921e8872202023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e73473044022065f45ba5998b59a27ffe1a7bed016af1f1f90d54b3aa8f7450aa5f56a25103bd02207f724703ad1edb96680b284b56d4ffcb88f7fb759eabbe08aa30f29b851383d2010103040100000001042200208c2353173743b595dfb4a07b72ba8e42e3797da74e87fe7d9d7497e3b2028903010547522103089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc21023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7352ad2206023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7310d90c6a4f000000800000008003000080220603089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc10d90c6a4f00000080000000800200008000220203a9a4c37f5996d3aa25dbac6b570af0650394492942460b354753ed9eeca5877110d90c6a4f000000800000008004000080002202027f6399757d2eff55a136ad02c684b1838b6556e5f1b6b34282a94b6b5005109610d90c6a4f00000080000000800500008000
** Base64 String:
cHNidP8BAJoCAAAAAljoeiG1ba8MI76OcHBFbDNvfLqlyHV5JPVFiHuyq911AAAAAAD/////g40EJ9DsZQpoqka7CwmK6kQiwHGyyng1Kgd5WdB86h0BAAAAAP////8CcKrwCAAAAAAWABTYXCtx0AYLCcmIauuBXlCZHdoSTQDh9QUAAAAAFgAUAK6pouXw+HaliN9VRuh0LR2HAI8AAAAAAAEAuwIAAAABqtc5MQGL0l+ErkALaISL4J23BurCrBgpi6vucatlb4sAAAAASEcwRAIgWPb8fGoz4bMVSNSByCbAFb0wE1qtQs1neQ2rZtKtJDsCIEoc7SYExnNbY5PltBaR3XiwDwxZQvufdRhW+qk4FX26Af7///8CgPD6AgAAAAAXqRQPuUY0IWlrgsgzryQceMF9295JNIfQ8gonAQAAABepFCnKdPigj4GZlCgYXJe12FLkBj9hh2UAAAAiAgLath/0mhTban0CsM0fu3j8SxgxK1tOVNrk26L7/vU210gwRQIhAPYQOLMI3B2oZaNIUnRvAVdyk0IIxtJEVDk82ZvfIhd3AiAFbmdaZ1ptCgK4WxTl4pB02KJam1dgvqKBb2YZEKAG6gEBAwQBAAAAAQRHUiEClYO/Oa4KYJdHrRma3dY0+mEIVZ1sXNObTCGD8auW4H8hAtq2H/SaFNtqfQKwzR+7ePxLGDErW05U2uTbovv+9TbXUq4iBgKVg785rgpgl0etGZrd1jT6YQhVnWxc05tMIYPxq5bgfxDZDGpPAAAAgAAAAIAAAACAIgYC2rYf9JoU22p9ArDNH7t4/EsYMStbTlTa5Nui+/71NtcQ2QxqTwAAAIAAAACAAQAAgAABASAAwusLAAAAABepFLf1+vQOPUClpFmx2zU18rcvqSHohyICAjrdkE89bc9Z3bkGsN7iNSm3/7ntUOXoYVGSaGAiHw5zRzBEAiBl9FulmYtZon/+GnvtAWrx8fkNVLOqj3RQql9WolEDvQIgf3JHA60e25ZoCyhLVtT/y4j3+3Weq74IqjDym4UTg9IBAQMEAQAAAAEEIgAgjCNTFzdDtZXftKB7crqOQuN5fadOh/59nXSX47ICiQMBBUdSIQMIncEMesbbVPkTKa9hczPbOIzq0MIx9yM3nRuZAwsC3CECOt2QTz1tz1nduQaw3uI1Kbf/ue1Q5ehhUZJoYCIfDnNSrSIGAjrdkE89bc9Z3bkGsN7iNSm3/7ntUOXoYVGSaGAiHw5zENkMak8AAACAAAAAgAMAAIAiBgMIncEMesbbVPkTKa9hczPbOIzq0MIx9yM3nRuZAwsC3BDZDGpPAAAAgAAAAIACAACAACICA6mkw39ZltOqJdusa1cK8GUDlEkpQkYLNUdT7Z7spYdxENkMak8AAACAAAAAgAQAAIAAIgICf2OZdX0u/1WhNq0CxoSxg4tlVuXxtrNCgqlLa1AFEJYQ2QxqTwAAAIAAAACABQAAgAA=
The private keys in the tests below are derived from the following master private key: * Extended Private Key:
tprv8ZgxMBicQKsPd9TeAdPADNnSyH9SSUUbTVeFszDE23Ki6TBB5nCefAdHkK8Fm3qMQR6sHwA56zqRmKmxnHk37JkiFzvncDqoKmPWubu7hDF
** Seed:
cUkG8i1RFfWGWy5ziR11zJ5V4U4W3viSFCfyJmZnvQaUsd1xuF3T
A creator creating a PSBT for a transaction which creates the following outputs: * scriptPubKey: 0014d85c2b71d0060b09c9886aeb815e50991dda124d, Amount: 1.49990000 * scriptPubKey: 001400aea9a2e5f0f876a588df5546e8742d1d87008f, Amount: 1.00000000 and spends the following inputs: * TXID: 75ddabb27b8845f5247975c8a5ba7c6f336c4570708ebe230caf6db5217ae858, Index: 0 * TXID: 1dea7cd05979072a3578cab271c02244ea8a090bbb46aa680a65ecd027048d83, Index: 1 must create this PSBT: * Bytes in Hex:
70736274ff01009a020000000258e87a21b56daf0c23be8e7070456c336f7cbaa5c8757924f545887bb2abdd750000000000ffffffff838d0427d0ec650a68aa46bb0b098aea4422c071b2ca78352a077959d07cea1d0100000000ffffffff0270aaf00800000000160014d85c2b71d0060b09c9886aeb815e50991dda124d00e1f5050000000016001400aea9a2e5f0f876a588df5546e8742d1d87008f000000000000000000
* Base64 String:
cHNidP8BAJoCAAAAAljoeiG1ba8MI76OcHBFbDNvfLqlyHV5JPVFiHuyq911AAAAAAD/////g40EJ9DsZQpoqka7CwmK6kQiwHGyyng1Kgd5WdB86h0BAAAAAP////8CcKrwCAAAAAAWABTYXCtx0AYLCcmIauuBXlCZHdoSTQDh9QUAAAAAFgAUAK6pouXw+HaliN9VRuh0LR2HAI8AAAAAAAAAAAA=
Given the above PSBT, an updater with only the following: * Redeem Scripts: ** 5221029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f2102dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d752ae ** 00208c2353173743b595dfb4a07b72ba8e42e3797da74e87fe7d9d7497e3b2028903 * Witness Scripts: ** 522103089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc21023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7352ae * Previous Transactions: **
0200000000010158e87a21b56daf0c23be8e7070456c336f7cbaa5c8757924f545887bb2abdd7501000000171600145f275f436b09a8cc9a2eb2a2f528485c68a56323feffffff02d8231f1b0100000017a914aed962d6654f9a2b36608eb9d64d2b260db4f1118700c2eb0b0000000017a914b7f5faf40e3d40a5a459b1db3535f2b72fa921e88702483045022100a22edcc6e5bc511af4cc4ae0de0fcd75c7e04d8c1c3a8aa9d820ed4b967384ec02200642963597b9b1bc22c75e9f3e117284a962188bf5e8a74c895089046a20ad770121035509a48eb623e10aace8bfd0212fdb8a8e5af3c94b0b133b95e114cab89e4f7965000000
**
0200000001aad73931018bd25f84ae400b68848be09db706eac2ac18298babee71ab656f8b0000000048473044022058f6fc7c6a33e1b31548d481c826c015bd30135aad42cd67790dab66d2ad243b02204a1ced2604c6735b6393e5b41691dd78b00f0c5942fb9f751856faa938157dba01feffffff0280f0fa020000000017a9140fb9463421696b82c833af241c78c17ddbde493487d0f20a270100000017a91429ca74f8a08f81999428185c97b5d852e4063f618765000000
* Public Keys ** Key: 029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f, Derivation Path: m/0'/0'/0' ** Key: 02dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d7, Derivation Path: m/0'/0'/1' ** Key: 03089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc, Derivation Path: m/0'/0'/2' ** Key: 023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e73, Derivation Path: m/0'/0'/3' ** Key: 03a9a4c37f5996d3aa25dbac6b570af0650394492942460b354753ed9eeca58771, Derivation Path: m/0'/0'/4' ** Key: 027f6399757d2eff55a136ad02c684b1838b6556e5f1b6b34282a94b6b50051096, Derivation Path: m/0'/0'/5' Must create this PSBT: * Bytes in Hex:
70736274ff01009a020000000258e87a21b56daf0c23be8e7070456c336f7cbaa5c8757924f545887bb2abdd750000000000ffffffff838d0427d0ec650a68aa46bb0b098aea4422c071b2ca78352a077959d07cea1d0100000000ffffffff0270aaf00800000000160014d85c2b71d0060b09c9886aeb815e50991dda124d00e1f5050000000016001400aea9a2e5f0f876a588df5546e8742d1d87008f00000000000100bb0200000001aad73931018bd25f84ae400b68848be09db706eac2ac18298babee71ab656f8b0000000048473044022058f6fc7c6a33e1b31548d481c826c015bd30135aad42cd67790dab66d2ad243b02204a1ced2604c6735b6393e5b41691dd78b00f0c5942fb9f751856faa938157dba01feffffff0280f0fa020000000017a9140fb9463421696b82c833af241c78c17ddbde493487d0f20a270100000017a91429ca74f8a08f81999428185c97b5d852e4063f6187650000000104475221029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f2102dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d752ae2206029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f10d90c6a4f000000800000008000000080220602dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d710d90c6a4f0000008000000080010000800001012000c2eb0b0000000017a914b7f5faf40e3d40a5a459b1db3535f2b72fa921e88701042200208c2353173743b595dfb4a07b72ba8e42e3797da74e87fe7d9d7497e3b2028903010547522103089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc21023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7352ae2206023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7310d90c6a4f000000800000008003000080220603089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc10d90c6a4f00000080000000800200008000220203a9a4c37f5996d3aa25dbac6b570af0650394492942460b354753ed9eeca5877110d90c6a4f000000800000008004000080002202027f6399757d2eff55a136ad02c684b1838b6556e5f1b6b34282a94b6b5005109610d90c6a4f00000080000000800500008000
* Base64 String:
cHNidP8BAJoCAAAAAljoeiG1ba8MI76OcHBFbDNvfLqlyHV5JPVFiHuyq911AAAAAAD/////g40EJ9DsZQpoqka7CwmK6kQiwHGyyng1Kgd5WdB86h0BAAAAAP////8CcKrwCAAAAAAWABTYXCtx0AYLCcmIauuBXlCZHdoSTQDh9QUAAAAAFgAUAK6pouXw+HaliN9VRuh0LR2HAI8AAAAAAAEAuwIAAAABqtc5MQGL0l+ErkALaISL4J23BurCrBgpi6vucatlb4sAAAAASEcwRAIgWPb8fGoz4bMVSNSByCbAFb0wE1qtQs1neQ2rZtKtJDsCIEoc7SYExnNbY5PltBaR3XiwDwxZQvufdRhW+qk4FX26Af7///8CgPD6AgAAAAAXqRQPuUY0IWlrgsgzryQceMF9295JNIfQ8gonAQAAABepFCnKdPigj4GZlCgYXJe12FLkBj9hh2UAAAABBEdSIQKVg785rgpgl0etGZrd1jT6YQhVnWxc05tMIYPxq5bgfyEC2rYf9JoU22p9ArDNH7t4/EsYMStbTlTa5Nui+/71NtdSriIGApWDvzmuCmCXR60Zmt3WNPphCFWdbFzTm0whg/GrluB/ENkMak8AAACAAAAAgAAAAIAiBgLath/0mhTban0CsM0fu3j8SxgxK1tOVNrk26L7/vU21xDZDGpPAAAAgAAAAIABAACAAAEBIADC6wsAAAAAF6kUt/X69A49QKWkWbHbNTXyty+pIeiHAQQiACCMI1MXN0O1ld+0oHtyuo5C43l9p06H/n2ddJfjsgKJAwEFR1IhAwidwQx6xttU+RMpr2FzM9s4jOrQwjH3IzedG5kDCwLcIQI63ZBPPW3PWd25BrDe4jUpt/+57VDl6GFRkmhgIh8Oc1KuIgYCOt2QTz1tz1nduQaw3uI1Kbf/ue1Q5ehhUZJoYCIfDnMQ2QxqTwAAAIAAAACAAwAAgCIGAwidwQx6xttU+RMpr2FzM9s4jOrQwjH3IzedG5kDCwLcENkMak8AAACAAAAAgAIAAIAAIgIDqaTDf1mW06ol26xrVwrwZQOUSSlCRgs1R1Ptnuylh3EQ2QxqTwAAAIAAAACABAAAgAAiAgJ/Y5l1fS7/VaE2rQLGhLGDi2VW5fG2s0KCqUtrUAUQlhDZDGpPAAAAgAAAAIAFAACAAA==
An updater which adds SIGHASH_ALL to the above PSBT must create this PSBT: * Bytes in Hex:
70736274ff01009a020000000258e87a21b56daf0c23be8e7070456c336f7cbaa5c8757924f545887bb2abdd750000000000ffffffff838d0427d0ec650a68aa46bb0b098aea4422c071b2ca78352a077959d07cea1d0100000000ffffffff0270aaf00800000000160014d85c2b71d0060b09c9886aeb815e50991dda124d00e1f5050000000016001400aea9a2e5f0f876a588df5546e8742d1d87008f00000000000100bb0200000001aad73931018bd25f84ae400b68848be09db706eac2ac18298babee71ab656f8b0000000048473044022058f6fc7c6a33e1b31548d481c826c015bd30135aad42cd67790dab66d2ad243b02204a1ced2604c6735b6393e5b41691dd78b00f0c5942fb9f751856faa938157dba01feffffff0280f0fa020000000017a9140fb9463421696b82c833af241c78c17ddbde493487d0f20a270100000017a91429ca74f8a08f81999428185c97b5d852e4063f618765000000010304010000000104475221029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f2102dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d752ae2206029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f10d90c6a4f000000800000008000000080220602dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d710d90c6a4f0000008000000080010000800001012000c2eb0b0000000017a914b7f5faf40e3d40a5a459b1db3535f2b72fa921e8870103040100000001042200208c2353173743b595dfb4a07b72ba8e42e3797da74e87fe7d9d7497e3b2028903010547522103089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc21023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7352ae2206023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7310d90c6a4f000000800000008003000080220603089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc10d90c6a4f00000080000000800200008000220203a9a4c37f5996d3aa25dbac6b570af0650394492942460b354753ed9eeca5877110d90c6a4f000000800000008004000080002202027f6399757d2eff55a136ad02c684b1838b6556e5f1b6b34282a94b6b5005109610d90c6a4f00000080000000800500008000
* Base64 String:
cHNidP8BAJoCAAAAAljoeiG1ba8MI76OcHBFbDNvfLqlyHV5JPVFiHuyq911AAAAAAD/////g40EJ9DsZQpoqka7CwmK6kQiwHGyyng1Kgd5WdB86h0BAAAAAP////8CcKrwCAAAAAAWABTYXCtx0AYLCcmIauuBXlCZHdoSTQDh9QUAAAAAFgAUAK6pouXw+HaliN9VRuh0LR2HAI8AAAAAAAEAuwIAAAABqtc5MQGL0l+ErkALaISL4J23BurCrBgpi6vucatlb4sAAAAASEcwRAIgWPb8fGoz4bMVSNSByCbAFb0wE1qtQs1neQ2rZtKtJDsCIEoc7SYExnNbY5PltBaR3XiwDwxZQvufdRhW+qk4FX26Af7///8CgPD6AgAAAAAXqRQPuUY0IWlrgsgzryQceMF9295JNIfQ8gonAQAAABepFCnKdPigj4GZlCgYXJe12FLkBj9hh2UAAAABAwQBAAAAAQRHUiEClYO/Oa4KYJdHrRma3dY0+mEIVZ1sXNObTCGD8auW4H8hAtq2H/SaFNtqfQKwzR+7ePxLGDErW05U2uTbovv+9TbXUq4iBgKVg785rgpgl0etGZrd1jT6YQhVnWxc05tMIYPxq5bgfxDZDGpPAAAAgAAAAIAAAACAIgYC2rYf9JoU22p9ArDNH7t4/EsYMStbTlTa5Nui+/71NtcQ2QxqTwAAAIAAAACAAQAAgAABASAAwusLAAAAABepFLf1+vQOPUClpFmx2zU18rcvqSHohwEDBAEAAAABBCIAIIwjUxc3Q7WV37Sge3K6jkLjeX2nTof+fZ10l+OyAokDAQVHUiEDCJ3BDHrG21T5EymvYXMz2ziM6tDCMfcjN50bmQMLAtwhAjrdkE89bc9Z3bkGsN7iNSm3/7ntUOXoYVGSaGAiHw5zUq4iBgI63ZBPPW3PWd25BrDe4jUpt/+57VDl6GFRkmhgIh8OcxDZDGpPAAAAgAAAAIADAACAIgYDCJ3BDHrG21T5EymvYXMz2ziM6tDCMfcjN50bmQMLAtwQ2QxqTwAAAIAAAACAAgAAgAAiAgOppMN/WZbTqiXbrGtXCvBlA5RJKUJGCzVHU+2e7KWHcRDZDGpPAAAAgAAAAIAEAACAACICAn9jmXV9Lv9VoTatAsaEsYOLZVbl8bazQoKpS2tQBRCWENkMak8AAACAAAAAgAUAAIAA
Given the above updated PSBT, a signer that supports SIGHASH_ALL for P2PKH and P2WPKH spends and uses RFC6979 for nonce generation and has the following keys: * cP53pDbR5WtAD8dYAW9hhTjuvvTVaEiQBdrz9XPrgLBeRFiyCbQr (m/0'/0'/0') * cR6SXDoyfQrcp4piaiHE97Rsgta9mNhGTen9XeonVgwsh4iSgw6d (m/0'/0'/2') must create this PSBT: * Bytes in Hex:
70736274ff01009a020000000258e87a21b56daf0c23be8e7070456c336f7cbaa5c8757924f545887bb2abdd750000000000ffffffff838d0427d0ec650a68aa46bb0b098aea4422c071b2ca78352a077959d07cea1d0100000000ffffffff0270aaf00800000000160014d85c2b71d0060b09c9886aeb815e50991dda124d00e1f5050000000016001400aea9a2e5f0f876a588df5546e8742d1d87008f00000000000100bb0200000001aad73931018bd25f84ae400b68848be09db706eac2ac18298babee71ab656f8b0000000048473044022058f6fc7c6a33e1b31548d481c826c015bd30135aad42cd67790dab66d2ad243b02204a1ced2604c6735b6393e5b41691dd78b00f0c5942fb9f751856faa938157dba01feffffff0280f0fa020000000017a9140fb9463421696b82c833af241c78c17ddbde493487d0f20a270100000017a91429ca74f8a08f81999428185c97b5d852e4063f6187650000002202029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f473044022074018ad4180097b873323c0015720b3684cc8123891048e7dbcd9b55ad679c99022073d369b740e3eb53dcefa33823c8070514ca55a7dd9544f157c167913261118c01010304010000000104475221029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f2102dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d752ae2206029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f10d90c6a4f000000800000008000000080220602dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d710d90c6a4f0000008000000080010000800001012000c2eb0b0000000017a914b7f5faf40e3d40a5a459b1db3535f2b72fa921e887220203089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc473044022062eb7a556107a7c73f45ac4ab5a1dddf6f7075fb1275969a7f383efff784bcb202200c05dbb7470dbf2f08557dd356c7325c1ed30913e996cd3840945db12228da5f010103040100000001042200208c2353173743b595dfb4a07b72ba8e42e3797da74e87fe7d9d7497e3b2028903010547522103089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc21023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7352ae2206023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7310d90c6a4f000000800000008003000080220603089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc10d90c6a4f00000080000000800200008000220203a9a4c37f5996d3aa25dbac6b570af0650394492942460b354753ed9eeca5877110d90c6a4f000000800000008004000080002202027f6399757d2eff55a136ad02c684b1838b6556e5f1b6b34282a94b6b5005109610d90c6a4f00000080000000800500008000
* Base64 String:
cHNidP8BAJoCAAAAAljoeiG1ba8MI76OcHBFbDNvfLqlyHV5JPVFiHuyq911AAAAAAD/////g40EJ9DsZQpoqka7CwmK6kQiwHGyyng1Kgd5WdB86h0BAAAAAP////8CcKrwCAAAAAAWABTYXCtx0AYLCcmIauuBXlCZHdoSTQDh9QUAAAAAFgAUAK6pouXw+HaliN9VRuh0LR2HAI8AAAAAAAEAuwIAAAABqtc5MQGL0l+ErkALaISL4J23BurCrBgpi6vucatlb4sAAAAASEcwRAIgWPb8fGoz4bMVSNSByCbAFb0wE1qtQs1neQ2rZtKtJDsCIEoc7SYExnNbY5PltBaR3XiwDwxZQvufdRhW+qk4FX26Af7///8CgPD6AgAAAAAXqRQPuUY0IWlrgsgzryQceMF9295JNIfQ8gonAQAAABepFCnKdPigj4GZlCgYXJe12FLkBj9hh2UAAAAiAgKVg785rgpgl0etGZrd1jT6YQhVnWxc05tMIYPxq5bgf0cwRAIgdAGK1BgAl7hzMjwAFXILNoTMgSOJEEjn282bVa1nnJkCIHPTabdA4+tT3O+jOCPIBwUUylWn3ZVE8VfBZ5EyYRGMAQEDBAEAAAABBEdSIQKVg785rgpgl0etGZrd1jT6YQhVnWxc05tMIYPxq5bgfyEC2rYf9JoU22p9ArDNH7t4/EsYMStbTlTa5Nui+/71NtdSriIGApWDvzmuCmCXR60Zmt3WNPphCFWdbFzTm0whg/GrluB/ENkMak8AAACAAAAAgAAAAIAiBgLath/0mhTban0CsM0fu3j8SxgxK1tOVNrk26L7/vU21xDZDGpPAAAAgAAAAIABAACAAAEBIADC6wsAAAAAF6kUt/X69A49QKWkWbHbNTXyty+pIeiHIgIDCJ3BDHrG21T5EymvYXMz2ziM6tDCMfcjN50bmQMLAtxHMEQCIGLrelVhB6fHP0WsSrWh3d9vcHX7EnWWmn84Pv/3hLyyAiAMBdu3Rw2/LwhVfdNWxzJcHtMJE+mWzThAlF2xIijaXwEBAwQBAAAAAQQiACCMI1MXN0O1ld+0oHtyuo5C43l9p06H/n2ddJfjsgKJAwEFR1IhAwidwQx6xttU+RMpr2FzM9s4jOrQwjH3IzedG5kDCwLcIQI63ZBPPW3PWd25BrDe4jUpt/+57VDl6GFRkmhgIh8Oc1KuIgYCOt2QTz1tz1nduQaw3uI1Kbf/ue1Q5ehhUZJoYCIfDnMQ2QxqTwAAAIAAAACAAwAAgCIGAwidwQx6xttU+RMpr2FzM9s4jOrQwjH3IzedG5kDCwLcENkMak8AAACAAAAAgAIAAIAAIgIDqaTDf1mW06ol26xrVwrwZQOUSSlCRgs1R1Ptnuylh3EQ2QxqTwAAAIAAAACABAAAgAAiAgJ/Y5l1fS7/VaE2rQLGhLGDi2VW5fG2s0KCqUtrUAUQlhDZDGpPAAAAgAAAAIAFAACAAA==
Given the above updated PSBT, a signer with the following keys: * cT7J9YpCwY3AVRFSjN6ukeEeWY6mhpbJPxRaDaP5QTdygQRxP9Au (m/0'/0'/1') * cNBc3SWUip9PPm1GjRoLEJT6T41iNzCYtD7qro84FMnM5zEqeJsE (m/0'/0'/3') must create this PSBT: * Bytes in Hex:
70736274ff01009a020000000258e87a21b56daf0c23be8e7070456c336f7cbaa5c8757924f545887bb2abdd750000000000ffffffff838d0427d0ec650a68aa46bb0b098aea4422c071b2ca78352a077959d07cea1d0100000000ffffffff0270aaf00800000000160014d85c2b71d0060b09c9886aeb815e50991dda124d00e1f5050000000016001400aea9a2e5f0f876a588df5546e8742d1d87008f00000000000100bb0200000001aad73931018bd25f84ae400b68848be09db706eac2ac18298babee71ab656f8b0000000048473044022058f6fc7c6a33e1b31548d481c826c015bd30135aad42cd67790dab66d2ad243b02204a1ced2604c6735b6393e5b41691dd78b00f0c5942fb9f751856faa938157dba01feffffff0280f0fa020000000017a9140fb9463421696b82c833af241c78c17ddbde493487d0f20a270100000017a91429ca74f8a08f81999428185c97b5d852e4063f618765000000220202dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d7483045022100f61038b308dc1da865a34852746f015772934208c6d24454393cd99bdf2217770220056e675a675a6d0a02b85b14e5e29074d8a25a9b5760bea2816f661910a006ea01010304010000000104475221029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f2102dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d752ae2206029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f10d90c6a4f000000800000008000000080220602dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d710d90c6a4f0000008000000080010000800001012000c2eb0b0000000017a914b7f5faf40e3d40a5a459b1db3535f2b72fa921e8872202023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e73473044022065f45ba5998b59a27ffe1a7bed016af1f1f90d54b3aa8f7450aa5f56a25103bd02207f724703ad1edb96680b284b56d4ffcb88f7fb759eabbe08aa30f29b851383d2010103040100000001042200208c2353173743b595dfb4a07b72ba8e42e3797da74e87fe7d9d7497e3b2028903010547522103089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc21023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7352ae2206023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7310d90c6a4f000000800000008003000080220603089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc10d90c6a4f00000080000000800200008000220203a9a4c37f5996d3aa25dbac6b570af0650394492942460b354753ed9eeca5877110d90c6a4f000000800000008004000080002202027f6399757d2eff55a136ad02c684b1838b6556e5f1b6b34282a94b6b5005109610d90c6a4f00000080000000800500008000
* Base64 String:
cHNidP8BAJoCAAAAAljoeiG1ba8MI76OcHBFbDNvfLqlyHV5JPVFiHuyq911AAAAAAD/////g40EJ9DsZQpoqka7CwmK6kQiwHGyyng1Kgd5WdB86h0BAAAAAP////8CcKrwCAAAAAAWABTYXCtx0AYLCcmIauuBXlCZHdoSTQDh9QUAAAAAFgAUAK6pouXw+HaliN9VRuh0LR2HAI8AAAAAAAEAuwIAAAABqtc5MQGL0l+ErkALaISL4J23BurCrBgpi6vucatlb4sAAAAASEcwRAIgWPb8fGoz4bMVSNSByCbAFb0wE1qtQs1neQ2rZtKtJDsCIEoc7SYExnNbY5PltBaR3XiwDwxZQvufdRhW+qk4FX26Af7///8CgPD6AgAAAAAXqRQPuUY0IWlrgsgzryQceMF9295JNIfQ8gonAQAAABepFCnKdPigj4GZlCgYXJe12FLkBj9hh2UAAAAiAgLath/0mhTban0CsM0fu3j8SxgxK1tOVNrk26L7/vU210gwRQIhAPYQOLMI3B2oZaNIUnRvAVdyk0IIxtJEVDk82ZvfIhd3AiAFbmdaZ1ptCgK4WxTl4pB02KJam1dgvqKBb2YZEKAG6gEBAwQBAAAAAQRHUiEClYO/Oa4KYJdHrRma3dY0+mEIVZ1sXNObTCGD8auW4H8hAtq2H/SaFNtqfQKwzR+7ePxLGDErW05U2uTbovv+9TbXUq4iBgKVg785rgpgl0etGZrd1jT6YQhVnWxc05tMIYPxq5bgfxDZDGpPAAAAgAAAAIAAAACAIgYC2rYf9JoU22p9ArDNH7t4/EsYMStbTlTa5Nui+/71NtcQ2QxqTwAAAIAAAACAAQAAgAABASAAwusLAAAAABepFLf1+vQOPUClpFmx2zU18rcvqSHohyICAjrdkE89bc9Z3bkGsN7iNSm3/7ntUOXoYVGSaGAiHw5zRzBEAiBl9FulmYtZon/+GnvtAWrx8fkNVLOqj3RQql9WolEDvQIgf3JHA60e25ZoCyhLVtT/y4j3+3Weq74IqjDym4UTg9IBAQMEAQAAAAEEIgAgjCNTFzdDtZXftKB7crqOQuN5fadOh/59nXSX47ICiQMBBUdSIQMIncEMesbbVPkTKa9hczPbOIzq0MIx9yM3nRuZAwsC3CECOt2QTz1tz1nduQaw3uI1Kbf/ue1Q5ehhUZJoYCIfDnNSriIGAjrdkE89bc9Z3bkGsN7iNSm3/7ntUOXoYVGSaGAiHw5zENkMak8AAACAAAAAgAMAAIAiBgMIncEMesbbVPkTKa9hczPbOIzq0MIx9yM3nRuZAwsC3BDZDGpPAAAAgAAAAIACAACAACICA6mkw39ZltOqJdusa1cK8GUDlEkpQkYLNUdT7Z7spYdxENkMak8AAACAAAAAgAQAAIAAIgICf2OZdX0u/1WhNq0CxoSxg4tlVuXxtrNCgqlLa1AFEJYQ2QxqTwAAAIAAAACABQAAgAA=
Given both of the above PSBTs, a combiner must create this PSBT: * Bytes in Hex:
70736274ff01009a020000000258e87a21b56daf0c23be8e7070456c336f7cbaa5c8757924f545887bb2abdd750000000000ffffffff838d0427d0ec650a68aa46bb0b098aea4422c071b2ca78352a077959d07cea1d0100000000ffffffff0270aaf00800000000160014d85c2b71d0060b09c9886aeb815e50991dda124d00e1f5050000000016001400aea9a2e5f0f876a588df5546e8742d1d87008f00000000000100bb0200000001aad73931018bd25f84ae400b68848be09db706eac2ac18298babee71ab656f8b0000000048473044022058f6fc7c6a33e1b31548d481c826c015bd30135aad42cd67790dab66d2ad243b02204a1ced2604c6735b6393e5b41691dd78b00f0c5942fb9f751856faa938157dba01feffffff0280f0fa020000000017a9140fb9463421696b82c833af241c78c17ddbde493487d0f20a270100000017a91429ca74f8a08f81999428185c97b5d852e4063f6187650000002202029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f473044022074018ad4180097b873323c0015720b3684cc8123891048e7dbcd9b55ad679c99022073d369b740e3eb53dcefa33823c8070514ca55a7dd9544f157c167913261118c01220202dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d7483045022100f61038b308dc1da865a34852746f015772934208c6d24454393cd99bdf2217770220056e675a675a6d0a02b85b14e5e29074d8a25a9b5760bea2816f661910a006ea01010304010000000104475221029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f2102dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d752ae2206029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f10d90c6a4f000000800000008000000080220602dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d710d90c6a4f0000008000000080010000800001012000c2eb0b0000000017a914b7f5faf40e3d40a5a459b1db3535f2b72fa921e887220203089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc473044022062eb7a556107a7c73f45ac4ab5a1dddf6f7075fb1275969a7f383efff784bcb202200c05dbb7470dbf2f08557dd356c7325c1ed30913e996cd3840945db12228da5f012202023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e73473044022065f45ba5998b59a27ffe1a7bed016af1f1f90d54b3aa8f7450aa5f56a25103bd02207f724703ad1edb96680b284b56d4ffcb88f7fb759eabbe08aa30f29b851383d2010103040100000001042200208c2353173743b595dfb4a07b72ba8e42e3797da74e87fe7d9d7497e3b2028903010547522103089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc21023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7352ae2206023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7310d90c6a4f000000800000008003000080220603089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc10d90c6a4f00000080000000800200008000220203a9a4c37f5996d3aa25dbac6b570af0650394492942460b354753ed9eeca5877110d90c6a4f000000800000008004000080002202027f6399757d2eff55a136ad02c684b1838b6556e5f1b6b34282a94b6b5005109610d90c6a4f00000080000000800500008000
* Base64 String:
cHNidP8BAJoCAAAAAljoeiG1ba8MI76OcHBFbDNvfLqlyHV5JPVFiHuyq911AAAAAAD/////g40EJ9DsZQpoqka7CwmK6kQiwHGyyng1Kgd5WdB86h0BAAAAAP////8CcKrwCAAAAAAWABTYXCtx0AYLCcmIauuBXlCZHdoSTQDh9QUAAAAAFgAUAK6pouXw+HaliN9VRuh0LR2HAI8AAAAAAAEAuwIAAAABqtc5MQGL0l+ErkALaISL4J23BurCrBgpi6vucatlb4sAAAAASEcwRAIgWPb8fGoz4bMVSNSByCbAFb0wE1qtQs1neQ2rZtKtJDsCIEoc7SYExnNbY5PltBaR3XiwDwxZQvufdRhW+qk4FX26Af7///8CgPD6AgAAAAAXqRQPuUY0IWlrgsgzryQceMF9295JNIfQ8gonAQAAABepFCnKdPigj4GZlCgYXJe12FLkBj9hh2UAAAAiAgKVg785rgpgl0etGZrd1jT6YQhVnWxc05tMIYPxq5bgf0cwRAIgdAGK1BgAl7hzMjwAFXILNoTMgSOJEEjn282bVa1nnJkCIHPTabdA4+tT3O+jOCPIBwUUylWn3ZVE8VfBZ5EyYRGMASICAtq2H/SaFNtqfQKwzR+7ePxLGDErW05U2uTbovv+9TbXSDBFAiEA9hA4swjcHahlo0hSdG8BV3KTQgjG0kRUOTzZm98iF3cCIAVuZ1pnWm0KArhbFOXikHTYolqbV2C+ooFvZhkQoAbqAQEDBAEAAAABBEdSIQKVg785rgpgl0etGZrd1jT6YQhVnWxc05tMIYPxq5bgfyEC2rYf9JoU22p9ArDNH7t4/EsYMStbTlTa5Nui+/71NtdSriIGApWDvzmuCmCXR60Zmt3WNPphCFWdbFzTm0whg/GrluB/ENkMak8AAACAAAAAgAAAAIAiBgLath/0mhTban0CsM0fu3j8SxgxK1tOVNrk26L7/vU21xDZDGpPAAAAgAAAAIABAACAAAEBIADC6wsAAAAAF6kUt/X69A49QKWkWbHbNTXyty+pIeiHIgIDCJ3BDHrG21T5EymvYXMz2ziM6tDCMfcjN50bmQMLAtxHMEQCIGLrelVhB6fHP0WsSrWh3d9vcHX7EnWWmn84Pv/3hLyyAiAMBdu3Rw2/LwhVfdNWxzJcHtMJE+mWzThAlF2xIijaXwEiAgI63ZBPPW3PWd25BrDe4jUpt/+57VDl6GFRkmhgIh8Oc0cwRAIgZfRbpZmLWaJ//hp77QFq8fH5DVSzqo90UKpfVqJRA70CIH9yRwOtHtuWaAsoS1bU/8uI9/t1nqu+CKow8puFE4PSAQEDBAEAAAABBCIAIIwjUxc3Q7WV37Sge3K6jkLjeX2nTof+fZ10l+OyAokDAQVHUiEDCJ3BDHrG21T5EymvYXMz2ziM6tDCMfcjN50bmQMLAtwhAjrdkE89bc9Z3bkGsN7iNSm3/7ntUOXoYVGSaGAiHw5zUq4iBgI63ZBPPW3PWd25BrDe4jUpt/+57VDl6GFRkmhgIh8OcxDZDGpPAAAAgAAAAIADAACAIgYDCJ3BDHrG21T5EymvYXMz2ziM6tDCMfcjN50bmQMLAtwQ2QxqTwAAAIAAAACAAgAAgAAiAgOppMN/WZbTqiXbrGtXCvBlA5RJKUJGCzVHU+2e7KWHcRDZDGpPAAAAgAAAAIAEAACAACICAn9jmXV9Lv9VoTatAsaEsYOLZVbl8bazQoKpS2tQBRCWENkMak8AAACAAAAAgAUAAIAA
Given the above PSBT, an input finalizer must create this PSBT: * Bytes in Hex:
70736274ff01009a020000000258e87a21b56daf0c23be8e7070456c336f7cbaa5c8757924f545887bb2abdd750000000000ffffffff838d0427d0ec650a68aa46bb0b098aea4422c071b2ca78352a077959d07cea1d0100000000ffffffff0270aaf00800000000160014d85c2b71d0060b09c9886aeb815e50991dda124d00e1f5050000000016001400aea9a2e5f0f876a588df5546e8742d1d87008f00000000000100bb0200000001aad73931018bd25f84ae400b68848be09db706eac2ac18298babee71ab656f8b0000000048473044022058f6fc7c6a33e1b31548d481c826c015bd30135aad42cd67790dab66d2ad243b02204a1ced2604c6735b6393e5b41691dd78b00f0c5942fb9f751856faa938157dba01feffffff0280f0fa020000000017a9140fb9463421696b82c833af241c78c17ddbde493487d0f20a270100000017a91429ca74f8a08f81999428185c97b5d852e4063f6187650000000107da00473044022074018ad4180097b873323c0015720b3684cc8123891048e7dbcd9b55ad679c99022073d369b740e3eb53dcefa33823c8070514ca55a7dd9544f157c167913261118c01483045022100f61038b308dc1da865a34852746f015772934208c6d24454393cd99bdf2217770220056e675a675a6d0a02b85b14e5e29074d8a25a9b5760bea2816f661910a006ea01475221029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f2102dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d752ae0001012000c2eb0b0000000017a914b7f5faf40e3d40a5a459b1db3535f2b72fa921e8870107232200208c2353173743b595dfb4a07b72ba8e42e3797da74e87fe7d9d7497e3b20289030108da0400473044022062eb7a556107a7c73f45ac4ab5a1dddf6f7075fb1275969a7f383efff784bcb202200c05dbb7470dbf2f08557dd356c7325c1ed30913e996cd3840945db12228da5f01473044022065f45ba5998b59a27ffe1a7bed016af1f1f90d54b3aa8f7450aa5f56a25103bd02207f724703ad1edb96680b284b56d4ffcb88f7fb759eabbe08aa30f29b851383d20147522103089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc21023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7352ae00220203a9a4c37f5996d3aa25dbac6b570af0650394492942460b354753ed9eeca5877110d90c6a4f000000800000008004000080002202027f6399757d2eff55a136ad02c684b1838b6556e5f1b6b34282a94b6b5005109610d90c6a4f00000080000000800500008000
* Base64 String:
cHNidP8BAJoCAAAAAljoeiG1ba8MI76OcHBFbDNvfLqlyHV5JPVFiHuyq911AAAAAAD/////g40EJ9DsZQpoqka7CwmK6kQiwHGyyng1Kgd5WdB86h0BAAAAAP////8CcKrwCAAAAAAWABTYXCtx0AYLCcmIauuBXlCZHdoSTQDh9QUAAAAAFgAUAK6pouXw+HaliN9VRuh0LR2HAI8AAAAAAAEAuwIAAAABqtc5MQGL0l+ErkALaISL4J23BurCrBgpi6vucatlb4sAAAAASEcwRAIgWPb8fGoz4bMVSNSByCbAFb0wE1qtQs1neQ2rZtKtJDsCIEoc7SYExnNbY5PltBaR3XiwDwxZQvufdRhW+qk4FX26Af7///8CgPD6AgAAAAAXqRQPuUY0IWlrgsgzryQceMF9295JNIfQ8gonAQAAABepFCnKdPigj4GZlCgYXJe12FLkBj9hh2UAAAABB9oARzBEAiB0AYrUGACXuHMyPAAVcgs2hMyBI4kQSOfbzZtVrWecmQIgc9Npt0Dj61Pc76M4I8gHBRTKVafdlUTxV8FnkTJhEYwBSDBFAiEA9hA4swjcHahlo0hSdG8BV3KTQgjG0kRUOTzZm98iF3cCIAVuZ1pnWm0KArhbFOXikHTYolqbV2C+ooFvZhkQoAbqAUdSIQKVg785rgpgl0etGZrd1jT6YQhVnWxc05tMIYPxq5bgfyEC2rYf9JoU22p9ArDNH7t4/EsYMStbTlTa5Nui+/71NtdSrgABASAAwusLAAAAABepFLf1+vQOPUClpFmx2zU18rcvqSHohwEHIyIAIIwjUxc3Q7WV37Sge3K6jkLjeX2nTof+fZ10l+OyAokDAQjaBABHMEQCIGLrelVhB6fHP0WsSrWh3d9vcHX7EnWWmn84Pv/3hLyyAiAMBdu3Rw2/LwhVfdNWxzJcHtMJE+mWzThAlF2xIijaXwFHMEQCIGX0W6WZi1mif/4ae+0BavHx+Q1Us6qPdFCqX1aiUQO9AiB/ckcDrR7blmgLKEtW1P/LiPf7dZ6rvgiqMPKbhROD0gFHUiEDCJ3BDHrG21T5EymvYXMz2ziM6tDCMfcjN50bmQMLAtwhAjrdkE89bc9Z3bkGsN7iNSm3/7ntUOXoYVGSaGAiHw5zUq4AIgIDqaTDf1mW06ol26xrVwrwZQOUSSlCRgs1R1Ptnuylh3EQ2QxqTwAAAIAAAACABAAAgAAiAgJ/Y5l1fS7/VaE2rQLGhLGDi2VW5fG2s0KCqUtrUAUQlhDZDGpPAAAAgAAAAIAFAACAAA==
Given the above PSBT, a transaction extractor must create this Bitcoin transaction: * Bytes in Hex:
0200000000010258e87a21b56daf0c23be8e7070456c336f7cbaa5c8757924f545887bb2abdd7500000000da00473044022074018ad4180097b873323c0015720b3684cc8123891048e7dbcd9b55ad679c99022073d369b740e3eb53dcefa33823c8070514ca55a7dd9544f157c167913261118c01483045022100f61038b308dc1da865a34852746f015772934208c6d24454393cd99bdf2217770220056e675a675a6d0a02b85b14e5e29074d8a25a9b5760bea2816f661910a006ea01475221029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f2102dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d752aeffffffff838d0427d0ec650a68aa46bb0b098aea4422c071b2ca78352a077959d07cea1d01000000232200208c2353173743b595dfb4a07b72ba8e42e3797da74e87fe7d9d7497e3b2028903ffffffff0270aaf00800000000160014d85c2b71d0060b09c9886aeb815e50991dda124d00e1f5050000000016001400aea9a2e5f0f876a588df5546e8742d1d87008f000400473044022062eb7a556107a7c73f45ac4ab5a1dddf6f7075fb1275969a7f383efff784bcb202200c05dbb7470dbf2f08557dd356c7325c1ed30913e996cd3840945db12228da5f01473044022065f45ba5998b59a27ffe1a7bed016af1f1f90d54b3aa8f7450aa5f56a25103bd02207f724703ad1edb96680b284b56d4ffcb88f7fb759eabbe08aa30f29b851383d20147522103089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc21023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7352ae00000000
Given these two PSBTs with unknown key-value pairs: * Bytes in Hex:
70736274ff01003f0200000001ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0000000000ffffffff010000000000000000036a0100000000000af00102030405060708090f0102030405060708090a0b0c0d0e0f000af00102030405060708090f0102030405060708090a0b0c0d0e0f000af00102030405060708090f0102030405060708090a0b0c0d0e0f00
** Base64 String:
cHNidP8BAD8CAAAAAf//////////////////////////////////////////AAAAAAD/////AQAAAAAAAAAAA2oBAAAAAAAK8AECAwQFBgcICQ8BAgMEBQYHCAkKCwwNDg8ACvABAgMEBQYHCAkPAQIDBAUGBwgJCgsMDQ4PAArwAQIDBAUGBwgJDwECAwQFBgcICQoLDA0ODwA=
* Bytes in Hex:
70736274ff01003f0200000001ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0000000000ffffffff010000000000000000036a0100000000000af00102030405060708100f0102030405060708090a0b0c0d0e0f000af00102030405060708100f0102030405060708090a0b0c0d0e0f000af00102030405060708100f0102030405060708090a0b0c0d0e0f00
** Base64 String:
cHNidP8BAD8CAAAAAf//////////////////////////////////////////AAAAAAD/////AQAAAAAAAAAAA2oBAAAAAAAK8AECAwQFBgcIEA8BAgMEBQYHCAkKCwwNDg8ACvABAgMEBQYHCBAPAQIDBAUGBwgJCgsMDQ4PAArwAQIDBAUGBwgQDwECAwQFBgcICQoLDA0ODwA=
A combiner which orders keys lexicographically must produce the following PSBT: * Bytes in Hex:
70736274ff01003f0200000001ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0000000000ffffffff010000000000000000036a0100000000000af00102030405060708090f0102030405060708090a0b0c0d0e0f0af00102030405060708100f0102030405060708090a0b0c0d0e0f000af00102030405060708090f0102030405060708090a0b0c0d0e0f0af00102030405060708100f0102030405060708090a0b0c0d0e0f000af00102030405060708090f0102030405060708090a0b0c0d0e0f0af00102030405060708100f0102030405060708090a0b0c0d0e0f00
* Base64 String:
cHNidP8BAD8CAAAAAf//////////////////////////////////////////AAAAAAD/////AQAAAAAAAAAAA2oBAAAAAAAK8AECAwQFBgcICQ8BAgMEBQYHCAkKCwwNDg8K8AECAwQFBgcIEA8BAgMEBQYHCAkKCwwNDg8ACvABAgMEBQYHCAkPAQIDBAUGBwgJCgsMDQ4PCvABAgMEBQYHCBAPAQIDBAUGBwgJCgsMDQ4PAArwAQIDBAUGBwgJDwECAwQFBgcICQoLDA0ODwrwAQIDBAUGBwgQDwECAwQFBgcICQoLDA0ODwA=
==Rationale== ==Reference implementation== The reference implementation of the PSBT format is available at https://github.com/achow101/bitcoin/tree/psbt. ==Acknowledgements== Special thanks to Pieter Wuille for suggesting that such a transaction format should be made and for coming up with the name and abbreviation of PSBT. Thanks to Pieter Wuille, Gregory Maxwell, Jonathan Underwood, Daniel Cousens and those who commented on the bitcoin-dev mailing list for additional comments and suggestions for improving this proposal. ================================================ FILE: bip-0175.mediawiki ================================================
  BIP: 175
  Layer: Applications
  Title: Pay to Contract Protocol
  Authors: Omar Shibli 
           Nicholas Gregory 
  Status: Closed
  Type: Informational
  Assigned: 2017-07-17
  License: BSD-2-Clause
==Abstract== Utilizing hierarchical deterministic wallets as described in BIP-0032 and the "Purpose Field" in BIP-0043, this document specifies the multiparty pay-to-contract key derivation scheme outlined by Ilja Gerhardt and Timo Hanke.[0] The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED", "MAY", and "OPTIONAL" in this document are to be interpreted as described in RFC 2119. ==Motivation== A Bitcoin transaction represents a "real world" contract between two parties transferring value. Counterparties in a business interaction traditionally keep track of a payment with bills (invoices) and receipts. Delivery of a good is made by the payee once the payer has signed the receipt, agreeing to pay for the items on the invoice. Gerhardt and Hanke [0] formulate this interaction within the confines of the Bitcoin protocol using homomorphic payment addresses and the multiparty pay-to-contract protocol. The protocol is constructed in such a way that all parties have cryptographic proof of both who is being paid and for what. Using the technique described in this BIP, an address can be provably derived from the terms of a contract and the payee's public key. This derivation scheme does not bloat the UTXO and is completely hidden to network participants; the derived address looks like any other P2(W)PKH or P2(W)SH address. Redemption of the funds requires knowledge of the contract and the payee's private key. This scheme utilizes the foundations of BIP-0032, providing a consistent way for preexisting wallet developers to implement the specification. ==Specification== This key derivation scheme requires two parties: a payer (customer) and a payee (merchant). The customer submits to the merchant a purchase request, specifying what goods/services they would like to buy. From the purchase request the merchant constructs an invoice (contract), specifying the billable items and total amount to be paid. The merchant must give this contract alongside a “payment base” extended public key to the customer. Given this information, the customer will be able to fulfill the contract by generating the public key of the payment address associated with the contract and the payment base, then sending the funds there. We define the following levels in BIP32 path: m / purpose' / coin_type' / contract_hash contract_hash consists of multiple levels. Apostrophe in the path indicates that BIP32 hardened derivation is used. We define the following extended public keys: Payment base denoted as payment_base: m / purpose' / coin_type' Payment address denoted as payment_address: m / purpose' / coin_type' / contract_hash or m / payment_base / contract_hash Each level has special meaning described in the chapters below. ===Purpose=== Purpose is a constant set to 175' (or 0x800000AF) following the BIP-0043 recommendation. It indicates that the subtree of this node is used according to this specification. m / 175' / * Hardened derivation is used at this level. ===Coin type=== The coin type field is identical to the same field in BIP-0044. Hardened derivation is used at this level. ===Payment address generation=== For a given contract documents denoted by c1,...,cn, payment base extended public key denoted by payment_base, and cryptographic hash function denoted by h. 1. Compute cryptographic hashes for all contract documents, by applying the hash function. h(c1),...,h(cn) 2. Sort all hashes lexicographically. hash_1,...,hash_n 3. Prepend payment_base and concatenate the sorted hashes and apply the hash function. h(payment_base+hash_1+...+hash_n) 4. Compute a partial BIP32 derivation path from the combined hash as defined in Hash to Partial Derivation Path Mapping procedure below. contract_hash 5. Prepend payment_base to contract_hash derivation path. payment_base / contract_hash 6. Compute public extended key from the derivation path in step 5. 7. Compute address of the public extended key (P2PKH) from step 6. ===Payment address verification=== For a given Bitcoin address, payment_base extended public key, contract documents denoted by c1,...,cn, and cryptographic hash function denoted by h, we can verify the integrity of the address by the following steps: 1. Compute contract address from the given inputs as described in Contract Address Generation section. 2. Compare the computed address from step 1 with the given Bitcoin address as an input. ===Redemption=== The merchant is able to construct the private key offline using the method described in the Payment Address Generation section. The merchant should actively monitor the blockchain for the payment to the payment address. Because the address is generated from the payment base and the contract, the merchant must implicitly agree to those terms in order to spend the funds. The act of making the payment to that address thus serves as a receipt for the customer. ===Hash to partial derivation path mapping=== At this section, we define hash to partial BIP32 derivation path mapping procedure that maps between an arbitrary hex number to a partial BIP32 derivation path. For a given hex number, do the following: 1. Partition hex number into parts, each part length is 4 chars. 2. Convert each part to integer in decimal format. 3. Concatenate all numbers with slash /. ==Examples== For the following given inputs: master private extended key: xprv9s21ZrQH143K2JF8RafpqtKiTbsbaxEeUaMnNHsm5o6wCW3z8ySyH4UxFVSfZ8n7ESu7fgir8imbZKLYVBxFPND1pniTZ81vKfd45EHKX73 coin type: 0 we can compute payment base as follows: payment base derivation path: m/175'/0' contract base public extended key: xpub6B3JSEWjqm5GgfzcjPwBixxLPzi15pFM3jq4E4yCzXXUFS5MFdXiSdw7b5dbdPGHuc7c1V4zXbbFRtc9G1njMUt9ZvMdGVGYQSQsurD6HAW In the below examples, we are going to use SHA256 as a cryptographic hash function, and the above contract base public key. ====Payment address generation==== As an input, we have a contract that consists of two documents, below are contents: document 1: bar document 2: foo 1. Apply the hash function: document 1: fcde2b2edba56bf408601fb721fe9b5c338d10ee429ea04fae5511b68fbf8fb9 document 2: 2c26b46b68ffc68ff99b453c1d30413413422d706483bfa0f98a5e886266e7ae 2. Sort all hashes lexicographically: 2c26b46b68ffc68ff99b453c1d30413413422d706483bfa0f98a5e886266e7ae fcde2b2edba56bf408601fb721fe9b5c338d10ee429ea04fae5511b68fbf8fb9 3. Concatenate hashes and apply the hash function. concatenated hash: payment_base xpub6B3JSEWjqm5GgfzcjPwBixxLPzi15pFM3jq4E4yCzXXUFS5MFdXiSdw7b5dbdPGHuc7c1V4zXbbFRtc9G1njMUt9ZvMdGVGYQSQsurD6HAW2c26b46b68ffc68ff99b453c1d30413413422d706483bfa0f98a5e886266e7aefcde2b2edba56bf408601fb721fe9b5c338d10ee429ea04fae5511b68fbf8fb9 combined hash: 310057788c6073640dc222466d003411cd5c1cc0bf2803fc6ebbfae03ceb4451 4. Compute the partial BIP32 derivation path of the combined hash. 12544/22392/35936/29540/3522/8774/27904/13329/52572/7360/48936/1020/28347/64224/15595/17489 5. Prepend payment_base to contract_hash derivation path. contract_base_pub/12544/22392/35936/29540/3522/8774/27904/13329/52572/7360/48936/1020/28347/64224/15595/17489 or m/175'/0'/12544/22392/35936/29540/3522/8774/27904/13329/52572/7360/48936/1020/28347/64224/15595/17489 6. Compute public extended key. xpub6hefaATTG5LbcwyPDvmNfnkyzefoM2TJDoo5astH7Gvs1g8vZURviBWvAvBnWc2CNb8ybJ6mDpnQYVsvNSZ3oUmbssX3rUVG97TFYa6AXVk 7. Compute address of the public extended key (P2PKH). 1C7f322izqMqLzZzfzkPAjxBzprxDi47Yf ====Verification example (negative test)==== Similar to the input above, except this time we have a contract that consists of one document, below is the content: document 1: baz 1. Apply the hash function. baa5a0964d3320fbc0c6a922140453c8513ea24ab8fd0577034804a967248096 2. Prepend payment_base xpub6B3JSEWjqm5GgfzcjPwBixxLPzi15pFM3jq4E4yCzXXUFS5MFdXiSdw7b5dbdPGHuc7c1V4zXbbFRtc9G1njMUt9ZvMdGVGYQSQsurD6HAWbaa5a0964d3320fbc0c6a922140453c8513ea24ab8fd0577034804a967248096 2. Apply hash function 3a08605829413ce0bf551b08d21e4a28dbda6e407f90eff1c448e839050c73a1 3. Compute the partial derivation path. 5338/54412/19213/962/30664/62597/11873/59874/56779/24089/54550/19585/28087/36422/18666/17562 4. Prepend contract_basepub to contract_hash derivation path. contract_base_pub/5338/54412/19213/962/30664/62597/11873/59874/56779/24089/54550/19585/28087/36422/18666/17562 or m/175'/0'/5338/54412/19213/962/30664/62597/11873/59874/56779/24089/54550/19585/28087/36422/18666/17562 5. Compute public extended key. xpub6h9k2KqsMpwghxt7naj1puhGV1ZDC88sxvpYN1HibCf8yQZdPsuhYmmvdK32Kf2Lb3rS1sV8UcZ1f84DJEiXuVfLCAj4bC85aEUCxh38m8i 7. Compute address of the public extended key (P2PKH). 1QGe5LaDMAmHeibJbZBmZqhQDZSp7QCqSs 8. As expected the address doesn't match the Bitcoin address from the last example 1C7f322izqMqLzZzfzkPAjxBzprxDi47Yf. Verification operation will succeed only if we use identical documents to ones that have been used in the contract address generation. ==Compatibility== This specification is not backward compatible with BIP32 specification, the proposed derivation scheme in this BIP is a BIP32 compliant. Communication between payer and payee as well as hashing the contract and generating the path requires significant modification to the wallet. ==Reference implementations== * Reference implementation to Hash to Partial Derivation Path Mapping in javascript ([[https://github.com/commerceblock/pay-to-contract-lib/blob/master/lib/contract.js|https://github.com/commerceblock/pay-to-contract-lib]]) ==Reference== * [[bip-0032.mediawiki|BIP32 - Hierarchical Deterministic Wallets]] * [[bip-0043.mediawiki|BIP43 - Purpose Field for Deterministic Wallets]] * [[bip-0044.mediawiki|BIP44 - Multi-Account Hierarchy for Deterministic Wallets]] * [[https://arxiv.org/abs/1212.3257|Homomorphic Payment Addresses and the Pay-to-Contract Protocol]] ==Copyright== This BIP is licensed under the 2-clause BSD license. ================================================ FILE: bip-0176.mediawiki ================================================
  BIP: 176
  Title: Bits Denomination
  Authors: Jimmy Song 
  Comments-Summary: No comments yet.
  Comments-URI: https://github.com/bitcoin/bips/wiki/Comments:BIP-0176
  Status: Draft
  Type: Informational
  Assigned: 2017-12-12
  License: BSD-2-Clause
== Abstract == Bits is presented here as the standard term for 100 (one hundred) satoshis or 1/1,000,000 (one one-millionth) of a bitcoin. == Motivation == The bitcoin price has grown over the years and once the price is past $10,000 USD or so, bitcoin amounts under $10 USD start having enough decimal places that it's difficult to tell whether the user is off by a factor of 10 or not. Switching the denomination to "bits" makes comprehension easier. For example, when BTC is $15,000 USD, $10.05 is a somewhat confusing 0.00067 BTC, versus 670 bits, which is a lot clearer. Additionally, reverse comparisons are easier as 59 bits being $1 is easier to comprehend for most people than 0.000059 BTC being $1. Similar comparisons can be made to other currencies: 1 yen being 0.8 bits, 1 won being 0.07 bits and so on. Potential benefits of utilizing "bits" include: # Reduce user error on small bitcoin amounts. # Reduce unit bias for users that want a "whole" bitcoin. # Allow easier comparisons of prices for most users. # Allow easier bi-directional comparisons to fiat currencies. # Allows all UTXO amounts to need at most 2 decimal places, which can be easier to handle. == Specification == Definition: 1 bit = 100 satoshis. Plural of "bit" is "bits." The terms "bit" and "bits" are not proper nouns and thus should not be capitalized unless used at the start of a sentence, etc. All bitcoin-denominated items are encouraged to also show the denomination in bits, either as the default or as an option. == Rationale == As bitcoin grows in price versus fiat currencies, it's important to give users the ability to quickly and accurately calculate prices for transactions, savings and other economic activities. "Bits" have been used as a denomination within the Bitcoin ecosystem for some time. The idea of this BIP is to formalize this name. Additionally, "bits" is likely the only other denomination that will be needed for Bitcoin as 0.01 bit = 1 satoshi, meaning that two decimal places will be sufficient to describe any current utxo. Existing terms used in bitcoin such as satoshi, milli-bitcoin (mBTC) and bitcoin (BTC) do not conflict as they operate at different orders of magnitude. The term micro-bitcoin (µBTC) can continue to exist in tandem with the term "bits." == Backwards Compatibility == Software such as the Bitcoin Core GUI currently use the µBTC denomination and can continue to do so. There is no obligation to switch to "bits." The term "bit" has many different definitions, but the ones of particular note are these: * 1 bit = 1/8 dollar (e.g., that candy cost me 2 bits {or 1/4 dollar}) * bit meaning some amount of data (e.g., the first bit of the version field is 0) * bit meaning strength of a cryptographic algorithm (e.g., 256-bit ECDSA is used in Bitcoin) The first is a bit dated and isn't likely to confuse people dealing with Bitcoin. The second and third are computer science terms and context should be sufficient to figure out what the user of the word means. == Copyright == This BIP is licensed under the BSD 2-clause license. == Credit == It's hard to ascertain exactly who invented the term "bits," but the term has been around for a while and the author of this BIP does not take any credit for inventing the term. ================================================ FILE: bip-0177.mediawiki ================================================
  BIP: 177
  Title: Redefine Bitcoin's Base Unit
  Authors: John Carvalho 
  Status: Draft
  Type: Informational
  Assigned: 2025-04-23
  License: CC0-1.0
==Introduction== ===Abstract=== This BIP proposes redefining the commonly recognized "bitcoin" unit so that the base unit becomes the primary reference unit. Under this proposal, one bitcoin is defined as that indivisible base unit, eliminating the convention of synthetic decimal places. By making the base unit the standard measure, this BIP aims to simplify user comprehension, reduce confusion, and align on-chain values directly with their displayed representation. ===Motivation=== The current convention defines one bitcoin as 100,000,000 base units. This representation requires dealing with eight simulated decimal places, which can be confusing and foster the misconception that bitcoin is inherently decimal-based. In reality, Bitcoin’s ledger represents values as integral base units. The decimal point is merely a human-imposed abstraction. By redefining the base unit as "one bitcoin," this BIP aligns user perception with the protocol’s true nature. It reduces cognitive overhead, ensures users understand Bitcoin as counting discrete units, and ultimately improves educational clarity and user experience. ===Specification=== '''Redefinition of the Unit:''' * Internally, the base units remain unchanged. * Historically, 1 bitcoin = 100,000,000 base units. Under this proposal, "1 bitcoin" equals one base unit. * What was previously referred to as "1 bitcoin" now corresponds to 100 million bitcoins under the new definition. '''Terminology:''' * The informal terms "satoshi" or "sat" are deprecated. * All references, interfaces, and documentation SHOULD refer to the base unit simply as "bitcoin." * The currency code "BTC" is unaffected by these changes, and continues to mean 100,000,000 base units. '''Display and Formatting:''' * Applications SHOULD allow users to toggle between the legacy BTC format (1 BTC = 100,000,000 base units) and the new integral format (1 bitcoin = 1 base unit). * Use of the ₿ symbol MAY be used to represent base-unit bitcoins but is OPTIONAL. Example 1: * Old display: 0.00010000 bitcoin * New display: ₿10,000 or 10,000 bitcoins or 0.00010000 BTC Example 2: * Old display: 10.23486 bitcoin * New display: ₿1,023,486,000 or 1,023,486,000 bitcoins or 10.23486 BTC Example 3: * Old display: 0.345 BTC * New display: No changes required or ₿34,500,000 or 34,500,000 bitcoins NOTE: Traditional number display abbreviations, like 2.5M for millions, are also optional. '''Conversion:''' * Ledger and consensus rules remain unchanged. * BTC as a currency code remains unchanged (1 BTC = 100,000,000 base units) * Implementations adopting this standard MUST multiply previously displayed bitcoin amounts by 100,000,000 to determine the new integer representation. ===Rationale=== '''Usability:''' Integer-only displays simplify mental arithmetic and reduce potential confusion or user error. '''Protocol Alignment:''' The Bitcoin protocol inherently counts discrete units. Removing the artificial decimal format aligns user perception with Bitcoin’s actual integral design. '''Educational Clarity:''' Presenting integers ensures newcomers do not mistakenly assume that Bitcoin’s nature is decimal-based. It conveys Bitcoin’s true design from the start. '''Future-Proofing:''' Adopting the base unit as the primary measure ensures a consistent standard that can scale smoothly as Bitcoin adoption grows. '''Perception of Supply:''' While the total count of base units is roughly 2.1 quadrillion, this proposal does not alter supply in any way. The change is purely representational. Comparisons can be drawn to other currencies like the Japanese yen or Indonesian rupiah, where high unit counts are standard and not perceived as inflationary. ===Addressing Alternative Approaches=== '''Refuting the "Bits" Proposal''' ([https://github.com/bitcoin/bips/blob/master/bip-0176.mediawiki BIP 176]) An alternative suggestion (BIP 176) proposes using "bits" to represent one-millionth of a bitcoin (100 satoshis). While this reduces the number of decimal places in certain contexts, it fails to fully address the core issues our BIP aims to solve: 1. '''Persistent Decimal Mindset:''' Using "bits" still retains a layered decimal approach, requiring users to think in terms of multiple denominations (BTC and bits). This shifts complexity rather than eliminating it. 2. '''Inconsistent User Experience:''' Users must learn to toggle between BTC for large amounts and bits for small amounts. Instead of providing a unified view of value, it fragments the user experience. 3. '''Incomplete Alignment with the Protocol’s Nature:''' The "bits" proposal does not realign the displayed value with the integral nature of Bitcoin’s ledger. It continues to rely on fractional units, masking the fundamental integer-based accounting that Bitcoin employs. 4. '''Not Permanently Future-Proof:''' Though "bits" may simplify certain price ranges, future circumstances could demand additional denominations or scaling adjustments. Our integral approach resolves this problem entirely by making the base unit the standard measure, avoiding future fragmentation. In essence, while BIP 176 attempts to simplify small amount representations, it only replaces one decimal representation with another. By redefining "bitcoin" as the base unit, this BIP eliminates reliance on decimal fractions and separate denominations entirely, offering a clearer, more intuitive, and ultimately more durable solution. ===Handling the Terms “satoshi” and “sat”=== '''Background''' “Satoshi” (or its shorthand “sat”) emerged organically some years ago, to honour Bitcoin’s creator and to give a friendly name to the 100-millionth "fraction" of a bitcoin. Over time “stacking sats” became a meme, and the term now appears in podcasts, apparel, and some wallet UIs. While culturally valuable, the term introduces an implicit second denomination layer that contradicts the goal of this BIP: a single base unit, called simply "bitcoin". Of course this BIP cannot stop anyone from using any colloquial term they prefer, but this document exists to specify how to display Bitcoin's only units as "bitcoin" correctly. ===Backward Compatibility=== No consensus rules are altered, and on-chain data remains unchanged. Differences arise solely in display formats: * '''For Developers:''' Update GUIs, APIs, and documentation to present values as integers. Remove references to fractional Bitcoin. BTC units remain unchanged. * '''For Users:''' The actual value of holdings does not change. Transitional measures, such as dual displays or explanatory tooltips, can ease the adjustment period. ===Security Considerations=== A short-term risk of confusion exists as users adapt to the new representation. Users accustomed to decimals may misinterpret initial displays. To mitigate this: * Offer dual displays and tooltips during the transition. * Provide clear educational materials and coordinated messaging. * Use alerts or confirmations in applications if input values appear unexpectedly large or small. * Highlight the unchanging 21M BTC supply cap and equivalence to avoid misinterpretation as inflationary. ===Reference Implementation=== Some wallets, such as Bitkit, have successfully adopted integer-only displays, demonstrating the feasibility of this approach, without incident. Transitional features — like showing both old and new formats side-by-side — can help smooth the transition. ===Test Vectors=== * Old: 1.00000000 Bitcoin → New: ₿100,000,000 (or 100,000,000 bitcoins) * Old: 0.00010000 Bitcoin → New: ₿10,000 (or 10,000 bitcoins) * Old: 0.00500000 Bitcoin → New: ₿500,000 (or 500,000 bitcoins) * Old: 0.005 BTC → New: 0.005 BTC (or ₿500,000 or 500,000 bitcoins) All formerly fractional representations now directly correspond to whole-number multiples of the base unit. ===Implementation Timeline=== '''Phase 1 (3-6 months):''' Introduce the concept, provide dual displays and educational materials. Begin pilot testing in willing wallet apps. '''Phase 2 (6-12 months):''' Prominent services adopt integer-only displays by default. Community coordination and media campaigns ensure consistency. '''Phase 3 (12+ months):''' Integer representation becomes standard. Documentation and user guides no longer reference decimal-based formats. ===Conclusion=== Redefining "bitcoin" as the smallest indivisible unit, and removing decimal-based representations, simplifies comprehension and aligns displayed values with the protocol’s integral accounting. While a transition period may be necessary, the long-term benefits include clearer communication, reduced confusion, and a more accurate understanding of Bitcoin’s fundamental design. ===Copyright=== This BIP is licensed under CC0-1.0. ================================================ FILE: bip-0178.mediawiki ================================================
  BIP: 178
  Layer: Applications
  Title: Version Extended WIF
  Authors: Karl-Johan Alm 
  Comments-Summary: Discouraged for implementation (one person)
  Comments-URI: https://github.com/bitcoin/bips/wiki/Comments:BIP-0178
  Status: Draft
  Type: Specification
  Assigned: 2018-04-04
  License: CC0-1.0
== Abstract == An extension to the Wallet Import Format (WIF) to specify what kind of bitcoin address the private key corresponds to. == Motivation == There are several types of bitcoin addresses which can all be associated with a given private key: P2PKH (legacy 1... format), P2SH-P2WPKH (SegWit public key inside P2SH), P2WPKH (bech32), etc. While private keys have a 1-byte suffix indicating whether the corresponding public key is compressed (0x01) or not (through suffix absence), there is no way of knowing what kind of bitcoin address were associated with the private key. As a result, when importing a private key, the wallet has to assume all kinds, and keep track of each possible alternative. By extending the suffix, we can specify what kind of bitcoin address was associated with a given private key. == Specification == Currently, private keys are stored as a uint256 (private key data) followed by an optional uint8 (compressed flag). The latter is extended to specify the address types: {|class="wikitable" style="text-align: center;" |- !Value !Type !Compr !Clarification |- |No suffix||P2PKH_UNCOMPRESSED||No||Uncompressed legacy public key. Unknown public key format |- |0x01||P2PKH_COMPRESSED||Yes||Compressed legacy public key. Unknown public key format |- |0x10||P2PKH||Yes||Compressed legacy public key. Legacy public key format (1...) |- |0x11||P2WPKH||Yes||Bech32 format (native Segwit) |- |0x12||P2WPKH_P2SH||Yes||Segwit nested in BIP16 P2SH (3...) |} When a wallet imports a private key, it will have two outcomes: * the key is using one of the legacy types, in which case all types must be accounted for * the key is using one of the extended types, in which case the wallet need only track the specific corresponding address Note: the difference between `0x01` and `0x10` is that the former can correspond to any of the types above, whereas the latter *only* corresponds to a P2PKH (legacy non-segwit). == Compatibility == This proposal is not backwards compatible, in that software that does not recognize the new types will not understand the compressed flag. It would be trivial to change this, by keeping the 'uncompressed' state as it is (no suffix) and changing 'compressed' to be 'anything not 0', as opposed to 'the value 1'. The proposal ''is'' backwards compatible in that new wallet software will always understand the old WIF format, however. It will, as it does today, assume that any kind of bitcoin address is possible, and will have to track all of them, as it has to today. == Acknowledgements == This BIP is based on the initial proposal by Thomas Voegtlin (thomasv at electrum dot org) on the Bitcoin Dev mailing listhttps://lists.linuxfoundation.org/pipermail/bitcoin-dev/2017-September/015007.html and the Electrum 3.0 implementationhttps://github.com/spesmilo/electrum/blob/82e88cb89df35288b80dfdbe071da74247351251/RELEASE-NOTES#L95-L108 == Reference implementation == There is a partial implementation which adds, but does not use, the types described in this BIP here: https://github.com/bitcoin/bitcoin/pull/12869 == References == == Copyright == This document is licensed under the Creative Commons CC0 1.0 Universal license. ================================================ FILE: bip-0179.mediawiki ================================================
  BIP: 179
  Title: Name for payment recipient identifiers
  Authors: Emil Engler 
           Luke Dashjr 
  Status: Draft
  Type: Informational
  Assigned: 2019-10-17
  License: CC0-1.0
==Abstract== This BIP proposes a new term for 'address' ==Specification== The new term is: ''Bitcoin'' '''Invoice''' ''Address'' The ''Bitcoin'' and ''Address'' parts are optional. The address suffix should only be used as a transitional step. A ''Bitcoin'' Invoice ''Address'' is a string of characters that can be used to indicate the intended recipient and purpose of a transaction. ==Motivation== Bitcoin addresses are intended to be only used '''once''' and you should generate a new one for every new incoming payment. The term 'address' however indicates consistency because nearly everything on the internet or the offline world with the term 'address' is something that rarely or even never changes (postal address, email address, IP addresses (depends heavily on the provider), etc.) The motivation for this BIP is to change the term address to something that indicates that the address is connected to a single transaction. ==Rationale== The reason why we use ''Bitcoin Invoice Address'' or just ''Invoice'' is to emphasize that it is single-use. The terms ''Bitcoin'' and ''Address'' are optional for the following reasons: For ''Bitcoin'': * Useful for multicoin wallets to indicate that it belongs to Bitcoin * Indicates a difference between a lightning and an on-chain invoice For ''Address'': * To not confuse users with a completely new term * To show that it is where you send something to * To not break backwards compatibility This gives us the four following possibilities: * Bitcoin Invoice Address * Bitcoin Invoice * Invoice Address * Invoice ==Backwards Compatibility== To avoid issues, the 'Address' suffix is permitted, but not recommended. The suffix 'Address' remains so users should be immediately able to recognize it until the new term is widely known. ==Acknowledgements== Thanks to Chris Belcher for the suggestion of the term 'Bitcoin Invoice Address' ==Copyright== This BIP is released under CC0-1.0 and therefore Public Domain. ================================================ FILE: bip-0180.mediawiki ================================================
  BIP: 180
  Layer: Peer Services
  Title: Block size/weight fraud proof
  Authors: Luke Dashjr 
  Status: Closed
  Type: Specification
  Assigned: 2017-03-17
  License: BSD-2-Clause
==Abstract== A fraud proof that enables light clients to detect oversized (or overweight) blocks. ==Copyright== This BIP is licensed under the BSD 2-clause license. ==Definitions== ; full tx size proof : SHA2 midstate and tail data proving the size of the full transaction data being hashed. ; size component : Either a merkle link and height in the merkle tree thereof, or a full tx size proof. ; full-size proof : The set of size components proving the lower-bound size of the block. ; stripped-size proof : The set of size components proving the lower-bound size of the block when stripped of segwit witness data. ==Specification== ===Proof format=== * varint: ceil(log2(number of transactions in block)) * varint: number of size components in stripped-size proof * foreach: ** varint: ceil(log2(number of transactions represented by this size-component)) + 1 ** if zero: *** (this indicates a full tx size proof) *** 256-bit: SHA2 midstate up until just before the final SHA2 chunk *** varint: total size of tx *** uint8: size of final SHA2 chunk (0-55) *** 0-55 bytes: final SHA2 chunk ** if one or more: *** (this indicates default tx size counting) *** 256-bit: SHA2 hash of merkle link * varint: number of size components in full-size proof (zero in case of a size-exceeded proof; non-zero for a weight-exceeded proof) * foreach: (same as with stripped-size proof) ===Proof verification=== To verify an individual size proof: #Check that at least one size component is a full tx size proof. (At least one size component MUST be a full tx size proof.) #Determine the lower-bound number of transactions in the block (lowTxCount). It is either pow(ceil(log2(txcount)) - 1, 2), or the position of the last full tx proof (plus one, if using 0-based positions). Note that the last full tx proof from *either* of the size proofs (stripped-size and full-size) should be used here. #Calculate the lower-bound transaction-data size as the default size * lowTxCount. #For each full tx size proof: ##Subtract the default size it was presumed to consume, and add the claimed total size of tx. ##Take the SHA2 midstate, and update it with the final SHA2 chunk (which needs to be padded, including with the total tx size). The final SHA2 hash is the transaction id (stripped-size proof) or hash (full-size proof). #For the full-size proof, replace the 60 byte default with any larger sizes proven from the stripped-size proof. #Build the merkle root, and compare it to the block header (stripped-size proof) or witness commitment (full-size proof). Ensure when building the merkle root, that there are no duplicate merkle links, and each merkle link claims to represent the correct number of represented transactions. #Add 80 bytes, plus the size of the tx-count varint, to the calculated lower-bound size. #The calculated size is returned as the lower-bound possible size of the block. For the stripped-size proof, the default size of transactions is 60 bytes. For the full-size proof, it is the size established by the stripped-size proof. To verify the complete weight proof: # Verify the stripped-size proof. Save the resulting lower-bound size (call it lowStrippedSize). # Verify the full-size proof. Save the resulting lower-bound size (call it lowFullSize). # Calculate minFullSize + (minStrippedSize * 3). This is the lower-bound block weight. # Compare the lower-bound block weight to the applicable block weight limit. ===Network protocol=== If a light client detects that one or more of its peers do not consider the block it knows to have the most work as their best block, it should inquire with all those peers for a fraud proof by sending a new message getfraud, with a block locator (between the last common block, and the presumed best tip) as the sole parameter (extra parameters should be ignored). Compatible nodes will respond with a (new) fraud message, which has 2-3 parameters: * uint256: The hash of the most recent block in the locator (or a parent thereof) that it has checked. In the event of an invalid block, this should be the exact invalid block's hash (post-invalid blocks should be treated as unchecked, even if the node has independently checked them for some reason). * varint: Fraud proof type code ** 0 = Block is valid ** 1 = No fraud proof available ** 2 = Size/weight exceeded * (For type 2) the fraud proof If none of the blocks in the locator are recognised, compatible nodes should send a fraud message with no parameters. (To avoid this outcome, clients may include a known-common block in the locator.) In the event that the peer claims a block earlier than the client's tip is valid, the light client should prepare a new locator between that block and its tip, and rerequest getfraud until it has determined which block the peer rejects and why. Once a block is proven to be invalid, the light client should never consider any blockchain including it as a candidate for the best chain. It should not recheck blocks known to be invalid, nor continue proving it from other nodes. (To avoid doubt: the user MAY be given the opportunity to override any rejections, but should be warned of the implications of doing so.) If an invalid fraud proof is provided, the client SHOULD CONSIDER disconnecting and possibly banning the node providing it. However, if any change has been made to the size/weight limits, that should be taken into consideration (eg, if the limit increases, an innocent node may prove a size smaller than the limit). ==Information== ===Creation of proofs=== Proofs should ideally use the smallest amount of data required to prove excess of the limit. The most obvious mechanism in doing so, would be to include full tx size proofs for the largest transactions until the limit is exceeded. However, in some cases, a smaller size may be accomplished by collapsing more merkle links. Because optimisation of proof size may be complicated, nodes are not required to implement it in any particular manner, so long as the proofs meet the requirements given above in [[#proof-verification|Proof verification]]. ==Motivation== Recently, there have been proposals for hardforks to increase the block size limit. While no consensus has been reached, proponents of these ideas often threaten and attempt to have miners force them through anyway. As things presently are, light clients cannot detect invalid blocks at all, and could be fooled into accepting an invalid chain created in such a manner. By supporting block size fraud proofs, light clients can protect their users from this form of unconsensual "hardfork" attempt. ==Rationale== Why must a full tx size proof be included? * This is necessary to establish that the claimed block transaction count is not inflated. Otherwise, a prover could claim any number of represented transactions for merkle links, and rely on the default size alone to exceed the limit. How does the full tx size proof actually prove the size? * The first step of SHA2 hashing is to transform the input data into chunks (per [https://tools.ietf.org/html/rfc4634#section-4.1 RFC 4634]). The final chunk is required to include the absolute length of the input data at the end of the final chunk. Therefore, by committing to the midstate prior to the final chunk, and replaying only the final chunk, we can confirm that the claimed size matches the full transaction data being hashed. How does this prove the block weight? * The block weight defined by [[bip-0141.mediawiki|BIP 141]] is the size of the block stripped of its segwit signatures times 3, plus the full size of the block. By proving lower-bound sizes of both the stripped block and the full block, a lower-bound weight can also be calculated. Why is the number of transactions in the block represented as a log2? * To avoid attacks that rely on fooling clients by claiming an amount they cannot verify. Why does it matter if a full tx size proof is on the right side of a duplicate merkle link? * We assume full tx size proofs show the number of transactions in the block. This assumption doesn't hold if the proof is provided on the right-hand side of duplicate links. Why a fraud proof only for oversized/overweight blocks? * While it is currently believed to be impossible to prove all invalid (or rather, won't-be-part-of-the-main-chain) blocks, there are regularly active proposals of miners attacking with simply oversized blocks in an attempt to force a hardfork. This specific attack can be proven, and reliably so, since the proof cannot be broken without also breaking the attempted hardfork at the same time. ==Backwards compatibility== These fraud proofs protect only clients which use them. In non-attack scenarios, they are unnecessary and clients supporting them will otherwise behave as any other. ==Reference implementation== TODO ================================================ FILE: bip-0197.mediawiki ================================================
  BIP: 197
  Layer: Applications
  Title: Hashed Time-Locked Collateral Contract
  Authors: Matthew Black 
           Tony Cai 
  Status: Draft
  Type: Specification
  Assigned: 2019-03-19
  License: BSD-3-Clause OR CC0-1.0
==Abstract== This BIP describes a script for generalized debt agreement contract based on Hashed Time-Lock Contract (BIP 199) transactions according to the Atomic Loans specification (https://arxiv.org/pdf/1901.05117.pdf). For more details visit https://atomicloans.io. ==Summary== A Hashed Time-Locked Collateral Contract (HTLCC) consists of two scripts that permit a designated party (the "borrower") to lock funds on the Bitcoin chain for a specified amount of time as collateral in a debt agreement where the loan principal is denominated in a currency on another blockchain. We denote the blockchain on which the loan principal is issued the principal blockchain. The purpose of each script is to enable the creation of a debt agreement between two parties (the "borrower" and the "lender"), where the collateral is locked in a P2SH, and can only be spent once the borrower repays the principal and interest in the debt agreement on the principal blockchain. In the case that the borrower does not repay, the borrower or lender can opt for liquidation of the collateral, which will involve the atomic swapping of collateral for the loan currency. In the case that at least one of the two parties don't opt for liquidation, then each party will be entitled to a percentage of the collateral, decided when the funds are initially locked in the P2SH. These funds are locked into two scripts. Refundable Collateral and Seizable Collateral scripts. The funds sent to these scripts represent the percentage of collateral that each party is entitled to in the case that repayment fails, and the parties don't opt for liquidation. The Refundable Collateral script takes the following form: OP_IF OP_SIZE OP_EQUALVERIFY [HASHOP] OP_EQUALVERIFY OP_DUP OP_HASH160 OP_EQUALVERIFY OP_CHECKSIG OP_ELSE OP_IF [TIMEOUTOP] OP_DROP OP_SIZE OP_PUSHDATA(1) OP_EQUALVERIFY [HASHOP] OP_EQUALVERIFY OP_SIZE OP_EQUALVERIFY [HASHOP] OP_EQUALVERIFY OP_2 OP_2 OP_CHECKMULTISIG OP_ELSE [TIMEOUTOP] OP_DROP OP_DUP OP_HASH160 OP_EQUALVERIFY OP_CHECKSIG OP_ENDIF OP_ENDIF The Seizable Collateral script takes the following form: OP_IF OP_SIZE OP_EQUALVERIFY [HASHOP] OP_EQUALVERIFY OP_DUP OP_HASH160 OP_EQUALVERIFY OP_CHECKSIG OP_ELSE OP_IF [TIMEOUTOP] OP_DROP OP_SIZE OP_EQUALVERIFY [HASHOP] OP_EQUALVERIFY OP_SIZE OP_EQUALVERIFY [HASHOP] OP_EQUALVERIFY OP_2 OP_2 OP_CHECKMULTISIG OP_ELSE OP_IF [TIMEOUTOP] OP_DROP OP_SIZE OP_EQUALVERIFY [HASHOP] OP_EQUALVERIFY OP_DUP OP_HASH160 OP_EQUALVERIFY OP_CHECKSIG OP_ELSE [TIMEOUTOP] OP_DROP OP_DUP OP_HASH160 OP_EQUALVERIFY OP_CHECKSIG OP_ENDIF OP_ENDIF OP_ENDIF [HASHOP] is either OP_SHA256 or OP_HASH160. [TIMEOUTOP] is either OP_CHECKSEQUENCEVERIFY or OP_CHECKLOCKTIMEVERIFY. ===Interaction=== * Alice (the "borrower") and Bob (the "lender") exchange public keys as well as two secret hashes A1, A2 created by Alice and three hashes B1, B2, B3 created by Bob. They then mutually agree upon a timeout threshold for the Loan Period, Liquidation Period, and Seizure Period. Alice constructs the script and P2SH address for the Refundable Collateral Contract and Seizable Collateral Contract. Bob constructs the script for the blockchain on which the loan principal will be issued - the principal blockchain. * Bob sends loan principal funds to the loan script on the principal blockchain * Alice sends funds to the Refundable Collateral P2SH address and the Seizable Collateral P2SH address. The amount of funds she sends to the two addresses will be determined beforehand off-chain between Alice and Bob. * Either ** Bob accepts locking of collateral by Alice and reveals B1, allowing Alice to withdraw the loan amount on the principal blockchain. ** Bob doesn't accept locking of collateral by Alice, and recovers the funds after the approve expiration while revealing B2, which allows Alice to refund the Refundable and Seizable collateral. ** If Bob accepts the locking of collateral by Alice *** Either **** Alice repays the loan by the end of the Loan Period and Bob reveals the secret to Alice by revealing it in the loan repayment acceptance transaction; OR **** Alice defaults on the loan and Alice and Bob both opt for collateral liquidation, where any third-party is able to bid on the collateral. The winning bidder, Charlie, will subsequently receive the liquidated collateral by way of an Atomic Swap between the collateral funds (ie. BTC locked in both the Refundable Collateral P2SH and the Seizable Collateral P2SH) and the bid funds (ie. funds denominated in the loan currency, put forth by Charlie as part of his bid). This is done by both Alice and Bob signing a multisig and revealing A2 and B2; OR **** Alice defaults on the loan and at least one of Alice or Bob opts out of collateral liquidation, then Alice recovers the Refundable Collateral funds and Bob spends the Seizable Collateral funds. **** Alice defaults on the loan and at least one of Alice or Bob opts out of collateral liquidation. But Bob doesn't spend the Seizable Collateral funds, so Alice recovers both the Refundable Collateral funds and the Seizable Collateral funds. ==Compatibility== BIP 197 is compatible with [https://github.com/ethereum/EIPs/pull/1850 ERC 1850] for [https://arxiv.org/pdf/1901.05117.pdf atomic loans] with Ethereum. Can be extended in the future to be compatible with other HTLC and smart contract compatible chains. ==Motivation== In many different protocols, the revealing of secrets is used as a settlement mechanism. HTLCC transactions are a safe way of exchanging secrets to advance the state of a debt agreement, due to the ability to recover a percentage of collateral funds from an uncooperative counterparty, and ensure principal + interest + liquidation fee is paid with a cooperative party. ==Definitions== borrower: entity that locks collateral on the Bitcoin chain and receives loan amount on principal blockchain from lender following the approval of the borrower’s borrow request lender: entity that contributes funds to the Hashed Time-Locked Principal Contract (HTLPC) on the principal blockchain, to be borrowed by the borrower upon the locking of collateral on the Bitcoin chain and the lender’s approval repay: when the borrower pays back the principal + interest before loanExpiration default: when the borrower fails to pay back the principal + interest before the loanExpiration secret: random number chosen by the borrower or lender, revealed to allow the parties to change the state of the debt agreement secretHash: hash of the secret, used in the construction of HTLCC SecretA1: secret generated by the borrower, used to prove that the borrower has withdrawn the loan SecretA2: secret generated by the borrower, used to allow the bidder to withdraw the liquidated collateral funds SecretB1: secret generated by the lender, used to accept the locking of collateral by borrower, enabling borrower to withdraw the loan amount SecretB2: secret generated by the lender, used to refund themselves in the event they aren't satisfied with borrower’slocking of collateral. Also used to accept borrower’s repayment of principal plus interest SecretB3: secret generated by the lender, used to allow the bidder to withdraw the liquidated collateral funds SecretC: secret generated by the bidder, used to accept the signatures of the borrower and lender for authorizing the liquidation of collateral loan expiration num: timestamp before which the borrower must repay the loan; or otherwise risk the liquidation or seizure of their collateral bidding expiration num: timestamp that determines the amount of time allocated to bidding before seizure period occurs seizure expiration num: timestamp that determines the amount of time during which the lender can seize funds within the Seizable Collateral P2SH, after which the borrower can refund their corresponding amount of the collateral they are entitled to (ie. either just the funds within the Refundable Collateral P2SH, or both the Refundable Collateral and Seizable Collateral in the event where the lender failed to seize). ===Approve Period=== During this time, the lender deploys the HTLPC on the principal blockchain. Following this, the borrower locks their collateral on the Bitcoin blockchain in a HTLCC. The lender then either reveals secretB1 to signify that they are satisfied with the collateral, and the borrower can withdraw the loan by revealing secretA1. If the lender is not satisfied with the collateral locked by the borrower, the lender can refunds their loan amount by revealing secretB2, which will subsequently allow the borrower to refund the collateral amount they deposited. ===Loan Period=== Once the borrower has withdrawn the loan amount, the Loan Period begins. Once the Loan Period is finished, the borrower is expected to repay the loan. If they do, the lender can then accept the repayment by revealing secretB2, enabling the borrower to refund their collateral amount. In the case that the borrower defaults or does not repay the full principal plus interest amount, the lender can choose to not accept the loan repayment, and the parties can opt for liquidation of the collateral in the Bidding Period. ===Bidding Period=== In the case of a default or the lender not accepting the borrower repayment, the lender and borrower can opt for liquidation of the collateral through the process of third party bidders bidding on the collateral. The Bidding Period can be initiated by either the lender or the borrower. Once the bidding timeout occurs, the lender and borrower must each provide a signature, followed by secretC revealed by the winning bidder once they have checked that the signature is proper. Finally, the lender and borrower must each reveal secretA2 and secretB3 to allow the collateral to be withdrawn by the winning bidder. ===Seizure Period=== In the case that either the lender or borrower don’t accept the bid, the lender can seize a percentage of the collateral. The amount is dependent on the amount of collateral locked in the Seizable Collateral and Refundable Collateral script as described in this BIP. During this period, the borrower can also refund the funds locked in the Refundable Collateral script. ===Refund Period=== In the case that the lender does not seize the collateral locked in the Seizable Collateral script, then the borrower can refund the funds locked in the Seizable Collateral script. ==Rationale== The rational for the following script checking the length of secrets pushed to the stack that are used with OP_SHA256 in the following script OP_SIZE OP_EQUALVERIFY is to ensure that the secret size is exactly a certain number of bytes long. This is especially important when this script is used alongside the HTLPC on other chains like Ethereum where the sha256 opcode only takes up 32 bytes and disregards the rest, there is a need to ensure that the length on the Bitcoin side is 32 bytes. ==Backwards Compatibility== As this is a new standard for collateralized debt, there is no need for backward compatibility. Once this is accepted as a standard there are certain aspects of the contract that can be modified while still retaining backwards compatibility, such as removing the need to verify the size of the hash if being used with two blockchains with the same maximum block size, which would be backward compatible with the current script. ==Implementation== https://github.com/AtomicLoans/chainabstractionlayer/blob/dev/packages/bitcoin-collateral-provider/lib/BitcoinCollateralProvider.js ==Copyright== This document is dual licensed as BSD 3-clause, and Creative Commons CC0 1.0 Universal. ================================================ FILE: bip-0199.mediawiki ================================================
  BIP: 199
  Layer: Applications
  Title: Hashed Time-Locked Contract transactions
  Authors: Sean Bowe 
           Daira Hopwood 
  Comments-Summary: No comments yet.
  Comments-URI: https://github.com/bitcoin/bips/wiki/Comments:BIP-0199
  Status: Closed
  Type: Specification
  Assigned: 2017-03-27
  License: BSD-3-Clause OR CC0-1.0
==Abstract== This BIP describes a script for generalized off-chain contract negotiation. ==Summary== A Hashed Time-Locked Contract (HTLC) is a script that permits a designated party (the "seller") to spend funds by disclosing the preimage of a hash. It also permits a second party (the "buyer") to spend the funds after a timeout is reached, in a refund situation. The script takes the following form: OP_IF [HASHOP] OP_EQUALVERIFY OP_DUP OP_HASH160 OP_ELSE [TIMEOUTOP] OP_DROP OP_DUP OP_HASH160 OP_ENDIF OP_EQUALVERIFY OP_CHECKSIG [HASHOP] is either OP_SHA256 or OP_HASH160. [TIMEOUTOP] is either OP_CHECKSEQUENCEVERIFY or OP_CHECKLOCKTIMEVERIFY. ===Interaction=== * Victor (the "buyer") and Peggy (the "seller") exchange public keys and mutually agree upon a timeout threshold. Peggy provides a hash digest. Both parties can now construct the script and P2SH address for the HTLC. * Victor sends funds to the P2SH address. * Either: ** Peggy spends the funds, and in doing so, reveals the preimage to Victor in the transaction; OR ** Victor recovers the funds after the timeout threshold. Victor is interested in a lower timeout to reduce the amount of time that his funds are encumbered in the event that Peggy does not reveal the preimage. Peggy is interested in a higher timeout to reduce the risk that she is unable to spend the funds before the threshold, or worse, that her transaction spending the funds does not enter the blockchain before Victor's but does reveal the preimage to Victor anyway. ==Motivation== In many off-chain protocols, secret disclosure is used as part of a settlement mechanism. In some others, the secrets themselves are valuable. HTLC transactions are a safe and cheap method of exchanging secrets for money over the blockchain, due to the ability to recover funds from an uncooperative counterparty, and the opportunity that the possessor of a secret has to receive the funds before such a refund can occur. ===Lightning network=== In the lightning network, HTLC scripts are used to perform atomic swaps between payment channels. Alice constructs K and hashes it to produce L. She sends an HTLC payment to Bob for the preimage of L. Bob sends an HTLC payment to Carol for the same preimage and amount. Only when Alice releases the preimage K does any exchange of value occur, and because the secret is divulged for each hop, all parties are compensated. If at any point some parties become uncooperative, the process can be aborted via the refund conditions. ===Zero-knowledge contingent payments=== Various practical zero-knowledge proving systems exist which can be used to guarantee that a hash preimage derives valuable information. As an example, a zero-knowledge proof can be used to prove that a hash preimage acts as a decryption key for an encrypted sudoku puzzle solution. (See [https://github.com/zcash/pay-to-sudoku pay-to-sudoku] for a concrete example of such a protocol.) HTLC transactions can be used to exchange such decryption keys for money without risk, and they do not require large or expensive-to-validate transactions. ==Implementation== https://github.com/bitcoin/bitcoin/pull/7601 ==Copyright== This document is dual licensed as BSD 3-clause, and Creative Commons CC0 1.0 Universal. ================================================ FILE: bip-0300/images.txt ================================================ Images used as reference in the documentation. ================================================ FILE: bip-0300.mediawiki ================================================
  BIP: 300
  Layer: Consensus (soft fork)
  Title: Hashrate Escrows (Consensus layer)
  Authors: Paul Sztorc 
           CryptAxe 
  Status: Draft
  Type: Specification
  Assigned: 2017-08-14
  License: BSD-2-Clause
  Discussion: https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2017-May/014364.html
==Abstract== BIP-300 enables a new type of L2, where "withdrawals" (the L2-to-L1 txns) are governed by proof-of-work -- instead of a federation or fixed set of pubkeys. BIP-300 emphasizes slow, transparent, and auditable withdrawals that are easy for honest users to get right and hard for dishonest miners to abuse. The main design goal for BIP-300 is ''partitioning'' -- users can ignore BIP-300 txns if they wish; it makes no difference to L1 if the user validates all, some, or none of them. The second design goal is ''security'' -- users of the L2 should feel confident that, [https://www.drivechain.info/blog/fees/ if the L2 network is paying a lot of fees], then miners will want to keep it around, and the withdrawals will therefore be processed accurately. Once BIP-300 has established a "bridge" between L1 and these L2s, users can swap coins in and out instantly, only using BIP-300 for final settlement. This setup allows Bitcoin to process all the transactions in the world, of any shape or size, regardless of blocksize, node software, tech stack, or decentralization level -- all without altering L1 at all. ==Motivation== BIP-300 allows us to achieve [https://www.truthcoin.info/blog/zside-meltcast/ strong privacy], [https://www.truthcoin.info/blog/thunder/ planetary scale], and [https://www.truthcoin.info/blog/all-world-txns/ hundreds of billions of dollars in annual mining revenues], all with a [https://www.drivechain.info/blog/fees/ security model] that is [https://x.com/Truthcoin/status/1701959339508965405 much stronger than] that of the [https://www.truthcoin.info/blog/ln-blackpill/ Lightning Network]. The original motivation stretches back to Reid Hoffman, who [https://blockstream.com/2015/01/13/en-reid-hoffman-on-the-future-of-the-bitcoin-ecosystem/ wrote in 2014]: "Sidechains allow developers to add features and functionality to the Bitcoin universe without actually modifying the Bitcoin Core code...Consequently, innovation can occur faster, in more flexible and distributed ways, without losing the synergies of a common platform with a single currency." See [http://www.drivechain.info/ drivechain.info] for more information. ==Specification== ===Overview=== BIP-300 consists of six new blockchain messages: * M1. "Propose New Sidechain" * M2. "ACK Proposal" * M3. "Propose Bundle" * M4. "ACK Bundle" * M5. Deposit -- a transfer of BTC from-main-to-side * M6. Withdrawal -- a transfer of BTC from-side-to-main Nodes organize this data into [https://github.com/LayerTwo-Labs/bip300301_enforcer/blob/13a4353c39a26d9d40180ea361b7580fd682e5b5/src/bip300.rs#L79-L96 a few caches], mainly these two: * D1. "The Sidechain List" * D2. "The Withdrawal List" ==== D1 (The Sidechain List) ==== D1 is a list of active sidechains. D1 is populated via M1 and M2. Fields #9 and #10 are updated via M5 and M6. {| class="wikitable" |- style="font-weight:bold; text-align:center; vertical-align:middle;" ! Field No. ! Label ! Type ! Description / Purpose |- style="vertical-align:middle;" | 1 | Escrow Number | uint8_t | The escrow's ID number. Used to uniquely refer to each sidechain. |- | 2 | Version | int32_t | Version number. |- | 3 | Sidechain Name | string | A human-readable name of the sidechain. |- style="vertical-align:middle;" | 4 | Sidechain Description | string | A human-readable name description of the sidechain. |- style="vertical-align:middle;" | 5 | Hash1 - tarball hash | uint256 | Intended as the sha256 hash of the tar.gz of the canonical sidechain software. (This is not enforced by BIP-300, and is for human purposes only.) |- style="vertical-align:middle;" | 6 | Hash2 - git commit hash | uint160 | Intended as the git commit hash of the canonical sidechain node software. (This is not enforced by BIP-300, and is for human purposes only.) |- | 7 | Active | bool | Does this sidechain slot contain an active sidechain?
|- style="vertical-align:middle;" | 8 | Activation Status | int , int | The age of the proposal (in blocks); and the number of "fails" (a block that does NOT ack the sidechain). This is discarded after the sidechain activates. |- style="vertical-align:middle;" | 9 | "CTIP" -- "TxID" | uint256 | A UTXO that holds the sidechain's money. (Part 1 of 2). |- style="vertical-align:middle;" | 10 | "CTIP" -- "vout" | int32_t | A UTXO that holds the sidechain's money. (Part 2 of 2). |} ==== D2 (The Withdrawal List) ==== Withdrawals are transactions that remove coins "from" L2 (i.e., from the BIP-300 locked UTXO), and place them back on L1. Each BIP-300 withdrawal can pay out up to 6,000 withdrawals, and only one withdrawal can succeed at a time (per L2). Therefore, since all L2 users share the same large withdrawal-event, on L1 we call these withdrawals "bundles". D2 is driven by M3, M4, M5, and M6. Those messages enforce the following principles: # The database has a canonical order (first come first serve). # From one block to the next, every "Blocks Remaining" field decreases by 1. # When "Blocks Remaining" reaches zero, the bundle is removed. # From one block to the next, the value in "ACKs" may either increase or decrease, by a maximum of 1 (see M4). # If a bundle's "ACKs" reach 13150 or greater, it "succeeds" and its corresponding M6 message can be included in a block. # If the M6 of a bundle is paid out, it is also removed. # If a bundle cannot possibly succeed ( 13150 - "ACKs" > "Blocks Remaining" ), it is removed immediately. {| class="wikitable" ! Field No. ! Label ! Type ! Description / Purpose |- | 1 | Sidechain Number | uint8_t | Links the withdrawal-request to a specific hashrate escrow. |- | 2 | Bundle Hash | uint256 | A withdrawal attempt. Specifically, it is a "blinded transaction id" (i.e., the double-Sha256 of a txn that has had two fields zeroed out, see M6) of a txn which could withdraw funds from a sidechain. |- | 3 | Work Score (ACKs) | uint16_t | How many miner upvotes a withdrawal has. Starts at 0. Fastest possible rate of increase is 1 per block. |- | 4 | Blocks Remaining | uint16_t | How long this bundle has left to live (measured in blocks). Starts at 26,300 and counts down. |} === M1 -- Propose Sidechain === New sidechains are proposed with M1, and ACKed with M2. M1 is a coinbase OP Return output containing the following: 1-byte - OP_RETURN (0x6a) 4-byte - Message header (0xD5E0C4AF) N-byte - The serialization of the sidechain. 1-byte nSidechain 4-byte nVersion x-byte title x-byte description 32-byte hashID1 20-byte hashID2 M1 is invalid if: * It would add a duplicate entry to D1. * There is already an M1 in this block. * The sidechain serialization does not parse. Otherwise: * A new entry is added to D1, whose initial Activation Status is (age=0, fails=0). === M2 -- ACK Sidechain Proposal === M2 is a coinbase OP Return output containing the following: 1-byte - OP_RETURN (0x6a) 4-byte - Message header (0xD6E1C5BF) 32-byte - the sha256D hash of sidechain's serialization M2 is ignored if it doesn't parse, or if it is for a sidechain that doesn't exist. M2 is invalid if: * An M2 is already in this block. * It tries to ACK two different M1s for the same slot. Otherwise: * The sidechain is "ACK"ed and does NOT get a "fail" for this block. (As it otherwise would.) A sidechain fails to activate if: * If the slot is unused: during the next 2016 blocks, it accumulates 1008 fails (i.e., 50% hashrate threshold). * If the slot is in use: during the next 26,300 blocks, it accumulates 13,150 fails (i.e., 50% hashrate threshold). ( Thus we can overwrite a used sidechain slot. BIP-300 sidechains are already vulnerable to one catastrophe per 13150 blocks (the invalid withdrawal), so this slot-overwrite option does not change the security assumptions. ) Otherwise, the sidechain activates (Active is set to TRUE). === Withdrawing in Bundles === Sidechain withdrawals take the form of "bundles" -- named because they "bundle up" many individual withdrawal-requests into a single rare L1 transaction. On the L2 side, individual withdrawal requests are periodically combined into a single CoinJoin-like withdrawal bundle. This bundle is hashed [https://github.com/LayerTwo-Labs/bip300301_messages/blob/398b224981c7c236c8354704e655996d33685149/src/lib.rs#L374C1-L419C2 in a particular way] (on both L2 and L1) -- this "blinded hash" commits to its own L1 fee, but (notably) it does not commit to its first tx-input (in that way, it is like [https://github.com/bitcoin/bips/blob/master/bip-0118.mediawiki BIP-118]). This hash is what L1 miners will slowly ACK over 3-6 months, not the M6 itself (nor any sidechain data, of course). A bundle will either pay all its withdrawals out (via M6), or fail (and pay nothing out for anyone). === M3 -- Propose Bundle === M3 is a coinbase OP Return output containing the following: 1-byte - OP_RETURN (0x6a) 4-byte - Commitment header (0xD45AA943) 32-byte - The bundle hash, to populate a new D2 entry 1-byte - nSidechain (the slot number) M3 is ignored if it does not parse, or if it is for a sidechain that doesn't exist. M3 is invalid if: * This block already has an M3 for that nSidechain. * A bundle with this hash is already in D2. * A bundle with this hash already paid out. * A bundle with this hash was rejected in the past. Otherwise: M3 adds an entry to D2, with initial ACK score = 1 and initial Blocks Remaining = 26,299. (Merely being added to D2, does count as your first upvote.) === M4 -- ACK Bundle(s) === Once a bundle is in D2, how can we give it enough ACKs to make it valid? M4 is a coinbase OP Return output containing the following: 1-byte - OP_RETURN (0x6a) 4-byte - Commitment header (0xD77D1776) 1-byte - Version n-byte - The "upvote vector" -- describes which bundle-choice is "upvoted", for each sidechain. The M4 message will be invalid (and invalidate the block), if: * It tries to upvote a bundle that doesn't exist. (For example, trying to upvote the 7th bundle on sidechain #2, when sidechain #2 has only three bundles.) * There are no bundles at all, from any sidechain. If M4 is NOT present in a block, then it is treated as an "abstain" for all sidechains. If M4 is present and valid: each withdrawal-bundle that is ACKed, will gain one upvote. Each sidechain always has two "virtual bundles" -- an "abstain" bundle (0xFF), and an "alarm" bundle (0xFE). Abstain leaves the ACK count unchanged, and alarm reduces all ACK counts of all bundles by 1. Any bundle which fails to receive a vote, is downvoted (and loses 1 ACK). If a sidechain has no pending bundles, then it is skipped over when M4 is created and parsed. ==== Examples ==== To upvote the 7th bundle on sidechain #1, and upvote the 4th bundle on sidechain #2, the upvote vector would be { 07, 04 }. And M4 would be [0x6A,D77D1776,00,0006,0003]. If block 900,000 has D2 of... {| class="wikitable" |- ! SC# ! Bundle Hash ! ACKs ! Blocks Remaining |- | 1 | h1 | 45 | 22,109 |- | 1 | h2 | 12 | 22,008 |- | 2 | h3 | 13 | 22,999 |- | 2 | h4 | 8 | 23,550
|- | 2 | h5 | 2 | 22,560 |} ...and then D2 wants to become: {| class="wikitable" |- ! SC# ! Bundle Hash ! ACKs ! Blocks Remaining |- | 1 | h1 | 46 | 22,108 |- | 1 | h2 | 11 | 22,007 |- | 2 | h3 | 12 | 22,998 |- | 2 | h4 | 9 | 23,549
|- | 2 | h5 | 1 | 22,559 |} ... then M4 would have been [0x6A,D77D1776,00,0000,0001]. ==== Saving Space ==== The version number allows us to shrink the upvote vector in many cases. Version 0x00 omits the upvote vector entirely (i.e., 6 bytes for the whole M4) and sets this block's M4 equal to the previous block's M4. Version 0x01 uses 1 byte per sidechain, and can be used while all ACKed withdrawals have an index <256 (i.e., 99.99%+ of the time). Version 0x02 uses 2 bytes per sidechain, but it always works, even in astronomically unlikely cases (such as when >1 sidechains have >256 bundle candidates). Version 0x03 omits the upvote vector, and instead upvotes only those withdrawals that are leading their rivals by at least 50 votes. For example, an upvote vector of { 2 , N/A, 1 } would be represented as [0x6A,D77D1776,01,01,00]. It means: "upvote the second bundle in sidechain #1; and the first bundle in sidechain #3" (iff sidechains #2 has no bundles proposed). An upvote vector of { N/A, N/A, 4 } would be [0x6A,D77D1776,01,03]. === M5 -- Deposit BTC (from L1 to L2) === Finally, we describe Deposits (M5) and Withdrawals (M6). These are not coinbase outputs, they are txns on L1. We call a transaction "M5" if it spends from the escrow output and '''increases''' the quantity of coins. Conversely, we call a transaction "M6" if it spends from the escrow output and '''decreases''' the quantity of coins. See [https://github.com/LayerTwo-Labs/bip300301_enforcer/blob/13a4353c39a26d9d40180ea361b7580fd682e5b5/src/bip300.rs#L462C1-L462C47 here]. Every time a deposit/withdrawal is made, the old UTXO is spent and a single new UTXO is created. (Deposits/Withdrawals never cause UTXO bloat.) At all times, the specific treasury UTXO ("CTIP") of each sidechain is cached in D1 (above). Every M5 is valid, as long as: * It has exactly one OP_DRIVECHAIN output -- this becomes the new CTIP. * The new CTIP has '''more''' coins in it, than before. === M6 -- Withdraw BTC (from L2 to L1) === M6 is invalid if: * The blinded hash of M6 does NOT match one of the approved bundle-hashes. (In other words: M6 must first be approved by 13,150 upvotes.) * The first output of M6 is NOT an OP_DRIVECHAIN. (This OP_DRIVECHAIN becomes the new CTIP. In other words: all non-withdrawn coins are paid back to the sidechain.) * The second output is NOT a zero-value OP_RETURN script of exactly 10 bytes, of which 8 bytes are a serialized Bitcoin amount. * The txn fee of M6 is NOT exactly equal to the amount of the previous bullet point. * There are additional OP_DRIVECHAIN outputs after the first one. Else, M6 is valid -- and the funds are withdrawn. (The point of the latter two bullet points, is to allow the bundle hash to cover the L1 transaction fee.) ===OP_DRIVECHAIN=== This proposal adds a single new opcode, OP_DRIVECHAIN, which has strict semantics for usage. OP_NOP5 (0xb4) is redefined as OP_DRIVECHAIN if and only if the entire script is OP_DRIVECHAIN followed by a single-byte push and OP_TRUE (exactly 4 bytes). The single-byte push contains the sidechain number. Note that this is not a "script number", and cannot be OP_1..OP_16 or any other kind of push; it is also unsigned, and must not be padded even if over sidechain number 127. The final OP_TRUE is to ensure this change remains a softfork: without it, sidechain numbers 0 and 128 would cause the legacy script interpreter to fail. If an OP_DRIVECHAIN input is spent, the additional rules for M5 or M6 (see above) must be enforced. ==Backward compatibility== This soft fork can be deployed without modifying Bitcoin Core at all (i.e., via [https://bip300cusf.com/ CUSF]). ==Deployment== This BIP deploys when/if >51% hashrate runs [https://github.com/LayerTwo-Labs/bip300301_enforcer/ the enforcer client]. Ideally, a critical mass of users would also run the enforcer client -- this would strongly dissuade miners from ever de-activating it. ==Reference Implementation== The enforcer is [https://github.com/LayerTwo-Labs/bip300301_enforcer/ here]. Also, several example L2s are [https://releases.drivechain.info/ here]. ==Copyright== This BIP is licensed under the BSD 2-clause license. ================================================ FILE: bip-0301.mediawiki ================================================
  BIP: 301
  Layer: Consensus (soft fork)
  Title: Blind Merged Mining (Consensus layer)
  Authors: Paul Sztorc 
           CryptAxe 
  Status: Draft
  Type: Specification
  Assigned: 2019-07-23
  License: BSD-2-Clause
==Abstract== Blind Merged Mining (BMM) allows SHA-256d miners to collect transaction fee revenue from other blockchains, without running any new software (i.e., without "looking" at those alt-chains, hence "blind"). Instead, this block-assembly work is done by alt-chain users. They choose the alt-chain block, and what txns go in it, the fees etc. Simultaneously, these users "bid" on L1 to win the right to be the sole creator of the alt-chain block. BIP-301 ensures that L1 miners only accept one bid (per 10 minutes, per L2 category), instead of taking all of them (which is what they would ordinarily do). ==Motivation== "Merged-Mining" (MM) allows miners to reuse their hashing work to secure other chains (for example, as in Namecoin). However, traditional MM has two drawbacks: # Miners must run a full node of the other chain(s). (Thus, they must run "non-Bitcoin" software which may be buggy.) # Miners are paid on the other chain, in Alt-currency. (Miners who MM Namecoin, will earn NMC.) ==Notation and Example== We use notation side:\* and main:\* in front of otherwise ambiguous words (such as "block", "node", or "chain"), to distinguish the mainchain version from its sidechain/alt-chain counterpart. We name all sidechain users "Simon", and name all mainchain miners "Mary". Furthermore, here is an example of BIP-301 in use. Imagine that a side:block contains 20,000 txns, each paying a $0.10 fee; therefore, the side:block is worth $2000 of fee revenue. In BIP-301, the sidechain's coinbase txn will pay this $2000 to "Simon". Simon does no hashing, but instead makes one L1 txn paying $1999 to the L1 miners ("Mary"). Thus, Mary ends up with all of the fee revenue, even though she didn't do anything on the sidechain. {| class="wikitable" |- ! colspan="3" | Upon finding a sidechain block worth $2000... |- style="font-weight:bold; text-decoration:underline;" | Item | Layer1 Miner ("Mary") | Sidechain User ("Simon") |- | Runs a sidechain node? | No | Yes |- | How much hashing? | 100% | 0% |- | Coins collected, on Layer2 | $0 | $2000 |- | Coins paid out, on Layer1 | $0 | $1999 |- | Coins rec'd, on Layer1 | $1999 | $0 |- | d(Net Worth) | +$1999 | +$1 |} BIP-301 makes this specialization-of-labor trustless on L1. If Mary takes Simon's money, then she must let Simon control the side:block. ==Specification== Each candidate for next side:block is defined by its unique side:blockhash "h*". (Even if the entire rest of the L2 block is identical, different Simons will have different side:coinbases and therefore different h*.) BIP-301 consists of two messages: "BMM Accept" and "BMM Request". # "BMM Accept" -- A coinbase output in L1, which contains h*. Mary can only choose one h* to endorse. # "BMM Request" -- A transaction where Simon offers to pay Mary, if (and only if) Mary's L1 block contains Simon's h*. As a miner, Mary controls the main:coinbase, so she may select any h*. Her selection determines which side:block is "found" -- and which associated BMM Request she can collect. === BMM Accept === To "Accept" a BMM proposal (endorsing Simon's side:block, and allowing Mary to accept Simon's money later in the block), Mary places an OP_RETURN output into the main:coinbase as follows:
    1-byte - OP_RETURN (0x6a)
    4-bytes - Message header (0xD1617368)
    1-byte - Sidechain number (0-255)
    32-bytes - h* (obtained from Simon)
[https://github.com/LayerTwo-Labs/bip300301_messages/blob/dd26518ff9505ea9088436797171799f359d0076/src/lib.rs#L256-L268 Code details here]. If these OP_RETURN outputs are not present, then no Requests were accepted. (And, Mary would get no money from Requests.) It is possible for Mary and Simon to be the same person. They would trust each other completely, so the BMM process would stop here. There would only be Accepts; Requests would be unnecessary. When Simon and Mary are different people, Simon will need to use BMM Requests. === BMM Request === Simon will use BMM Requests to buy the "right" to find a sidechain block, from Mary. For each side:block that Simon wants to attempt, he broadcasts a txn containing the following as an OP_RETURN:
    1-byte - OP_RETURN (0x6a)
    3-bytes - Message header (0x00bf00)
    1-byte - Sidechain number (0-255)
    32-bytes  - h* (obtained from L2 node)
    32-bytes  - prevMainBlock (the blockhash of the previous main:block)
h* is chosen by Simon to correspond to the side:block he wants to mine on the alt-chain. nSidechain is the number assigned to the sidechain/alt-chain when it was created. This txn is invalid if it fails any of the following checks: # Each "BMM Request", must match one corresponding "BMM Accept" (previous section). # Only one BMM Request is allowed in each main:block, per nSidechain. In other words, if 700 users broadcast BMM Requests for sidechain #4, then the main:miner must single out one BMM_Request_4 to include in this L1 block. # The 32-bytes of prevMainBlock must match the previous main:blockhash. Thus, Simon's txns are only valid for the current block, in the block history that he knows about. Most BMM Request txns will never make it into a block. Simon will make many BMM Requests, but only one will be accepted. Since only one BMM Request can enter the L1 block, Simon may feel comfortable making multiple offers all day long. This means Mary has many offers to choose from, and can choose the one that pays her the most. This BIP allows BMM Requests to take place over Lightning. One method is [https://www.drivechain.info/media/bmm-note/bmm-lightning/ here]. (BMM Accepts cannot be over LN, since they reside in main:coinbase txns.) ==Backward compatibility== This soft fork can be deployed without modifying Bitcoin Core at all (ie, via [https://bip300cusf.com/ CUSF]). ==Deployment== This BIP deploys when/if >51% hashrate runs [https://github.com/LayerTwo-Labs/bip300301_enforcer/ the enforcer client]. Ideally, a critical mass of users would also run the enforcer client -- this would strongly dissuade miners from ever de-activating it. ==Reference Implementation== The enforcer is [https://github.com/LayerTwo-Labs/bip300301_enforcer/ here]. Also, several example L2s using BIP-301 are [https://releases.drivechain.info/ here]. ==Copyright== This BIP is licensed under the BSD 2-clause license. ================================================ FILE: bip-0310.mediawiki ================================================
  BIP: 310
  Layer: Applications
  Title: Stratum protocol extensions
  Authors: Pavel Moravec 
           Jan Čapek 
  Status: Draft
  Type: Informational
  Assigned: 2018-03-10
  License: BSD-3-Clause OR CC0-1.0
==Abstract== This BIP provides a generic mechanism for specifying stratum protocol extensions. At the same time, one of the important extensions that is specified by this BIP is configuration of bits for "version rolling" in nVersion field of bitcoin block header. The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED", "MAY", and "OPTIONAL" in this document are to be interpreted as described in RFC 2119. ==Motivation== The initial motivation for specifying some general support for stratum protocol extensions was a need to allow miners to do so called "version rolling", changing value in the first field of the Bitcoin block header. Version rolling is backwards incompatible change to the stratum protocol because the miner couldn't communicate different block version value to the server in the original version of the stratum protocol. Similarly, a server couldn't communicate safe bits for rolling to a miner. So both miners and pools need to implement some protocol extension to support version rolling. Typically, if a miner sends an unknown message to a server, the server closes the connection (not all implementations do that but some do). So it is not very safe to try to send unknown messages to servers. We can use this opportunity to make one backwards incompatible change to the protocol to support multiple extensions in the future. In a way that a miner can advertise its capabilities and at the same time it can request some needed features from the server. It is preferable that the same mechanism for feature negotiation can be used for not yet known features. It SHOULD be easy to implement in the mining software too. We introduce one new message to the stratum protocol ('''"mining.configure"''') which handles the initial configuration/negotiation of features in a generic way. So that adding features in the future can be done without a necessity to add new messages to stratum protocol. Each extension has its unique string name, so called '''extension code'''. ==Specification== Currently, the following extensions are defined: * '''"version-rolling"''' * '''"minimum-difficulty"''' * '''"subscribe-extranonce"''' ===Additional data types=== The following names are used as type aliases, making the message description easier. * '''TMask''' - case independent hexadecimal string of length 8, encoding an unsigned 32-bit integer (~[0-9a-fA-F]{8}) * '''TExtensionCode''' - non-empty string with a value equal to the name of some protocol extension. * '''TExtensionResult''' - true / false / ''String''. ** true = The requested feature is supported and its configuration understood and applied. ** false = The feature is not supported or unknown. ** ''String'' = Error message containing information about what went wrong. ===Request "mining.configure"=== This message (JSON RPC Request) SHOULD be the '''first message''' sent by the miner after the connection with the server is established. The client uses the message to advertise its features and to request/allow some protocol extensions. The reason for it being the first is that we want the implementation and possible interactions to be as easy and simple as possible. An extension can define explicitly what does a repeated configuration of that extension mean. Each extension code provides a namespace for its extension parameters and extension return values. By convention, the names are formed from extension codes by adding "." and a parameter name. The same applies for the return values, which are transferred in a result map too. E.g. "version-rolling.mask" is the name of the parameter "mask" of extension "version-rolling". '''Parameters''': * '''extensions''' (REQUIRED, List of ''TExtensionCode'') ::- Each string in the list MUST be a valid extension code. The meaning of each code is described independently as part of the extension definition. A miner SHOULD advertise all its available features. * '''extension-parameters''' (REQUIRED, ''Map of (String -> Any)'') ::- Parameters of the requested/allowed extensions from the first parameter. '''Return value''': * ''Map of (String -> Any)'' ::- Each code from the '''extensions''' list MUST have a defined return value (''TExtensionCode'' -> ''TExtensionResult''). This way the miner knows if the extension is activated or not. E.g. {"version-rolling":false} for unsupported version rolling. ::- Some extensions need additional information to be delivered to the miner. The return value map is used for this purpose. Example request (new-lines added):
 {"method": "mining.configure",
  "id": 1,
  "params": [["minimum-difficulty", "version-rolling"],
	     {"minimum-difficulty.value": 2048,
	      "version-rolling.mask": "1fffe000", "version-rolling.min-bit-count": 2}]}
(The miner requests extensions "version-rolling" and "minimum-difficulty". It sets the parameters according to the extensions' definitions.) Example result (new-lines added):
 {"error": null,
  "id": 1,
  "result": {"version-rolling": true,
	     "version-rolling.mask": "18000000",
	     "minimum-difficulty": true}}
=Defined extensions= ==Extension "version-rolling"== This extension allows the miner to change the value of some bits in the version field in the block header. Currently there are no standard bits used for version rolling so they need to be negotiated between a miner and a server. A miner sends the server a mask describing bits which the miner is capable of changing. 1 = changeable bit, 0 = not changeable (miner_mask) and a minimum number of bits that it needs for efficient version rolling. A server typically allows you to change only some of the version bits (server_mask) and the rest of the version bits are fixed. E.g. because the block needs to be valid or some signaling is in place. The server responds to the configuration message by sending a mask with common bits intersection of the miner's mask and its a mask (response = server_mask & miner_mask) Example request (a miner capable of changing any 2 bits from a 16-bit mask): {"method": "mining.configure", "id": 1, "params": [["version-rolling"], {"version-rolling.mask": "1fffe000", "version-rolling.min-bit-count": 2}]} Example result (success): {"error": null, "id": 1, "result": {"version-rolling": true, "version-rolling.mask": "18000000"}} Example result (unknown extension): {"error": null, "id": 1, "result": {"version-rolling": false}} '''Extension parameters''': * '''"version-rolling.mask"''' (OPTIONAL, ''TMask'', default value "ffffffff") ::- Bits set to 1 can be changed by the miner. This value is expected to be stable for the whole mining session. A miner doesn't have to send the mask, in this case a default full mask is used. * '''"version-rolling.min-bit-count"''' (REQUIRED, ''Integer'', >= 0) ::- The miner also provides a minimum number of bits that it needs for efficient version rolling in hardware. Note that this parameter provides important diagnostic information to the pool server. If the requested bit count exceeds the limit of the pool server, the miner always has the chance to operate in a degraded mode without using full hashing power. The pool server SHOULD NOT terminate miner connection if this rare mismatch case occurs. '''Extension return values''': * '''"version-rolling"''' (REQUIRED, ''TExtensionResult'') ::- When responded with true, the server will accept new parameter of '''"mining.submit"''', see later. * '''"version-rolling.mask"''' (REQUIRED, ''TMask'') ::- Bits set to 1 are allowed to be changed by the miner. If a miner changes bits with mask value 0, the server will reject the submit. ::- The server SHOULD return the largest mask possible (as many bits set to 1 as possible). This can be useful in a mining proxy setup when a proxy needs to negotiate the best mask for its future clients. There is a [https://github.com/bitcoin/bips/pull/661/files Draft BIP] describing available nVersion bits. The server SHOULD pick a mask that preferably covers all bits specified in the BIP. ===Notification '''"mining.set_version_mask"'''=== Server notifies the miner about a new mask valid for the connection. This message can be sent at any time after the successful setup of the version rolling extension by the "mining.configure" message. The new mask is valid '''immediately''', so that the server doesn't wait for the next job. '''Parameters''': * ''mask'' (REQUIRED, ''TMask''): The meaning is the same as the '''"version-rolling.mask"''' return parameter. Example: {"params":["00003000"], "id":null, "method": "mining.set_version_mask"} ===Changes in request '''"mining.submit"'''=== Immediately after successful activation of the version-rolling extension (result to '''"mining.configure"''' sent by server), the server MUST accept an additional parameter of the message '''"mining.submit"'''. The client MUST send one additional parameter, '''version_bits''' (6th parameter, after ''worker_name'', ''job_id'', ''extranonce2'', ''ntime'' and ''nonce''). '''Additional parameters''': * ''version_bits'' (REQUIRED, ''TMask'') - Version bits set by miner. ::- Miner can set only bits corresponding to the set bits in the last received mask from the server either as response to "mining.configure" or "mining.set_version_mask" notification (last_mask). This must hold: version_bits & ~last_mask == 0 ::- The server computes ''nVersion'' for the submit as follows: nVersion = (job_version & ~last_mask) | (version_bits & last_mask) where job_version is the block version sent to miner as part of job with id job_id. ==Extension "minimum-difficulty"== This extension allows miner to request a minimum difficulty for the connected machine. It solves a problem in the original stratum protocol where there is no way how to communicate hard limit of the connected device. '''Extension parameters''': * '''"minimum-difficulty.value"''' (REQUIRED, ''Integer/Float'', >= 0) ::- The minimum difficulty value acceptable for the miner/connection. The value can be 0 for essentially disabling the feature. '''Extension return values''': * '''"minimum-difficulty"''' (REQUIRED, ''TExtensionResult'') ::- Whether the minimum difficulty was accepted or not. ::- This extension can be configured multiple times by calling "mining.configure" with "minimum-difficulty" code again. ==Extension "subscribe-extranonce"== Parameter-less extension. Miner advertises its capability of receiving message '''"mining.set_extranonce"''' message (useful for hash rate routing scenarios). ==Extension "info"== Miner provides additional text-based information. '''Extension parameters''': * '''"info.connection-url"''' (OPTIONAL, ''String'') ::- Exact URL used by the mining software to connect to the stratum server. * '''"info.hw-version"''' (OPTIONAL, ''String'') ::- Manufacturer specific hardware revision string. * '''"info.sw-version"''' (OPTIONAL, ''String'') ::- Manufacturer specific software version * '''"info.hw-id"''' (OPTIONAL, ''String'') ::- Unique identifier of the mining device ==Compatibility== Currently, there is a similar protocol feature '''mining.capabilities''' that was intended for various protocol extensions. However, '''mining.configure''' is incompatible with this feature as it requires a server response confirming all accepted/negotiated extensions. The reason why we made it incompatible is that '''mining.capabilities''' request has no associated response. ==Copyright== This document is dual licensed as BSD 3-clause, and Creative Commons CC0 1.0 Universal. ================================================ FILE: bip-0320.mediawiki ================================================
  BIP: 320
  Title: nVersion bits for general purpose use
  Authors: BtcDrak 
  Status: Draft
  Type: Specification
  Assigned: 2018-03-01
  License: BSD-3-Clause OR CC0-1.0
==Abstract== This BIP reserves 16 bits of the block header nVersion field for general purpose use and removes their meaning for the purpose of version bits soft-fork signalling. The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED", "MAY", and "OPTIONAL" in this document are to be interpreted as described in RFC 2119. ==Motivation== There are a variety of things that miners may desire to use some of the nVersion field bits for. However, due to their use to coordinate miner activated soft-forks, full node software will generate false warnings about unknown soft forks if those bits are used for non soft fork signalling purposes. By reserving bits from the nVersion field for general use, node software can be updated to ignore those bits and therefore will not emit false warnings. Reserving 16 bits for general use leaves enough for 13 parallel soft-forks using version bits. ===Example Uses=== The following are example cases that would benefit from using some of the bits from the nVersion field. This list is not exhaustive. Bitcoin mining hardware currently can exhaust the 32 bit nonce field in less than 200ms requiring the controller to distribute new jobs very frequently to each mining chip consuming a lot of bandwidth and CPU time. This can be greatly reduced by rolling more bits. Rolling too many bits from nTime is not ideal because it may distort the timestamps over a longer period. Version-rolling AsicBoost requires two bits from the nVersion field to calculate 4-way collisions. Any two bits can be used and mining equipment can negotiate which bits are to be used with mining pools via the Stratum "version-rolling" extension. ==Specification== Sixteen bits from the block header nVersion field, starting from 13 and ending at 28 inclusive (0x1fffe000), are reserved for general use and removed from BIP8 and BIP9 specifications. A mask of 0xe0001fff should be applied to nVersion bits so bits 13-28 inclusive will be ignored for soft-fork signalling and unknown soft-fork warnings. This specification does not reserve specific bits for specific purposes. ==Reference Implementation== https://github.com/btcdrak/bitcoin/commit/d12516e136d4a8952904a13eedc9f4225f35dc3b ==Backwards Compatibility== Non-upgraded nodes will interpret the reserved bits of this proposal as signals for soft forks, and may additionally activate the warning system for unknown soft forks. This proposal does not require a soft fork to implement. At the time of writing no known soft forks are pending using any of 16 bits reserved in this BIP, and given that a non-trivial percentage of the hashrate is already making uses of those bits, future soft forks SHOULD NOT utilise those bits for activation signalling. ==Acknowledgements== Timo Hanke and Sergio Lerner for originally proposing 15-bit extra nNonce2. ==References== [[bip-0008.mediawiki|BIP8]] [[bip-0009.mediawiki|BIP9]] [https://arxiv.org/pdf/1604.00575.pdf AsicBoost white paper] [https://github.com/BlockheaderNonce2/bitcoin/wiki Blockheader Extra nNonce2 proposal] [https://github.com/slushpool/stratumprotocol/blob/master/stratum-extensions.mediawiki Stratum protocol extension BIP for version-rolling] ==Copyright== This document is dual licensed as BSD 3-clause, and Creative Commons CC0 1.0 Universal. ================================================ FILE: bip-0321.mediawiki ================================================
  BIP: 321
  Layer: Applications
  Title: URI Scheme
  Authors: Matt Corallo 
  Status: Complete
  Type: Specification
  Assigned: 2024-11-15
  License: BSD-2-Clause
  Replaces: 21
== Copyright == This BIP is licensed under the BSD 2-clause license. == Abstract == This BIP proposes a URI scheme for describing Bitcoin payment instructions. == Motivation == The purpose of this URI scheme is to enable users to easily make payments by simply clicking links on webpages or scanning QR Codes. This BIP is a modification and intended replacement of [[bip-0021.mediawiki|BIP 0021]] to add information about the modern usage of bitcoin: URIs (including standard query parameters and modern address types) as well as provide forward-looking guidance on how to incorporate new payment instructions. It further adds an optional extension to provide the payment initiator with proof of payment. BIP 21 was based on BIP 20, which was, in turn based on an earlier document by Nils Schneider. == Specification == === General rules for handling (important!) === Bitcoin clients MUST NOT act on URIs without getting the user's authorization. They SHOULD require the user to manually approve each payment individually, though in some cases they MAY allow the user to automatically make this decision. === Operating system integration === Graphical bitcoin clients SHOULD register themselves as the handler for the "bitcoin:" URI scheme by default, if no other handler is already registered. If there is already a registered handler, they MAY prompt the user to change it once when they first run the client. === General Format === Bitcoin URIs follow the general format for URIs as set forth in RFC 3986. The path component consists of a bitcoin address, and the query component provides additional payment options. Elements of the query component may contain characters outside the valid range. These must first be encoded according to UTF-8, and then each octet of the corresponding UTF-8 sequence must be percent-encoded as described in RFC 3986. === ABNF grammar === bitcoinurn = "bitcoin:" [ bitcoinaddress ] [ "?" bitcoinparams ] bitcoinaddress = *base58 / *bech32 / *bech32m bitcoinparams = bitcoinparam [ "&" bitcoinparams ] bitcoinparam = [ amountparam / labelparam / messageparam / responseparam / otherparam / reqparam ] amountparam = "amount=" *digit [ "." *digit ] labelparam = "label=" *qchar messageparam = "message=" *qchar responseparam = [ "req-" ] "pop=" *qchar otherparam = qchar *qchar [ "=" *qchar ] reqparam = "req-" qchar *qchar [ "=" *qchar ] Here, "qchar" corresponds to valid characters of an RFC 3986 URI query component, excluding the "=" and "&" characters, which this BIP takes as separators. The scheme component ("bitcoin:") is case-insensitive, and implementations must accept any combination of uppercase and lowercase letters. The query parameter keys are also case-insensitive. Query parameter values and bitcoin address fields may be case-sensitive depending on their content. Multiple query parameters with the same key MAY be included for query parameters representing payment instructions. Multiple query parameters with the same key MUST NOT be included for keys "label", "message", or "pop". Multiple query parameters with the same key for other keys MUST be allowed for unknown query parameters. Future query parameter keys may or may not allow for duplicate parameters. === Bitcoin Address === The bitcoinaddress body MUST be either a base58 P2SH or P2PKH address, bech32 Segwit version 0 address, bech32m Segwit address, or empty. Future address formats SHOULD instead be placed in query keys as optional payment instructions to provide backwards compatibility during upgrade cycles. The bitcoinaddress part of the URI MAY be left empty if there is at least one payment instruction provided in a query parameter, allowing for recipients wishing to avoid a standard on-chain fallback. === Query Keys === The following keys are defined generally and apply to any URI regardless of payment instructions: *label: Label for the recipient (e.g. name of receiver) *message: message that describes the transaction to the user ([[#Examples|see examples below]]) *pop: a URI which the Bitcoin Wallet may return to in order to provide the application which initiated the payment with proof that a payment was completed. The following keys are currently defined for payment instructions of various forms: *lightning: Lightning BOLT 11 invoices *lno: Lightning BOLT12 offers *pay: [[bip-0351.mediawiki|BIP 351 Private Payment addresses]] *sp: [[bip-0352.mediawiki|BIP 352 Silent Payment addresses]] New payment instructions using bech32 or bech32m encodings SHOULD reuse their address format's Human Readable Part as the parameter key. ==== Transfer amount ==== If an amount is provided, it MUST be specified in decimal BTC. All amounts MUST contain no commas and use a period (.) as the separating character to separate whole numbers and decimal fractions. I.e. amount=50.00 or amount=50 is treated as 50 BTC, and amount=50,000.00 is invalid. === Proof of Payment === The URI MAY include a "pop" (or "req-pop") parameter whose value can be used to build a URI which the wallet application can, after payment completes, "open" to provide proof the payment was completed or other information about the payment. The value of a "pop" (or "req-pop") parameter shall be a percent-encoded (per RFC 3986 section 2.1) URI prefix. The wallet application, if it supports providing payment information SHOULD percent-decode the provided URI once, append the query parameter key from which the payment instructions used were read, append a single =, and finally append the Payment Information to the resulting URI and open it with the default system handler for the URI. For payment instructions read from the body of the URI, "onchain" SHALL be used in place of the key. A wallet MUST validate that the provided URI's scheme is not (case-insensitive) "http", "https", "file", "javascript", "mailto" or any other scheme which will open in a web browser prior to opening it. If a wallet will not open the pop scheme (either because it does not support returning payment information for the selected payment method or because it uses a URI scheme which should not be opened) and the parameter was passed as a "req-pop" parameter, the wallet MUST NOT initiate payment. For payments made using an on-chain transaction, the Payment Information shall be the full (including witness data) Bitcoin transaction as it was broadcasted to the Bitcoin network, encoded in hex. For payments made using a BOLT 11 invoice (communicated via the `lightning` parameter), the Payment Information shall be the hex-encoded payment preimage. Other payment schemes will define their own Payment Information format. This BIP may be updated from time to time with Payment Information formats for other payment schemes. == Rationale == === Payment identifiers, not person identifiers === Best practices are that a unique address should be used for every transaction on-chain. Therefore, a URI which contains an on-chain payment address MUST NOT represent an exchange of personal information, but a one-time payment instruction. URIs which represent only reusable non-address-reusing payment instructions (like Lightning BOLT12 offers or Silent Payments) MAY be reused as a wallet sees fit. === Proof of Payment === On many mobile operating systems (especially, or any operating system more generally), applications may "open" a bitcoin: URI in order to initiate a payment with the user's default wallet application. These payment-initiating applications may wish to learn about the completed payment. For payments completed on-chain, this is largely addressed by having the payment-initiating application monitor the blockchain for payment completion, however for other payment schemes (e.g. lightning), no such global ledger of transactions exists. In that case, proof of payment must be provided via some other mechanism. In order to avoid inadvertently revealing the sender's IP address or other information to the recipient, proof URIs must only be opened when they will simply switch to another locally-installed application (i.e. the application which initiated the payment). When clicking a URI from a website, the website should already have plenty of logic on its backend to process payment completion and a proof-of-payment callback is unnecessary. == Reference Implementation == Documentation: https://docs.rs/bitcoin-payment-instructions Code repository: https://github.com/rust-bitcoin/bitcoin-payment-instructions == Forward compatibility == Query parameter keys which are prefixed with a req- are considered required. If a client does not implement handling a query parameter which has a key prefixed with req-, it MUST consider the entire URI invalid. Any other query parameters which are not implemented, but which are not prefixed with a req-, can be safely ignored. As future new address types should be added using query parameters rather than the `bitcoinaddress` field, URIs seamlessly support various payment instructions while senders only need to support legacy instructions. This allows old senders to pay newer recipients which offer more modern payment instruction formats. == Backward compatibility == Compared to BIP 21, this document describes standard query parameters containing payment instructions, makes query parameters case-insensitive, allows bech32 and bech32m addresses in the `bitcoinaddress` field, and allows for URIs with an empty `bitcoinaddress` field. Use of bech32 and bech32m `bitcoinaddress` fields were long-since common practice in 2024, and the `lightning` query parameter storing BOLT 11 payment instructions became common practice in the year or three leading up to 2024. Inclusion of standard query parameters was added to provide guidance on query parameter usage going forward. Additionally, this BIP describes the "pop" query parameter, which was unused and will be ignored by BIP 21 implementations. Any existing BIP 21 implementation should automatically be fully compliant with this BIP, as the changes only describe existing practice or impact future address format inclusion, with the one possible exception of query parameters being made case-insensitive. Note, however, that treating query parameters as case-insensitive is already common practice due to the use of mostly-uppercase URIs in QR codes. == Appendix == === Examples === ==== URIs ==== Just the address: bitcoin:175tWpb8K1S7NmH4Zx6rewF9WQrcZv245W Address with recipient's name as label: bitcoin:175tWpb8K1S7NmH4Zx6rewF9WQrcZv245W?label=Luke-Jr Request 20.30 BTC to "Luke-Jr": bitcoin:175tWpb8K1S7NmH4Zx6rewF9WQrcZv245W?amount=20.3&label=Luke-Jr Request 50 BTC with message: bitcoin:175tWpb8K1S7NmH4Zx6rewF9WQrcZv245W?amount=50&label=Luke-Jr&message=Donation%20for%20project%20xyz Request funds to be paid over lightning to a BOLT 11 invoice with a fallback to on-chain payments: bitcoin:175tWpb8K1S7NmH4Zx6rewF9WQrcZv245W?lightning=lnbc420bogusinvoice Request funds to be paid over lightning to a BOLT 11 invoice with no fallback: bitcoin:?lightning=lnbc420bogusinvoice Request funds to be paid over lightning to a BOLT 12 offer with no fallback: bitcoin:?lno=lno1bogusoffer Request funds to be paid over lightning to a BOLT 12 offer or silent payments address with no fallback: bitcoin:?lno=lno1bogusoffer&sp=sp1qsilentpayment Request funds to be paid to a silent payments address with no fallback: bitcoin:?sp=sp1qsilentpayment Request funds to be paid to a silent payments address with a fallback: bitcoin:175tWpb8K1S7NmH4Zx6rewF9WQrcZv245W?sp=sp1qsilentpayment Some future version that has variables which are (currently) not understood and required and thus invalid: bitcoin:175tWpb8K1S7NmH4Zx6rewF9WQrcZv245W?req-somethingyoudontunderstand=50&req-somethingelseyoudontget=999 Some future version that has variables which are (currently) not understood but not required and thus valid: bitcoin:175tWpb8K1S7NmH4Zx6rewF9WQrcZv245W?somethingyoudontunderstand=50&somethingelseyoudontget=999 Multiple segwit addresses may be included for various versions of segwit, note that the human-readable part for all of them is `bc` bitcoin:?bc=bc1qufgy354j3kmvuch987xe4s40836x3h0lg8f5n2&bc=bc1p5swkugezn97763tl0yty6556856uug0q6jflljvep9m4p7339x5qzyrh4g Many QR codes utilize all-uppercase URIs, which should be handled fine BITCOIN:BC1QUFGY354J3KMVUCH987XE4S40836X3H0LG8F5N2?BC=BC1P5SWKUGEZN97763TL0YTY6556856UUG0Q6JFLLJVEP9M4P7339X5QZYRH4G BITCOIN:?BC=BC1QUFGY354J3KMVUCH987XE4S40836X3H0LG8F5N2&BC=BC1P5SWKUGEZN97763TL0YTY6556856UUG0Q6JFLLJVEP9M4P7339X5QZYRH4G A testnet segwit addresses must be included in the `tb` parameter bitcoin:?tb=tb1qghfhmd4zh7ncpmxl3qzhmq566jk8ckq4gafnmg Characters must be URI encoded properly. ==== Invalid URIs ==== Labels must not appear twice: bitcoin:175tWpb8K1S7NmH4Zx6rewF9WQrcZv245W?label=Luke-Jr&label=Matt Amounts must not appear twice: bitcoin:175tWpb8K1S7NmH4Zx6rewF9WQrcZv245W?amount=42&amount=10 Amounts must not appear twice even if they are the same: bitcoin:175tWpb8K1S7NmH4Zx6rewF9WQrcZv245W?amount=42&amount=42 Multiple proof of payment URIs must not appear, even if they are sometimes prefixed with req-: bitcoin:175tWpb8K1S7NmH4Zx6rewF9WQrcZv245W?pop=callback%3a&req-pop=callback%3a A testnet segwit addresses must be included in the `tb` parameter, not the `bc` parameter. bitcoin:?bc=tb1qghfhmd4zh7ncpmxl3qzhmq566jk8ckq4gafnmg ==== Proof of Payment ==== If the original URI is bitcoin:175tWpb8K1S7NmH4Zx6rewF9WQrcZv245W?pop=initiatingapp%3a the wallet should perform the payment information callback by opening initiatingapp:onchain=$HEX_ENCODED_TRANSACTION If the original URI is bitcoin:?lightning=lnbc420bogusinvoice&pop=callbackuri%3abody%3fpop= the wallet should perform the proof-of-payment callback by opening callbackuri:body?pop=lightning=$HEX_ENCODED_PAYMENT_PREIMAGE If the original URI is bitcoin:175tWpb8K1S7NmH4Zx6rewF9WQrcZv245W?lightning=lnbc420bogusinvoice&pop=app%3a%3f and the wallet pays on-chain, it should perform the payment information callback by opening app:?onchain=$HEX_ENCODED_TRANSACTION but if the app pays using lightning, it should perform the proof-of-payment callback by opening app:?lightning=$HEX_ENCODED_PAYMENT_PREIMAGE If the original URI is bitcoin:175tWpb8K1S7NmH4Zx6rewF9WQrcZv245W?pop=https%3aiwantyouripaddress.com the wallet should make a payment as it normally would but MUST NOT interact with iwantyouripaddress.com If the original URI is bitcoin:175tWpb8K1S7NmH4Zx6rewF9WQrcZv245W?req-pop=https%3aevilwebsite.com the wallet MUST NOT make a payment ================================================ FILE: bip-0322.mediawiki ================================================
  BIP: 322
  Layer: Applications
  Title: Generic Signed Message Format
  Authors: Karl-Johan Alm 
  Comments-Summary: No comments yet.
  Comments-URI: https://github.com/bitcoin/bips/wiki/Comments:BIP-0322
  Status: Draft
  Type: Specification
  Assigned: 2018-09-10
  License: CC0-1.0
== Abstract == A standard for interoperable signed messages based on the Bitcoin Script format, either for proving fund availability, or committing to a message as the intended recipient of funds sent to the invoice address. == Motivation == The current message signing standard only works for P2PKH (1...) invoice addresses. We propose to extend and generalize the standard by using a Bitcoin Script based approach. This ensures that any coins, no matter what script they are controlled by, can in-principle be signed for. For easy interoperability with existing signing hardware, we also define a signature message format which resembles a Bitcoin transaction (except that it contains an invalid input, so it cannot be spent on any real network). Additionally, the current message signature format uses ECDSA signatures which do not commit to the public key, meaning that they do not actually prove knowledge of any secret keys. (Indeed, valid signatures can be tweaked by 3rd parties to become valid signatures on certain related keys.) Ultimately no message signing protocol can actually prove control of funds, both because a signature is obsolete as soon as it is created, and because the possessor of a secret key may be willing to sign messages on others' behalf even if it would not sign actual transactions. No signmessage protocol can fix these limitations. == Types of Signatures == This BIP specifies three formats for signing messages: ''legacy'', ''simple'' and ''full''. Additionally, a variant of the ''full'' format can be used to demonstrate control over a set of UTXOs. === Legacy === New proofs should use the new format for all invoice address formats, including P2PKH. The legacy format MAY be used, but must be restricted to the legacy P2PKH invoice address format. === Simple === A ''simple'' signature consists of a witness stack, consensus encoded as a vector of vectors of bytes, and base64-encoded. Validators should construct to_spend and to_sign as defined below, with default values for all fields except that * message_hash is a BIP340-tagged hash of the message, as specified below * message_challenge in to_spend is set to the scriptPubKey being signed with * message_signature in to_sign is set to the provided simple signature. and then proceed as they would for a full signature. === Full === Full signatures follow an analogous specification to the BIP-325 challenges and solutions used by Signet. Let there be two virtual transactions to_spend and to_sign. The to_spend transaction is: nVersion = 0 nLockTime = 0 vin[0].prevout.hash = 0000...000 vin[0].prevout.n = 0xFFFFFFFF vin[0].nSequence = 0 vin[0].scriptSig = OP_0 PUSH32[ message_hash ] vin[0].scriptWitness = [] vout[0].nValue = 0 vout[0].scriptPubKey = message_challenge where message_hash is a BIP340-tagged hash of the message, i.e. sha256_tag(m), where tag = BIP0322-signed-message and m is the message as is without length prefix or null terminator, and message_challenge is the to be proven (public) key script. The to_sign transaction is: nVersion = 0 or (FULL format only) as appropriate (e.g. 2, for time locks) nLockTime = 0 or (FULL format only) as appropriate (for time locks) vin[0].prevout.hash = to_spend.txid vin[0].prevout.n = 0 vin[0].nSequence = 0 or (FULL format only) as appropriate (for time locks) vin[0].scriptWitness = message_signature vout[0].nValue = 0 vout[0].scriptPubKey = OP_RETURN A full signature consists of the base64-encoding of the to_sign transaction in standard network serialisation once it has been signed. === Full (Proof of Funds) === A signer may construct a proof of funds, demonstrating control of a set of UTXOs, by constructing a full signature as above, with the following modifications. * All outputs that the signer wishes to demonstrate control of are included as additional inputs of to_sign, and their witness and scriptSig data should be set as though these outputs were actually being spent. Unlike an ordinary signature, validators of a proof of funds need access to the current UTXO set, to learn that the claimed inputs exist on the blockchain, and to learn their scriptPubKeys. == Detailed Specification == For all signature types, except legacy, the to_spend and to_sign transactions must be valid transactions which pass all consensus checks, except of course that the output with prevout 000...000:FFFFFFFF does not exist. === Verification === A validator is given as input an address ''A'' (which may be omitted in a proof-of-funds), signature ''s'' and message ''m'', and outputs one of three states * ''valid at time T and age S'' indicates that the signature has set timelocks but is otherwise valid * ''inconclusive'' means the validator was unable to check the scripts * ''invalid'' means that some check failed ==== Verification Process ==== Validation consists of the following steps: # Basic validation ## Compute the transaction to_spend from ''m'' and ''A'' ## Decode ''s'' as the transaction to_sign ## If ''s'' was a full transaction, confirm all fields are set as specified above; in particular that ##* to_sign has at least one input and its first input spends the output of to_spend ##* to_sign has exactly one output, as specified above ## Confirm that the two transactions together satisfy all consensus rules, except for to_spend's missing input, and except that ''nSequence'' of to_sign's first input and ''nLockTime'' of to_sign are not checked. # (Optional) If the validator does not have a full script interpreter, it should check that it understands all scripts being satisfied. If not, it should stop here and output ''inconclusive''. # Check the **required rules**: ## All signatures must use the SIGHASH_ALL flag. ## The use of CODESEPARATOR or FindAndDelete is forbidden. ## LOW_S, STRICTENC and NULLFAIL: valid ECDSA signatures must be strictly DER-encoded and have a low-S value; invalid ECDSA signature must be the empty push ## MINIMALDATA: all pushes must be minimally encoded ## CLEANSTACK: require that only a single stack element remains after evaluation ## MINIMALIF: the argument of IF/NOTIF must be exactly 0x01 or empty push ## If any of the above steps failed, the validator should stop and output the ''invalid'' state. # Check the **upgradeable rules** ## The version of to_sign must be 0 or 2. ## The use of NOPs reserved for upgrades is forbidden. ## The use of segwit versions greater than 1 are forbidden. ## If any of the above steps failed, the validator should stop and output the ''inconclusive'' state. # Let ''T'' by the nLockTime of to_sign and ''S'' be the nSequence of the first input of to_sign. Output the state ''valid at time T and age S''. === Signing === Signers who control an address ''A'' who wish to sign a message ''m'' act as follows: # They construct to_spend and to_sign as specified above, using the scriptPubKey of ''A'' for message_challenge and tagged hash of ''m'' as message_hash. # Optionally, they may set nLockTime of to_sign or nSequence of its first input. # Optionally, they may add any additional inputs to to_sign that they wish to prove control of. # They satisfy to_sign as they would any other transaction. They then encode their signature, choosing either ''simple'' or ''full'' as follows: * If they added no inputs to to_sign, left nSequence and nLockTime at 0, and ''A'' is a Segwit address (either pure or P2SH-wrapped), then they may base64-encode message_signature * Otherwise they must base64-encode to_sign. == Compatibility == This specification is backwards compatible with the legacy signmessage/verifymessage specification through the special case as described above. == Reference implementation == * Bitcoin Core pull request (basic support) at: https://github.com/bitcoin/bitcoin/pull/24058 == Acknowledgements == Thanks to David Harding, Jim Posen, Kalle Rosenbaum, Pieter Wuille, Andrew Poelstra, and many others for their feedback on the specification. == References == # Original mailing list thread: https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2018-March/015818.html == Copyright == This document is licensed under the Creative Commons CC0 1.0 Universal license. == Test vectors == === Message hashing === Message hashes are BIP340-tagged hashes of a message, i.e. sha256_tag(m), where tag = BIP0322-signed-message, and m is the message as is without length prefix or null terminator: * Message = "" (empty string): c90c269c4f8fcbe6880f72a721ddfbf1914268a794cbb21cfafee13770ae19f1 * Message = "Hello World": f0eb03b1a75ac6d9847f55c624a99169b5dccba2a31f5b23bea77ba270de0a7a === Message signing === Given below parameters: * private key L3VFeEujGtevx9w18HD1fhRbCH67Az2dpCymeRE1SoPK6XQtaN2k * corresponding address bc1q9vza2e8x573nczrlzms0wvx3gsqjx7vavgkx0l Produce signatures: * Message = "" (empty string): AkcwRAIgM2gBAQqvZX15ZiysmKmQpDrG83avLIT492QBzLnQIxYCIBaTpOaD20qRlEylyxFSeEA2ba9YOixpX8z46TSDtS40ASECx/EgAxlkQpQ9hYjgGu6EBCPMVPwVIVJqO4XCsMvViHI= or AkgwRQIhAPkJ1Q4oYS0htvyuSFHLxRQpFAY56b70UvE7Dxazen0ZAiAtZfFz1S6T6I23MWI2lK/pcNTWncuyL8UL+oMdydVgzAEhAsfxIAMZZEKUPYWI4BruhAQjzFT8FSFSajuFwrDL1Yhy * Message = "Hello World": AkcwRAIgZRfIY3p7/DoVTty6YZbWS71bc5Vct9p9Fia83eRmw2QCICK/ENGfwLtptFluMGs2KsqoNSk89pO7F29zJLUx9a/sASECx/EgAxlkQpQ9hYjgGu6EBCPMVPwVIVJqO4XCsMvViHI= or AkgwRQIhAOzyynlqt93lOKJr+wmmxIens//zPzl9tqIOua93wO6MAiBi5n5EyAcPScOjf1lAqIUIQtr3zKNeavYabHyR8eGhowEhAsfxIAMZZEKUPYWI4BruhAQjzFT8FSFSajuFwrDL1Yhy === Transaction Hashes === to_spend: * Message = "" (empty string): c5680aa69bb8d860bf82d4e9cd3504b55dde018de765a91bb566283c545a99a7 * Message = "Hello World": b79d196740ad5217771c1098fc4a4b51e0535c32236c71f1ea4d61a2d603352b to_sign: * Message = "" (empty string): 1e9654e951a5ba44c8604c4de6c67fd78a27e81dcadcfe1edf638ba3aaebaed6 * Message = "Hello World": 88737ae86f2077145f93cc4b153ae9a1cb8d56afa511988c149c5c8c9d93bddf ================================================ FILE: bip-0324/ellswift_decode_test_vectors.csv ================================================ ellswift,x,comment 00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000,edd1fd3e327ce90cc7a3542614289aee9682003e9cf7dcc9cf2ca9743be5aa0c,u%p=0;t%p=0;valid_x(x2) 000000000000000000000000000000000000000000000000000000000000000001d3475bf7655b0fb2d852921035b2ef607f49069b97454e6795251062741771,b5da00b73cd6560520e7c364086e7cd23a34bf60d0e707be9fc34d4cd5fdfa2c,u%p=0;valid_x(x1) 000000000000000000000000000000000000000000000000000000000000000082277c4a71f9d22e66ece523f8fa08741a7c0912c66a69ce68514bfd3515b49f,f482f2e241753ad0fb89150d8491dc1e34ff0b8acfbb442cfe999e2e5e6fd1d2,u%p=0;valid_x(x3);valid_x(x2);valid_x(x1) 00000000000000000000000000000000000000000000000000000000000000008421cc930e77c9f514b6915c3dbe2a94c6d8f690b5b739864ba6789fb8a55dd0,9f59c40275f5085a006f05dae77eb98c6fd0db1ab4a72ac47eae90a4fc9e57e0,u%p=0;valid_x(x2) 0000000000000000000000000000000000000000000000000000000000000000bde70df51939b94c9c24979fa7dd04ebd9b3572da7802290438af2a681895441,aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa9fffffd6b,u%p=0;(u'^3-t'^2+7)%p=0;valid_x(x3) 0000000000000000000000000000000000000000000000000000000000000000d19c182d2759cd99824228d94799f8c6557c38a1c0d6779b9d4b729c6f1ccc42,70720db7e238d04121f5b1afd8cc5ad9d18944c6bdc94881f502b7a3af3aecff,u%p=0;valid_x(x3) 0000000000000000000000000000000000000000000000000000000000000000fffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2f,edd1fd3e327ce90cc7a3542614289aee9682003e9cf7dcc9cf2ca9743be5aa0c,u%p=0;t%p=0;valid_x(x2);t>=p 0000000000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffffffffffffffffffffffffffff2664bbd5,50873db31badcc71890e4f67753a65757f97aaa7dd5f1e82b753ace32219064b,u%p=0;valid_x(x3);valid_x(x2);valid_x(x1);t>=p 0000000000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffffffffffffffffffffffffffff7028de7d,1eea9cc59cfcf2fa151ac6c274eea4110feb4f7b68c5965732e9992e976ef68e,u%p=0;valid_x(x2);t>=p 0000000000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffffffffffffffffffffffffffffcbcfb7e7,12303941aedc208880735b1f1795c8e55be520ea93e103357b5d2adb7ed59b8e,u%p=0;valid_x(x1);t>=p 0000000000000000000000000000000000000000000000000000000000000000fffffffffffffffffffffffffffffffffffffffffffffffffffffffff3113ad9,7eed6b70e7b0767c7d7feac04e57aa2a12fef5e0f48f878fcbb88b3b6b5e0783,u%p=0;valid_x(x3);t>=p 0a2d2ba93507f1df233770c2a797962cc61f6d15da14ecd47d8d27ae1cd5f8530000000000000000000000000000000000000000000000000000000000000000,532167c11200b08c0e84a354e74dcc40f8b25f4fe686e30869526366278a0688,t%p=0;(u'^3+t'^2+7)%p=0;valid_x(x3);valid_x(x2);valid_x(x1) 0a2d2ba93507f1df233770c2a797962cc61f6d15da14ecd47d8d27ae1cd5f853fffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2f,532167c11200b08c0e84a354e74dcc40f8b25f4fe686e30869526366278a0688,t%p=0;(u'^3+t'^2+7)%p=0;valid_x(x3);valid_x(x2);valid_x(x1);t>=p 0ffde9ca81d751e9cdaffc1a50779245320b28996dbaf32f822f20117c22fbd6c74d99efceaa550f1ad1c0f43f46e7ff1ee3bd0162b7bf55f2965da9c3450646,74e880b3ffd18fe3cddf7902522551ddf97fa4a35a3cfda8197f947081a57b8f,valid_x(x3) 0ffde9ca81d751e9cdaffc1a50779245320b28996dbaf32f822f20117c22fbd6ffffffffffffffffffffffffffffffffffffffffffffffffffffffff156ca896,377b643fce2271f64e5c8101566107c1be4980745091783804f654781ac9217c,valid_x(x2);t>=p 123658444f32be8f02ea2034afa7ef4bbe8adc918ceb49b12773b625f490b368ffffffffffffffffffffffffffffffffffffffffffffffffffffffff8dc5fe11,ed16d65cf3a9538fcb2c139f1ecbc143ee14827120cbc2659e667256800b8142,(u'^3-t'^2+7)%p=0;valid_x(x3);valid_x(x2);valid_x(x1);t>=p 146f92464d15d36e35382bd3ca5b0f976c95cb08acdcf2d5b3570617990839d7ffffffffffffffffffffffffffffffffffffffffffffffffffffffff3145e93b,0d5cd840427f941f65193079ab8e2e83024ef2ee7ca558d88879ffd879fb6657,(u'^3+t'^2+7)%p=0;valid_x(x3);t>=p 15fdf5cf09c90759add2272d574d2bb5fe1429f9f3c14c65e3194bf61b82aa73ffffffffffffffffffffffffffffffffffffffffffffffffffffffff04cfd906,16d0e43946aec93f62d57eb8cde68951af136cf4b307938dd1447411e07bffe1,(u'^3+t'^2+7)%p=0;valid_x(x2);t>=p 1f67edf779a8a649d6def60035f2fa22d022dd359079a1a144073d84f19b92d50000000000000000000000000000000000000000000000000000000000000000,025661f9aba9d15c3118456bbe980e3e1b8ba2e047c737a4eb48a040bb566f6c,t%p=0;valid_x(x2) 1f67edf779a8a649d6def60035f2fa22d022dd359079a1a144073d84f19b92d5fffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2f,025661f9aba9d15c3118456bbe980e3e1b8ba2e047c737a4eb48a040bb566f6c,t%p=0;valid_x(x2);t>=p 1fe1e5ef3fceb5c135ab7741333ce5a6e80d68167653f6b2b24bcbcfaaaff507fffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2f,98bec3b2a351fa96cfd191c1778351931b9e9ba9ad1149f6d9eadca80981b801,t%p=0;(u'^3-t'^2+7)%p=0;valid_x(x3);valid_x(x2);valid_x(x1);t>=p 4056a34a210eec7892e8820675c860099f857b26aad85470ee6d3cf1304a9dcf375e70374271f20b13c9986ed7d3c17799698cfc435dbed3a9f34b38c823c2b4,868aac2003b29dbcad1a3e803855e078a89d16543ac64392d122417298cec76e,(u'^3-t'^2+7)%p=0;valid_x(x3) 4197ec3723c654cfdd32ab075506648b2ff5070362d01a4fff14b336b78f963fffffffffffffffffffffffffffffffffffffffffffffffffffffffffb3ab1e95,ba5a6314502a8952b8f456e085928105f665377a8ce27726a5b0eb7ec1ac0286,(u'^3+t'^2+7)%p=0;valid_x(x1);t>=p 47eb3e208fedcdf8234c9421e9cd9a7ae873bfbdbc393723d1ba1e1e6a8e6b24ffffffffffffffffffffffffffffffffffffffffffffffffffffffff7cd12cb1,d192d52007e541c9807006ed0468df77fd214af0a795fe119359666fdcf08f7c,(u'^3+t'^2+7)%p=0;valid_x(x3);valid_x(x2);valid_x(x1);t>=p 5eb9696a2336fe2c3c666b02c755db4c0cfd62825c7b589a7b7bb442e141c1d693413f0052d49e64abec6d5831d66c43612830a17df1fe4383db896468100221,ef6e1da6d6c7627e80f7a7234cb08a022c1ee1cf29e4d0f9642ae924cef9eb38,(u'^3+t'^2+7)%p=0;valid_x(x1) 7bf96b7b6da15d3476a2b195934b690a3a3de3e8ab8474856863b0de3af90b0e0000000000000000000000000000000000000000000000000000000000000000,50851dfc9f418c314a437295b24feeea27af3d0cd2308348fda6e21c463e46ff,t%p=0;valid_x(x1) 7bf96b7b6da15d3476a2b195934b690a3a3de3e8ab8474856863b0de3af90b0efffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2f,50851dfc9f418c314a437295b24feeea27af3d0cd2308348fda6e21c463e46ff,t%p=0;valid_x(x1);t>=p 851b1ca94549371c4f1f7187321d39bf51c6b7fb61f7cbf027c9da62021b7a65fc54c96837fb22b362eda63ec52ec83d81bedd160c11b22d965d9f4a6d64d251,3e731051e12d33237eb324f2aa5b16bb868eb49a1aa1fadc19b6e8761b5a5f7b,(u'^3+t'^2+7)%p=0;valid_x(x2) 943c2f775108b737fe65a9531e19f2fc2a197f5603e3a2881d1d83e4008f91250000000000000000000000000000000000000000000000000000000000000000,311c61f0ab2f32b7b1f0223fa72f0a78752b8146e46107f8876dd9c4f92b2942,t%p=0;valid_x(x3);valid_x(x2);valid_x(x1) 943c2f775108b737fe65a9531e19f2fc2a197f5603e3a2881d1d83e4008f9125fffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2f,311c61f0ab2f32b7b1f0223fa72f0a78752b8146e46107f8876dd9c4f92b2942,t%p=0;valid_x(x3);valid_x(x2);valid_x(x1);t>=p a0f18492183e61e8063e573606591421b06bc3513631578a73a39c1c3306239f2f32904f0d2a33ecca8a5451705bb537d3bf44e071226025cdbfd249fe0f7ad6,97a09cf1a2eae7c494df3c6f8a9445bfb8c09d60832f9b0b9d5eabe25fbd14b9,valid_x(x1) a1ed0a0bd79d8a23cfe4ec5fef5ba5cccfd844e4ff5cb4b0f2e71627341f1c5b17c499249e0ac08d5d11ea1c2c8ca7001616559a7994eadec9ca10fb4b8516dc,65a89640744192cdac64b2d21ddf989cdac7500725b645bef8e2200ae39691f2,valid_x(x2) ba94594a432721aa3580b84c161d0d134bc354b690404d7cd4ec57c16d3fbe98ffffffffffffffffffffffffffffffffffffffffffffffffffffffffea507dd7,5e0d76564aae92cb347e01a62afd389a9aa401c76c8dd227543dc9cd0efe685a,valid_x(x1);t>=p bcaf7219f2f6fbf55fe5e062dce0e48c18f68103f10b8198e974c184750e1be3932016cbf69c4471bd1f656c6a107f1973de4af7086db897277060e25677f19a,2d97f96cac882dfe73dc44db6ce0f1d31d6241358dd5d74eb3d3b50003d24c2b,valid_x(x3);valid_x(x2);valid_x(x1) bcaf7219f2f6fbf55fe5e062dce0e48c18f68103f10b8198e974c184750e1be3ffffffffffffffffffffffffffffffffffffffffffffffffffffffff6507d09a,e7008afe6e8cbd5055df120bd748757c686dadb41cce75e4addcc5e02ec02b44,valid_x(x3);valid_x(x2);valid_x(x1);t>=p c5981bae27fd84401c72a155e5707fbb811b2b620645d1028ea270cbe0ee225d4b62aa4dca6506c1acdbecc0552569b4b21436a5692e25d90d3bc2eb7ce24078,948b40e7181713bc018ec1702d3d054d15746c59a7020730dd13ecf985a010d7,(u'^3+t'^2+7)%p=0;valid_x(x3) c894ce48bfec433014b931a6ad4226d7dbd8eaa7b6e3faa8d0ef94052bcf8cff336eeb3919e2b4efb746c7f71bbca7e9383230fbbc48ffafe77e8bcc69542471,f1c91acdc2525330f9b53158434a4d43a1c547cff29f15506f5da4eb4fe8fa5a,(u'^3-t'^2+7)%p=0;valid_x(x3);valid_x(x2);valid_x(x1) cbb0deab125754f1fdb2038b0434ed9cb3fb53ab735391129994a535d925f6730000000000000000000000000000000000000000000000000000000000000000,872d81ed8831d9998b67cb7105243edbf86c10edfebb786c110b02d07b2e67cd,t%p=0;(u'^3-t'^2+7)%p=0;valid_x(x3);valid_x(x2);valid_x(x1) d917b786dac35670c330c9c5ae5971dfb495c8ae523ed97ee2420117b171f41effffffffffffffffffffffffffffffffffffffffffffffffffffffff2001f6f6,e45b71e110b831f2bdad8651994526e58393fde4328b1ec04d59897142584691,valid_x(x3);t>=p e28bd8f5929b467eb70e04332374ffb7e7180218ad16eaa46b7161aa679eb4260000000000000000000000000000000000000000000000000000000000000000,66b8c980a75c72e598d383a35a62879f844242ad1e73ff12edaa59f4e58632b5,t%p=0;valid_x(x3) e28bd8f5929b467eb70e04332374ffb7e7180218ad16eaa46b7161aa679eb426fffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2f,66b8c980a75c72e598d383a35a62879f844242ad1e73ff12edaa59f4e58632b5,t%p=0;valid_x(x3);t>=p e7ee5814c1706bf8a89396a9b032bc014c2cac9c121127dbf6c99278f8bb53d1dfd04dbcda8e352466b6fcd5f2dea3e17d5e133115886eda20db8a12b54de71b,e842c6e3529b234270a5e97744edc34a04d7ba94e44b6d2523c9cf0195730a50,(u'^3+t'^2+7)%p=0;valid_x(x3);valid_x(x2);valid_x(x1) f292e46825f9225ad23dc057c1d91c4f57fcb1386f29ef10481cb1d22518593fffffffffffffffffffffffffffffffffffffffffffffffffffffffff7011c989,3cea2c53b8b0170166ac7da67194694adacc84d56389225e330134dab85a4d55,(u'^3-t'^2+7)%p=0;valid_x(x3);t>=p fffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2f0000000000000000000000000000000000000000000000000000000000000000,edd1fd3e327ce90cc7a3542614289aee9682003e9cf7dcc9cf2ca9743be5aa0c,u%p=0;t%p=0;valid_x(x2);u>=p fffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2f01d3475bf7655b0fb2d852921035b2ef607f49069b97454e6795251062741771,b5da00b73cd6560520e7c364086e7cd23a34bf60d0e707be9fc34d4cd5fdfa2c,u%p=0;valid_x(x1);u>=p fffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2f4218f20ae6c646b363db68605822fb14264ca8d2587fdd6fbc750d587e76a7ee,aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa9fffffd6b,u%p=0;(u'^3-t'^2+7)%p=0;valid_x(x3);u>=p fffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2f82277c4a71f9d22e66ece523f8fa08741a7c0912c66a69ce68514bfd3515b49f,f482f2e241753ad0fb89150d8491dc1e34ff0b8acfbb442cfe999e2e5e6fd1d2,u%p=0;valid_x(x3);valid_x(x2);valid_x(x1);u>=p fffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2f8421cc930e77c9f514b6915c3dbe2a94c6d8f690b5b739864ba6789fb8a55dd0,9f59c40275f5085a006f05dae77eb98c6fd0db1ab4a72ac47eae90a4fc9e57e0,u%p=0;valid_x(x2);u>=p fffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2fd19c182d2759cd99824228d94799f8c6557c38a1c0d6779b9d4b729c6f1ccc42,70720db7e238d04121f5b1afd8cc5ad9d18944c6bdc94881f502b7a3af3aecff,u%p=0;valid_x(x3);u>=p fffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2ffffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2f,edd1fd3e327ce90cc7a3542614289aee9682003e9cf7dcc9cf2ca9743be5aa0c,u%p=0;t%p=0;valid_x(x2);u>=p;t>=p fffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2fffffffffffffffffffffffffffffffffffffffffffffffffffffffff2664bbd5,50873db31badcc71890e4f67753a65757f97aaa7dd5f1e82b753ace32219064b,u%p=0;valid_x(x3);valid_x(x2);valid_x(x1);u>=p;t>=p fffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2fffffffffffffffffffffffffffffffffffffffffffffffffffffffff7028de7d,1eea9cc59cfcf2fa151ac6c274eea4110feb4f7b68c5965732e9992e976ef68e,u%p=0;valid_x(x2);u>=p;t>=p fffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2fffffffffffffffffffffffffffffffffffffffffffffffffffffffffcbcfb7e7,12303941aedc208880735b1f1795c8e55be520ea93e103357b5d2adb7ed59b8e,u%p=0;valid_x(x1);u>=p;t>=p fffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2ffffffffffffffffffffffffffffffffffffffffffffffffffffffffff3113ad9,7eed6b70e7b0767c7d7feac04e57aa2a12fef5e0f48f878fcbb88b3b6b5e0783,u%p=0;valid_x(x3);u>=p;t>=p ffffffffffffffffffffffffffffffffffffffffffffffffffffffff13cea4a70000000000000000000000000000000000000000000000000000000000000000,649984435b62b4a25d40c6133e8d9ab8c53d4b059ee8a154a3be0fcf4e892edb,t%p=0;valid_x(x1);u>=p ffffffffffffffffffffffffffffffffffffffffffffffffffffffff13cea4a7fffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2f,649984435b62b4a25d40c6133e8d9ab8c53d4b059ee8a154a3be0fcf4e892edb,t%p=0;valid_x(x1);u>=p;t>=p ffffffffffffffffffffffffffffffffffffffffffffffffffffffff15028c590063f64d5a7f1c14915cd61eac886ab295bebd91992504cf77edb028bdd6267f,3fde5713f8282eead7d39d4201f44a7c85a5ac8a0681f35e54085c6b69543374,(u'^3+t'^2+7)%p=0;valid_x(x2);u>=p ffffffffffffffffffffffffffffffffffffffffffffffffffffffff2715de860000000000000000000000000000000000000000000000000000000000000000,3524f77fa3a6eb4389c3cb5d27f1f91462086429cd6c0cb0df43ea8f1e7b3fb4,t%p=0;valid_x(x3);valid_x(x2);valid_x(x1);u>=p ffffffffffffffffffffffffffffffffffffffffffffffffffffffff2715de86fffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2f,3524f77fa3a6eb4389c3cb5d27f1f91462086429cd6c0cb0df43ea8f1e7b3fb4,t%p=0;valid_x(x3);valid_x(x2);valid_x(x1);u>=p;t>=p ffffffffffffffffffffffffffffffffffffffffffffffffffffffff2c2c5709e7156c417717f2feab147141ec3da19fb759575cc6e37b2ea5ac9309f26f0f66,d2469ab3e04acbb21c65a1809f39caafe7a77c13d10f9dd38f391c01dc499c52,(u'^3-t'^2+7)%p=0;valid_x(x3);valid_x(x2);valid_x(x1);u>=p ffffffffffffffffffffffffffffffffffffffffffffffffffffffff3a08cc1efffffffffffffffffffffffffffffffffffffffffffffffffffffffff760e9f0,38e2a5ce6a93e795e16d2c398bc99f0369202ce21e8f09d56777b40fc512bccc,valid_x(x3);u>=p;t>=p ffffffffffffffffffffffffffffffffffffffffffffffffffffffff3e91257d932016cbf69c4471bd1f656c6a107f1973de4af7086db897277060e25677f19a,864b3dc902c376709c10a93ad4bbe29fce0012f3dc8672c6286bba28d7d6d6fc,valid_x(x3);u>=p ffffffffffffffffffffffffffffffffffffffffffffffffffffffff795d6c1c322cadf599dbb86481522b3cc55f15a67932db2afa0111d9ed6981bcd124bf44,766dfe4a700d9bee288b903ad58870e3d4fe2f0ef780bcac5c823f320d9a9bef,(u'^3+t'^2+7)%p=0;valid_x(x1);u>=p ffffffffffffffffffffffffffffffffffffffffffffffffffffffff8e426f0392389078c12b1a89e9542f0593bc96b6bfde8224f8654ef5d5cda935a3582194,faec7bc1987b63233fbc5f956edbf37d54404e7461c58ab8631bc68e451a0478,valid_x(x1);u>=p ffffffffffffffffffffffffffffffffffffffffffffffffffffffff91192139ffffffffffffffffffffffffffffffffffffffffffffffffffffffff45f0f1eb,ec29a50bae138dbf7d8e24825006bb5fc1a2cc1243ba335bc6116fb9e498ec1f,valid_x(x2);u>=p;t>=p ffffffffffffffffffffffffffffffffffffffffffffffffffffffff98eb9ab76e84499c483b3bf06214abfe065dddf43b8601de596d63b9e45a166a580541fe,1e0ff2dee9b09b136292a9e910f0d6ac3e552a644bba39e64e9dd3e3bbd3d4d4,(u'^3-t'^2+7)%p=0;valid_x(x3);u>=p ffffffffffffffffffffffffffffffffffffffffffffffffffffffff9b77b7f2c74d99efceaa550f1ad1c0f43f46e7ff1ee3bd0162b7bf55f2965da9c3450646,8b7dd5c3edba9ee97b70eff438f22dca9849c8254a2f3345a0a572ffeaae0928,valid_x(x2);u>=p ffffffffffffffffffffffffffffffffffffffffffffffffffffffff9b77b7f2ffffffffffffffffffffffffffffffffffffffffffffffffffffffff156ca896,0881950c8f51d6b9a6387465d5f12609ef1bb25412a08a74cb2dfb200c74bfbf,valid_x(x3);valid_x(x2);valid_x(x1);u>=p;t>=p ffffffffffffffffffffffffffffffffffffffffffffffffffffffffa2f5cd838816c16c4fe8a1661d606fdb13cf9af04b979a2e159a09409ebc8645d58fde02,2f083207b9fd9b550063c31cd62b8746bd543bdc5bbf10e3a35563e927f440c8,(u'^3+t'^2+7)%p=0;valid_x(x3);valid_x(x2);valid_x(x1);u>=p ffffffffffffffffffffffffffffffffffffffffffffffffffffffffb13f75c00000000000000000000000000000000000000000000000000000000000000000,4f51e0be078e0cddab2742156adba7e7a148e73157072fd618cd60942b146bd0,t%p=0;valid_x(x3);u>=p ffffffffffffffffffffffffffffffffffffffffffffffffffffffffb13f75c0fffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2f,4f51e0be078e0cddab2742156adba7e7a148e73157072fd618cd60942b146bd0,t%p=0;valid_x(x3);u>=p;t>=p ffffffffffffffffffffffffffffffffffffffffffffffffffffffffe7bc1f8d0000000000000000000000000000000000000000000000000000000000000000,16c2ccb54352ff4bd794f6efd613c72197ab7082da5b563bdf9cb3edaafe74c2,t%p=0;valid_x(x2);u>=p ffffffffffffffffffffffffffffffffffffffffffffffffffffffffe7bc1f8dfffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2f,16c2ccb54352ff4bd794f6efd613c72197ab7082da5b563bdf9cb3edaafe74c2,t%p=0;valid_x(x2);u>=p;t>=p ffffffffffffffffffffffffffffffffffffffffffffffffffffffffef64d162750546ce42b0431361e52d4f5242d8f24f33e6b1f99b591647cbc808f462af51,d41244d11ca4f65240687759f95ca9efbab767ededb38fd18c36e18cd3b6f6a9,(u'^3+t'^2+7)%p=0;valid_x(x3);u>=p fffffffffffffffffffffffffffffffffffffffffffffffffffffffff0e5be52372dd6e894b2a326fc3605a6e8f3c69c710bf27d630dfe2004988b78eb6eab36,64bf84dd5e03670fdb24c0f5d3c2c365736f51db6c92d95010716ad2d36134c8,valid_x(x3);valid_x(x2);valid_x(x1);u>=p fffffffffffffffffffffffffffffffffffffffffffffffffffffffffefbb982fffffffffffffffffffffffffffffffffffffffffffffffffffffffff6d6db1f,1c92ccdfcf4ac550c28db57cff0c8515cb26936c786584a70114008d6c33a34b,valid_x(x1);u>=p;t>=p ================================================ FILE: bip-0324/gen_test_vectors.py ================================================ """Generate the BIP-0324 test vectors.""" import csv import hashlib import os import sys from reference import ( FE, GE, MINUS_3_SQRT, hkdf_sha256, SECP256K1_G, ellswift_decode, ellswift_ecdh_xonly, xswiftec_inv, xswiftec, v2_ecdh, initialize_v2_transport, v2_enc_packet ) FILENAME_PACKET_TEST = os.path.join(sys.path[0], 'packet_encoding_test_vectors.csv') FILENAME_XSWIFTEC_INV_TEST = os.path.join(sys.path[0], 'xswiftec_inv_test_vectors.csv') FILENAME_ELLSWIFT_DECODE_TEST = os.path.join(sys.path[0], 'ellswift_decode_test_vectors.csv') def xswiftec_flagged(u, t, simplified=False): """A variant of xswiftec which also returns 'flags', describing conditions encountered.""" flags = [] if u == 0: flags.append("u%p=0") u = FE(1) if t == 0: flags.append("t%p=0") t = FE(1) if u**3 + t**2 + 7 == 0: flags.append("(u'^3+t'^2+7)%p=0") t = 2 * t X = (u**3 + 7 - t**2) / (2 * t) Y = (X + t) / (MINUS_3_SQRT * u) if X == 0: if not simplified: flags.append("(u'^3-t'^2+7)%p=0") x3 = u + 4 * Y**2 if GE.is_valid_x(x3): flags.append("valid_x(x3)") x2 = (-X / Y - u) / 2 if GE.is_valid_x(x2): flags.append("valid_x(x2)") x1 = (X / Y - u) / 2 if GE.is_valid_x(x1): flags.append("valid_x(x1)") for x in (x3, x2, x1): if GE.is_valid_x(x): break return x, flags def ellswift_create_deterministic(seed, features): """This is a variant of ellswift_create which doesn't use randomness. features is an integer selecting some properties of the result: - (f & 3) == 0: only x1 is valid on decoding (see xswiftec{_flagged}) - (f & 3) == 1: only x2 is valid on decoding - (f & 3) == 2: only x3 is valid on decoding - (f & 3) == 3: x1,x2,x3 are all valid on decoding - (f & 4) == 4: u >= p - (f & 8) == 8: u mod n == 0 Returns privkey, ellswift """ cnt = 0 while True: sec = hkdf_sha256(32, seed, (cnt).to_bytes(4, 'little'), b"sec") xval = (int.from_bytes(sec, 'big') * SECP256K1_G).x cnt += 1 if features & 8: u = 0 if features & 4: u += FE.SIZE else: udat = hkdf_sha256(64, seed, (cnt).to_bytes(4, 'little'), b"u") if features & 4: u = FE.SIZE + 1 + int.from_bytes(udat, 'big') % (2**256 - FE.SIZE - 1) else: u = 1 + int.from_bytes(udat, 'big') % (FE.SIZE - 1) case = hkdf_sha256(1, seed, (cnt).to_bytes(4, 'little'), b"case")[0] & 7 coru = FE(u) + ((features & 8) == 8) t = xswiftec_inv(xval, coru, case) if t is None: continue assert xswiftec(FE(u), t) == xval x2, flags = xswiftec_flagged(FE(u), t) assert x2 == xval have_x1 = "valid_x(x1)" in flags have_x2 = "valid_x(x2)" in flags have_x3 = "valid_x(x3)" in flags if (features & 3) == 0 and not (have_x1 and not have_x2 and not have_x3): continue if (features & 3) == 1 and not (not have_x1 and have_x2 and not have_x3): continue if (features & 3) == 2 and not (not have_x1 and not have_x2 and have_x3): continue if (features & 3) == 3 and not (have_x1 and have_x2 and have_x3): continue return sec, u.to_bytes(32, 'big') + t.to_bytes() def ellswift_decode_flagged(ellswift, simplified=False): """Decode a 64-byte ElligatorSwift encoded coordinate, returning byte array + flag string.""" uv = int.from_bytes(ellswift[:32], 'big') tv = int.from_bytes(ellswift[32:], 'big') x, flags = xswiftec_flagged(FE(uv), FE(tv)) if not simplified: if uv >= FE.SIZE: flags.append("u>=p") if tv >= FE.SIZE: flags.append("t>=p") return int(x).to_bytes(32, 'big'), ";".join(flags) def random_fe_int(_, seed, i, p): """Function to use in tuple_expand, generating a random integer in 0..p-1.""" rng_out = hkdf_sha256(64, seed, i.to_bytes(4, 'little'), b"v%i_fe" % p) return int.from_bytes(rng_out, 'big') % FE.SIZE def random_fe_int_high(_, seed, i, p): """Function to use in tuple_expand, generating a random integer in p..2^256-1.""" rng_out = hkdf_sha256(64, seed, i.to_bytes(4, 'little'), b"v%i_fe_high" % p) return FE.SIZE + int.from_bytes(rng_out, 'big') % (2**256 - FE.SIZE) def fn_of(p_in, fn): """Function to use in tuple_expand, to pick one variable in function of another.""" def inner(vs, _seed, _i, p): assert p != p_in if isinstance(vs[p_in], int): return fn(vs[p_in]) return None return inner def tuple_expand(out, tuplespec, prio, seed=None, cnt=1): """Given a tuple specification, expand it cnt times, and add results to out. Expansion is defined recursively: - If any of the spec elements is a list, each element of the list results in an expansion (by replacing the list with its element). - If any of the spec elements is a function, that function is invoked with (spec, seed, expansion count, index in spec) as arguments. If the function needs to wait for other indices to be expanded, it can return None. The output consists of (prio, expansion count, SHA256(result), result, seed) tuples.""" def recurse(vs, seed, i, change_pos=None, change=None): if change_pos is not None: vs = list(vs) vs[change_pos] = change for p, v in enumerate(vs): if v is None: return if isinstance(v, list): for ve in v: recurse(vs, seed, i, p, ve) return if callable(v): res = v(vs, seed, i, p) if res is not None: recurse(vs, seed, i, p, res) return h = hashlib.sha256() for v in vs: h.update(int(v).to_bytes(32, 'big')) out.append((prio, i, h.digest(), vs, seed)) for i in range(cnt): recurse(tuplespec, seed, i) def gen_ellswift_decode_cases(seed, simplified=False): """Generate a set of interesting (ellswift, x, flags) ellswift decoding cases.""" inputs = [] # Aggregate for use in tuple_expand, expanding to int in 0..p-1, and one in p..2^256-1. RANDOM_VAL = [random_fe_int, random_fe_int_high] # Aggregate for use in tuple_expand, expanding to integers which %p equal 0. ZERO_VAL = [0, FE.SIZE] # Helpers for constructing u and t values such that u^3+t^2+7=0 or u^3-t^2+7=0. T_FOR_SUM_ZERO = fn_of(0, lambda u: (-FE(u)**3 - 7).sqrts()) T_FOR_DIFF_ZERO = fn_of(0, lambda u: (FE(u)**3 + 7).sqrts()) U_FOR_SUM_ZERO = fn_of(1, lambda t: (-FE(t)**2 - 7).cbrts()) U_FOR_DIFF_ZERO = fn_of(1, lambda t: (FE(t)**2 - 7).cbrts()) tuple_expand(inputs, [RANDOM_VAL, RANDOM_VAL], 0, seed + b"random", 64) tuple_expand(inputs, [RANDOM_VAL, T_FOR_SUM_ZERO], 1, seed + b"t=sqrt(-u^3-7)", 64) tuple_expand(inputs, [U_FOR_SUM_ZERO, RANDOM_VAL], 1, seed + b"u=cbrt(-t^2-7)", 64) tuple_expand(inputs, [RANDOM_VAL, T_FOR_DIFF_ZERO], 1, seed + b"t=sqrt(u^3+7)", 64) tuple_expand(inputs, [U_FOR_DIFF_ZERO, RANDOM_VAL], 1, seed + b"u=cbrt(t^2-7)", 64) tuple_expand(inputs, [ZERO_VAL, RANDOM_VAL], 2, seed + b"u=0", 64) tuple_expand(inputs, [RANDOM_VAL, ZERO_VAL], 2, seed + b"t=0", 64) tuple_expand(inputs, [ZERO_VAL, FE(8).sqrts()], 3, seed + b"u=0;t=sqrt(8)") tuple_expand(inputs, [FE(-8).cbrts(), ZERO_VAL], 3, seed + b"t=0;u=cbrt(-8)") tuple_expand(inputs, [FE(-6).cbrts(), ZERO_VAL], 3, seed + b"t=0;u=cbrt(-6)") tuple_expand(inputs, [ZERO_VAL, ZERO_VAL], 3, seed + b"u=0;t=0") # Unused. tuple_expand(inputs, [ZERO_VAL, FE(-8).sqrts()], 4, seed + b"u=0;t=sqrt(-8)") seen = set() cases = [] for _prio, _cnt, _hash, vs, _seed in sorted(inputs): inp = int(vs[0]).to_bytes(32, 'big') + int(vs[1]).to_bytes(32, 'big') outp, flags = ellswift_decode_flagged(inp, simplified) if flags not in seen: cases.append((inp, outp, flags)) seen.add(flags) return cases def gen_all_ellswift_decode_vectors(fil): """Generate all xelligatorswift decoding test vectors.""" cases = gen_ellswift_decode_cases(b"") writer = csv.DictWriter(fil, ["ellswift", "x", "comment"]) writer.writeheader() for val, x, flags in sorted(cases): writer.writerow({"ellswift": val.hex(), "x": x.hex(), "comment": flags}) def xswiftec_inv_flagged(x, u, case): """A variant of xswiftec_inv which also returns flags, describing conditions encountered.""" flags = [] if case & 2 == 0: if GE.is_valid_x(-x - u): flags.append("bad[valid_x(-x-u)]") return None, flags v = x if case & 1 == 0 else -x - u if v == 0: flags.append("info[v=0]") s = -(u**3 + 7) / (u**2 + u*v + v**2) assert s != 0 # would imply X=0 on curve else: s = x - u if s == 0: flags.append("bad[s=0]") return None, flags q = (-s * (4 * (u**3 + 7) + 3 * s * u**2)) if q == 0: flags.append("info[q=0]") r = q.sqrt() if r is None: flags.append("bad[non_square(q)]") return None, flags if case & 1: if r == 0: flags.append("bad[r=0]") return None, flags r = -r v = (-u + r / s) / 2 if v == 0: flags.append("info[v=0]") w = s.sqrt() assert w != 0 if w is None: flags.append("bad[non_square(s)]") return None, flags if case & 4: w = -w Y = w / 2 assert Y != 0 X = 2 * Y * (v + u / 2) if X == 0: flags.append("info[X=0]") flags.append("ok") return w * (u * (MINUS_3_SQRT - 1) / 2 - v), flags def xswiftec_inv_combo_flagged(x, u): """Compute the aggregate results and flags from xswiftec_inv_flagged for case=0..7.""" ts = [] allflags = [] for case in range(8): t, flags = xswiftec_inv_flagged(x, u, case) if t is not None: assert x == xswiftec(u, t) ts.append(t) allflags.append(f"case{case}:{'&'.join(flags)}") return ts, ";".join(allflags) def gen_all_xswiftec_inv_vectors(fil): """Generate all xswiftec_inv test vectors.""" # Two constants used below. Compute them only once. C1 = (FE(MINUS_3_SQRT) - 1) / 2 C2 = (-FE(MINUS_3_SQRT) - 1) / 2 # Helper functions that pick x and u with special properties. TRIGGER_Q_ZERO = fn_of(1, lambda u: (FE(u)**3 + 28) / (FE(-3) * FE(u)**2)) TRIGGER_DIVZERO_A = fn_of(1, lambda u: FE(u) * C1) TRIGGER_DIVZERO_B = fn_of(1, lambda u: FE(u) * C2) TRIGGER_V_ZERO = fn_of(1, lambda u: FE(-7) / FE(u)**2) TRIGGER_X_ZERO = fn_of(0, lambda x: FE(-2) * FE(x)) inputs = [] tuple_expand(inputs, [random_fe_int, random_fe_int], 0, b"uniform", 256) tuple_expand(inputs, [TRIGGER_Q_ZERO, random_fe_int], 1, b"x=-(u^3+28)/(3*u^2)", 64) tuple_expand(inputs, [TRIGGER_V_ZERO, random_fe_int], 1, b"x=-7/u^2", 512) tuple_expand(inputs, [random_fe_int, fn_of(0, lambda x: x)], 2, b"u=x", 64) tuple_expand(inputs, [random_fe_int, fn_of(0, lambda x: -FE(x))], 2, b"u=-x", 64) # Unused. tuple_expand(inputs, [TRIGGER_DIVZERO_A, random_fe_int], 3, b"x=u*(sqrt(-3)-1)/2", 64) tuple_expand(inputs, [TRIGGER_DIVZERO_B, random_fe_int], 3, b"x=u*(-sqrt(-3)-1)/2", 64) tuple_expand(inputs, [random_fe_int, TRIGGER_X_ZERO], 3, b"u=-2x", 64) seen = set() cases = [] for _prio, _cnt, _hash, vs, _seed in sorted(inputs): x, u = FE(vs[0]), FE(vs[1]) if u == 0: continue if not GE.is_valid_x(x): continue ts, flags = xswiftec_inv_combo_flagged(x, u) if flags not in seen: cases.append((int(u), int(x), ts, flags)) seen.add(flags) writer = csv.DictWriter(fil, ["u", "x"] + [f"case{c}_t" for c in range(8)] + ["comment"]) writer.writeheader() for u, x, ts, flags in sorted(cases): row = {"u": FE(u), "x": FE(x), "comment": flags} for c in range(8): if ts[c] is not None: row[f"case{c}_t"] = FE(ts[c]) writer.writerow(row) def gen_packet_encoding_vector(case): """Given a dict case with specs, construct a packet_encoding test vector as a CSV line.""" ikm = str(case).encode('utf-8') in_initiating = case["init"] in_ignore = int(case["ignore"]) in_priv_ours, in_ellswift_ours = ellswift_create_deterministic(ikm, case["features"]) mid_x_ours = (int.from_bytes(in_priv_ours, 'big') * SECP256K1_G).x.to_bytes() assert mid_x_ours == ellswift_decode(in_ellswift_ours) in_ellswift_theirs = case["theirs"] in_contents = hkdf_sha256(case["contentlen"], ikm, b"contents", b"") contents = in_contents * case["multiply"] in_aad = hkdf_sha256(case["aadlen"], ikm, b"aad", b"") mid_shared_secret = v2_ecdh(in_priv_ours, in_ellswift_theirs, in_ellswift_ours, in_initiating) peer = initialize_v2_transport(mid_shared_secret, in_initiating) for _ in range(case["idx"]): v2_enc_packet(peer, b"") ciphertext = v2_enc_packet(peer, contents, in_aad, case["ignore"]) long_msg = len(ciphertext) > 128 return { "in_idx": case['idx'], "in_priv_ours": in_priv_ours.hex(), "in_ellswift_ours": in_ellswift_ours.hex(), "in_ellswift_theirs": in_ellswift_theirs.hex(), "in_initiating": int(in_initiating), "in_contents": in_contents.hex(), "in_multiply": case['multiply'], "in_aad": in_aad.hex(), "in_ignore": in_ignore, "mid_x_ours": mid_x_ours.hex(), "mid_x_theirs": ellswift_decode(in_ellswift_theirs).hex(), "mid_x_shared": ellswift_ecdh_xonly(in_ellswift_theirs, in_priv_ours).hex(), "mid_shared_secret": mid_shared_secret.hex(), "mid_initiator_l": peer['initiator_L'].hex(), "mid_initiator_p": peer['initiator_P'].hex(), "mid_responder_l": peer['responder_L'].hex(), "mid_responder_p": peer['responder_P'].hex(), "mid_send_garbage_terminator": peer["send_garbage_terminator"].hex(), "mid_recv_garbage_terminator": peer["recv_garbage_terminator"].hex(), "out_session_id": peer["session_id"].hex(), "out_ciphertext": "" if long_msg else ciphertext.hex(), "out_ciphertext_endswith": ciphertext[-128:].hex() if long_msg else "" } def gen_all_packet_encoding_vectors(fil): """Return a list of CSV lines, one for each packet encoding vector.""" ellswift = gen_ellswift_decode_cases(b"simplified_", simplified=True) ellswift.sort(key=lambda x: hashlib.sha256(b"simplified:" + x[0]).digest()) fields = [ "in_idx", "in_priv_ours", "in_ellswift_ours", "in_ellswift_theirs", "in_initiating", "in_contents", "in_multiply", "in_aad", "in_ignore", "mid_x_ours", "mid_x_theirs", "mid_x_shared", "mid_shared_secret", "mid_initiator_l", "mid_initiator_p", "mid_responder_l", "mid_responder_p", "mid_send_garbage_terminator", "mid_recv_garbage_terminator", "out_session_id", "out_ciphertext", "out_ciphertext_endswith" ] writer = csv.DictWriter(fil, fields) writer.writeheader() for case in [ {"init": True, "contentlen": 1, "multiply": 1, "aadlen": 0, "ignore": False, "idx": 1, "theirs": ellswift[0][0], "features": 0}, {"init": False, "contentlen": 17, "multiply": 1, "aadlen": 0, "ignore": False, "idx": 999, "theirs": ellswift[1][0], "features": 1}, {"init": True, "contentlen": 63, "multiply": 1, "aadlen": 4095, "ignore": False, "idx": 0, "theirs": ellswift[2][0], "features": 2}, {"init": False, "contentlen": 128, "multiply": 1, "aadlen": 0, "ignore": True, "idx": 223, "theirs": ellswift[3][0], "features": 3}, {"init": True, "contentlen": 193, "multiply": 1, "aadlen": 0, "ignore": False, "idx": 448, "theirs": ellswift[4][0], "features": 4}, {"init": False, "contentlen": 41, "multiply": 97561, "aadlen": 0, "ignore": False, "idx": 673, "theirs": ellswift[5][0], "features": 5}, {"init": True, "contentlen": 241, "multiply": 69615, "aadlen": 0, "ignore": True, "idx": 1024, "theirs": ellswift[6][0], "features": 6}, ]: writer.writerow(gen_packet_encoding_vector(case)) if __name__ == "__main__": print(f"Generating {FILENAME_PACKET_TEST}...") with open(FILENAME_PACKET_TEST, "w", encoding="utf-8") as fil_packet: gen_all_packet_encoding_vectors(fil_packet) print(f"Generating {FILENAME_XSWIFTEC_INV_TEST}...") with open(FILENAME_XSWIFTEC_INV_TEST, "w", encoding="utf-8") as fil_xswiftec_inv: gen_all_xswiftec_inv_vectors(fil_xswiftec_inv) print(f"Generating {FILENAME_ELLSWIFT_DECODE_TEST}...") with open(FILENAME_ELLSWIFT_DECODE_TEST, "w", encoding="utf-8") as fil_ellswift_decode: gen_all_ellswift_decode_vectors(fil_ellswift_decode) ================================================ FILE: bip-0324/message_type_ids.md ================================================ # One-byte message type allocations This table lists additional message type IDs that various BIPs have assigned or proposed for assignment. Type | Message | Proposal ---- | ------------ | -------- 29 | uproof | [BIP 183 / PR#1923](https://github.com/bitcoin/bips/pull/1923) 30 | getuproof | [BIP 183 / PR#1923](https://github.com/bitcoin/bips/pull/1923) 31 | uttls | [BIP 183 / PR#1923](https://github.com/bitcoin/bips/pull/1923) 32 | getuttls | [BIP 183 / PR#1923](https://github.com/bitcoin/bips/pull/1923) 33 | usummary | [BIP 183 / PR#1923](https://github.com/bitcoin/bips/pull/1923) 34 | utreexotx | [BIP 183 / PR#1923](https://github.com/bitcoin/bips/pull/1923) 35 | uroot | [BIP 183 / PR#1923](https://github.com/bitcoin/bips/pull/1923) 36 | geturoot | [BIP 183 / PR#1923](https://github.com/bitcoin/bips/pull/1923) 37 | feature | [BIP 434](https://github.com/bitcoin/bips/blob/master/bip-0434.md) Note that this table is not authoritative but instead is reflective of the BIPs proposing the changes. If multiple BIPs make conflicting assignments for message type IDs, that may lead to multiple entries for the same message type ID in this table. BIPs that are in Draft status may be included in the table, and as a result, the IDs and messages they define may be changed in future. ================================================ FILE: bip-0324/packet_encoding_test_vectors.csv ================================================ in_idx,in_priv_ours,in_ellswift_ours,in_ellswift_theirs,in_initiating,in_contents,in_multiply,in_aad,in_ignore,mid_x_ours,mid_x_theirs,mid_x_shared,mid_shared_secret,mid_initiator_l,mid_initiator_p,mid_responder_l,mid_responder_p,mid_send_garbage_terminator,mid_recv_garbage_terminator,out_session_id,out_ciphertext,out_ciphertext_endswith 1,61062ea5071d800bbfd59e2e8b53d47d194b095ae5a4df04936b49772ef0d4d7,ec0adff257bbfe500c188c80b4fdd640f6b45a482bbc15fc7cef5931deff0aa186f6eb9bba7b85dc4dcc28b28722de1e3d9108b985e2967045668f66098e475b,a4a94dfce69b4a2a0a099313d10f9f7e7d649d60501c9e1d274c300e0d89aafaffffffffffffffffffffffffffffffffffffffffffffffffffffffff8faf88d5,1,8e,1,,0,19e965bc20fc40614e33f2f82d4eeff81b5e7516b12a5c6c0d6053527eba0923,0c71defa3fafd74cb835102acd81490963f6b72d889495e06561375bd65f6ffc,4eb2bf85bd00939468ea2abb25b63bc642e3d1eb8b967fb90caa2d89e716050e,c6992a117f5edbea70c3f511d32d26b9798be4b81a62eaee1a5acaa8459a3592,9a6478b5fbab1f4dd2f78994b774c03211c78312786e602da75a0d1767fb55cf,7d0c7820ba6a4d29ce40baf2caa6035e04f1e1cefd59f3e7e59e9e5af84f1f51,17bc726421e4054ac6a1d54915085aaa766f4d3cf67bbd168e6080eac289d15e,9f0fc1c0e85fd9a8eee07e6fc41dba2ff54c7729068a239ac97c37c524cca1c0,faef555dfcdb936425d84aba524758f3,02cb8ff24307a6e27de3b4e7ea3fa65b,ce72dffb015da62b0d0f5474cab8bc72605225b0cee3f62312ec680ec5f41ba5,7530d2a18720162ac09c25329a60d75adf36eda3c3, 999,6f312890ec83bbb26798abaadd574684a53e74ccef7953b790fcc29409080246,a8785af31c029efc82fa9fc677d7118031358d7c6a25b5779a9b900e5ccd94aac97eb36a3c5dbcdb2ca5843cc4c2fe0aaa46d10eb3d233a81c3dde476da00eef,fffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2f0000000000000000000000000000000000000000000000000000000000000000,0,3eb1d4e98035cfd8eeb29bac969ed3824a,1,,0,d4b65faa965b31fe2d9faaeb806c6449a50fe3679555c3518f7a0885f572457f,edd1fd3e327ce90cc7a3542614289aee9682003e9cf7dcc9cf2ca9743be5aa0c,13c1bf6a3ca37da9ffc7f45ec1810fa935c45454c03dc0144c1a9755bb52f81f,a6f79eb08243b6f65dbe42bfe4a6cf3f131d6963fa5d06c770a18f7b9c489b78,efc938c88c925459a9c837238716cfadfb1c3016f60d12923933710b5fcc9b55,91702f3cbd33b3c4a0b29b40548aea1ab01e43582db194afee70637d247aa036,7f457572e4260c611a6858acc8f325d87a3c8af8a59ce1da26ef6041f35715e8,1fe4d56334f5b0a5bd3c71ce4e338f40fc7e194925daa7ee6ce98aecf1766d7c,44737108aec5f8b6c1c277b31bbce9c1,ca29b3a35237f8212bd13ed187a1da2e,b0490e26111cb2d55bbff2ace00f7f644f64006539abb4e7513f05107bb10608,d78adbcba0eebfb15cfbd8142c84dc729d233d0dc11b1d851e46a114122b8d5b96b7d59317, 0,846a784f1a03dea59cc679754a60a7145542fa130e3efbd815c81e909ce32933,480eacf1536b52257bf8ce78d8f4ce09395d744767c6c129e7838947ee625af3245592c111275e877d5baae22584cb5f1153e67c16bcd7da767726cd0d0c846a,ffffffffffffffffffffffffffffffffffffffffffffffffffffffff22d5e441524d571a52b3def126189d3f416890a99d4da6ede2b0cde1760ce2c3f98457ae,1,054290a6c6ba8d80478172e89d32bf690913ae9835de6dcf206ff1f4d652286fe0ddf74deba41d55de3edc77c42a32af79bbea2c00bae7492264c60866ae5a,1,84932a55aac22b51e7b128d31d9f0550da28e6a3f394224707d878603386b2f9d0c6bcd8046679bfed7b68c517e7431e75d9dd34605727d2ef1c2babbf680ecc8d68d2c4886e9953a4034abde6da4189cd47c6bb3192242cf714d502ca6103ee84e08bc2ca4fd370d5ad4e7d06c7fbf496c6c7cc7eb19c40c61fb33df2a9ba48497a96c98d7b10c1f91098a6b7b16b4bab9687f27585ade1491ae0dba6a79e1e2d85dd9d9d45c5135ca5fca3f0f99a60ea39edbc9efc7923111c937913f225d67788d5f7e8852b697e26b92ec7bfcaa334a1665511c2b4c0a42d06f7ab98a9719516c8fd17f73804555ee84ab3b7d1762f6096b778d3cb9c799cbd49a9e4a325197b4e6cc4a5c4651f8b41ff88a92ec428354531f970263b467c77ed11312e2617d0d53fe9a8707f51f9f57a77bfb49afe3d89d85ec05ee17b9186f360c94ab8bb2926b65ca99dae1d6ee1af96cad09de70b6767e949023e4b380e66669914a741ed0fa420a48dbc7bfae5ef2019af36d1022283dd90655f25eec7151d471265d22a6d3f91dc700ba749bb67c0fe4bc0888593fbaf59d3c6fff1bf756a125910a63b9682b597c20f560ecb99c11a92c8c8c3f7fbfaa103146083a0ccaecf7a5f5e735a784a8820155914a289d57d8141870ffcaf588882332e0bcd8779efa931aa108dab6c3cce76691e345df4a91a03b71074d66333fd3591bff071ea099360f787bbe43b7b3dff2a59c41c7642eb79870222ad1c6f2e5a191ed5acea51134679587c9cf71c7d8ee290be6bf465c4ee47897a125708704ad610d8d00252d01959209d7cd04d5ecbbb1419a7e84037a55fefa13dee464b48a35c96bcb9a53e7ed461c3a1607ee00c3c302fd47cd73fda7493e947c9834a92d63dcfbd65aa7c38c3e3a2748bb5d9a58e7495d243d6b741078c8f7ee9c8813e473a323375702702b0afae1550c8341eedf5247627343a95240cb02e3e17d5dca16f8d8d3b2228e19c06399f8ec5c5e9dbe4caef6a0ea3ffb1d3c7eac03ae030e791fa12e537c80d56b55b764cadf27a8701052df1282ba8b5e3eb62b5dc7973ac40160e00722fa958d95102fc25c549d8c0e84bed95b7acb61ba65700c4de4feebf78d13b9682c52e937d23026fb4c6193e6644e2d3c99f91f4f39a8b9fc6d013f89c3793ef703987954dc0412b550652c01d922f525704d32d70d6d4079bc3551b563fb29577b3aecdc9505011701dddfd94830431e7a4918927ee44fb3831ce8c4513839e2deea1287f3fa1ab9b61a256c09637dbc7b4f0f8fbb783840f9c24526da883b0df0c473cf231656bd7bc1aaba7f321fec0971c8c2c3444bff2f55e1df7fea66ec3e440a612db9aa87bb505163a59e06b96d46f50d8120b92814ac5ab146bc78dbbf91065af26107815678ce6e33812e6bf3285d4ef3b7b04b076f21e7820dcbfdb4ad5218cf4ff6a65812d8fcb98ecc1e95e2fa58e3efe4ce26cd0bd400d6036ab2ad4f6c713082b5e3f1e04eb9e3b6c8f63f57953894b9e220e0130308e1fd91f72d398c1e7962ca2c31be83f31d6157633581a0a6910496de8d55d3d07090b6aa087159e388b7e7dec60f5d8a60d93ca2ae91296bd484d916bfaaa17c8f45ea4b1a91b37c82821199a2b7596672c37156d8701e7352aa48671d3b1bbbd2bd5f0a2268894a25b0cb2514af39c8743f8cce8ab4b523053739fd8a522222a09acf51ac704489cf17e4b7125455cb8f125b4d31af1eba1f8cf7f81a5a100a141a7ee72e8083e065616649c241f233645c5fc865d17f0285f5c52d9f45312c979bfb3ce5f2a1b951deddf280ffb3f370410cffd1583bfa90077835aa201a0712d1dcd1293ee177738b14e6b5e2a496d05220c3253bb6578d6aff774be91946a614dd7e879fb3dcf7451e0b9adb6a8c44f53c2c464bcc0019e9fad89cac7791a0a3f2974f759a9856351d4d2d7c5612c17cfc50f8479945df57716767b120a590f4bf656f4645029a525694d8a238446c5f5c2c1c995c09c1405b8b1eb9e0352ffdf766cc964f8dcf9f8f043dfab6d102cf4b298021abd78f1d9025fa1f8e1d710b38d9d1652f2d88d1305874ec41609b6617b65c5adb19b6295dc5c5da5fdf69f28144ea12f17c3c6fcce6b9b5157b3dfc969d6725fa5b098a4d9b1d31547ed4c9187452d281d0a5d456008caf1aa251fac8f950ca561982dc2dc908d3691ee3b6ad3ae3d22d002577264ca8e49c523bd51c4846be0d198ad9407bf6f7b82c79893eb2c05fe9981f687a97a4f01fe45ff8c8b7ecc551135cd960a0d6001ad35020be07ffb53cb9e731522ca8ae9364628914b9b8e8cc2f37f03393263603cc2b45295767eb0aac29b0930390eb89587ab2779d2e3decb8042acece725ba42eda650863f418f8d0d50d104e44fbbe5aa7389a4a144a8cecf00f45fb14c39112f9bfb56c0acbd44fa3ff261f5ce4acaa5134c2c1d0cca447040820c81ab1bcdc16aa075b7c68b10d06bbb7ce08b5b805e0238f24402cf24a4b4e00701935a0c68add3de090903f9b85b153cb179a582f57113bfc21c2093803f0cfa4d9d4672c2b05a24f7e4c34a8e9101b70303a7378b9c50b6cddd46814ef7fd73ef6923feceab8fc5aa8b0d185f2e83c7a99dcb1077c0ab5c1f5d5f01ba2f0420443f75c4417db9ebf1665efbb33dca224989920a64b44dc26f682cc77b4632c8454d49135e52503da855bc0f6ff8edc1145451a9772c06891f41064036b66c3119a0fc6e80dffeb65dc456108b7ca0296f4175fff3ed2b0f842cd46bd7e86f4c62dfaf1ddbf836263c00b34803de164983d0811cebfac86e7720c726d3048934c36c23189b02386a722ca9f0fe00233ab50db928d3bccea355cc681144b8b7edcaae4884d5a8f04425c0890ae2c74326e138066d8c05f4c82b29df99b034ea727afde590a1f2177ace3af99cfb1729d6539ce7f7f7314b046aab74497e63dd399e1f7d5f16517c23bd830d1fdee810f3c3b77573dd69c4b97d80d71fb5a632e00acdfa4f8e829faf3580d6a72c40b28a82172f8dcd4627663ebf6069736f21735fd84a226f427cd06bb055f94e7c92f31c48075a2955d82a5b9d2d0198ce0d4e131a112570a8ee40fb80462a81436a58e7db4e34b6e2c422e82f934ecda9949893da5730fc5c23c7c920f363f85ab28cc6a4206713c3152669b47efa8238fa826735f17b4e78750276162024ec85458cd5808e06f40dd9fd43775a456a3ff6cae90550d76d8b2899e0762ad9a371482b3e38083b1274708301d6346c22fea9bb4b73db490ff3ab05b2f7f9e187adef139a7794454b7300b8cc64d3ad76c0e4bc54e08833a4419251550655380d675bc91855aeb82585220bb97f03e976579c08f321b5f8f70988d3061f41465517d53ac571dbf1b24b94443d2e9a8e8a79b392b3d6a4ecdd7f626925c365ef6221305105ce9b5f5b6ecc5bed3d702bd4b7f5008aa8eb8c7aa3ade8ecf6251516fbefeea4e1082aa0e1848eddb31ffe44b04792d296054402826e4bd054e671f223e5557e4c94f89ca01c25c44f1a2ff2c05a70b43408250705e1b858bf0670679fdcd379203e36be3500dd981b1a6422c3cf15224f7fefdef0a5f225c5a09d15767598ecd9e262460bb33a4b5d09a64591efabc57c923d3be406979032ae0bc0997b65336a06dd75b253332ad6a8b63ef043f780a1b3fb6d0b6cad98b1ef4a02535eb39e14a866cfc5fc3a9c5deb2261300d71280ebe66a0776a151469551c3c5fa308757f956655278ec6330ae9e3625468c5f87e02cd9a6489910d4143c1f4ee13aa21a6859d907b788e28572fecee273d44e4a900fa0aa668dd861a60fb6b6b12c2c5ef3c8df1bd7ef5d4b0d1cdb8c15fffbb365b9784bd94abd001c6966216b9b67554ad7cb7f958b70092514f7800fc40244003e0fd1133a9b850fb17f4fcafde07fc87b07fb510670654a5d2d6fc9876ac74728ea41593beef003d6858786a52d3a40af7529596767c17000bfaf8dc52e871359f4ad8bf6e7b2853e5229bdf39657e213580294a5317c5df172865e1e17fe37093b585e04613f5f078f761b2b1752eb32983afda24b523af8851df9a02b37e77f543f18888a782a994a50563334282bf9cdfccc183fdf4fcd75ad86ee0d94f91ee2300a5befbccd14e03a77fc031a8cfe4f01e4c5290f5ac1da0d58ea054bd4837cfd93e5e34fc0eb16e48044ba76131f228d16cde9b0bb978ca7cdcd10653c358bdb26fdb723a530232c32ae0a4cecc06082f46e1c1d596bfe60621ad1e354e01e07b040cc7347c016653f44d926d13ca74e6cbc9d4ab4c99f4491c95c76fff5076b3936eb9d0a286b97c035ca88a3c6309f5febfd4cdaac869e4f58ed409b1e9eb4192fb2f9c2f12176d460fd98286c9d6df84598f260119fd29c63f800c07d8df83d5cc95f8c2fea2812e7890e8a0718bb1e031ecbebc0436dcf3e3b9a58bcc06b4c17f711f80fe1dffc3326a6eb6e00283055c6dabe20d311bfd5019591b7954f8163c9afad9ef8390a38f3582e0a79cdf0353de8eeb6b5f9f27b16ffdef7dd62869b4840ee226ccdce95e02c4545eb981b60571cd83f03dc5eaf8c97a0829a4318a9b3dc06c0e003db700b2260ff1fa8fee66890e637b109abb03ec901b05ca599775f48af50154c0e67d82bf0f558d7d3e0778dc38bea1eb5f74dc8d7f90abdf5511a424be66bf8b6a3cacb477d2e7ef4db68d2eba4d5289122d851f9501ba7e9c4957d8eba3be3fc8e785c4265a1d65c46f2809b70846c693864b169c9dcb78be26ea14b8613f145b01887222979a9e67aee5f800caa6f5c4229bdeefc901232ace6143c9865e4d9c07f51aa200afaf7e48a7d1d8faf366023beab12906ffcb3eaf72c0eb68075e4daf3c080e0c31911befc16f0cc4a09908bb7c1e26abab38bd7b788e1a09c0edf1a35a38d2ff1d3ed47fcdaae2f0934224694f5b56705b9409b6d3d64f3833b686f7576ec64bbdd6ff174e56c2d1edac0011f904681a73face26573fbba4e34652f7ae84acfb2fa5a5b3046f98178cd0831df7477de70e06a4c00e305f31aafc026ef064dd68fd3e4252b1b91d617b26c6d09b6891a00df68f105b5962e7f9d82da101dd595d286da721443b72b2aba2377f6e7772e33b3a5e3753da9c2578c5d1daab80187f55518c72a64ee150a7cb5649823c08c9f62cd7d020b45ec2cba8310db1a7785a46ab24785b4d54ff1660b5ca78e05a9a55edba9c60bf044737bc468101c4e8bd1480d749be5024adefca1d998abe33eaeb6b11fbb39da5d905fdd3f611b2e51517ccee4b8af72c2d948573505590d61a6783ab7278fc43fe55b1fcc0e7216444d3c8039bb8145ef1ce01c50e95a3f3feab0aee883fdb94cc13ee4d21c542aa795e18932228981690f4d4c57ca4db6eb5c092e29d8a05139d509a8aeb48baa1eb97a76e597a32b280b5e9d6c36859064c98ff96ef5126130264fa8d2f49213870d9fb036cff95da51f270311d9976208554e48ffd486470d0ecdb4e619ccbd8226147204baf8e235f54d8b1cba8fa34a9a4d055de515cdf180d2bb6739a175183c472e30b5c914d09eeb1b7dafd6872b38b48c6afc146101200e6e6a44fe5684e220adc11f5c403ddb15df8051e6bdef09117a3a5349938513776286473a3cf1d2788bb875052a2e6459fa7926da33380149c7f98d7700528a60c954e6f5ecb65842fde69d614be69eaa2040a4819ae6e756accf936e14c1e894489744a79c1f2c1eb295d13e2d767c09964b61f9cfe497649f712,0,014e5bdbb1d7eb34a88a016ab3dd45e343dc703fafa8266907ab67a76c5eb2d6,568146140669e69646a6ffeb3793e8010e2732209b4c34ec13e209a070109183,10578110283044630bc13a9f12b00eb0af7cba9f53506add2b57ae07b3987ced,e500c670f1b32f60e05009bddcdbfa7153afb19c20479583a54b43d85b3433a8,67b155367abf65d45a60412e16bd5ef5e862aa0a4a7a56366cfcc602072176b8,93f5b4c59038c16c3f09793976c75e522bf994635e3f1ef9f04e628281e0d5f7,08fe46857ab4e62d7463c00ac510e041d28dbfc21853e8f4db971890c7330098,2271d5f5351a91ca768a83c5aa7f45fb2b2742e89351d93a680f51a030f9255c,3ba1f51de6272aa28fd21059b91d3893,faf3b317340de00e29f2181db270ff81,d083d09c1bdf71795b39a9534601cf7c7a7e767e578c44a17dfaf43a3c18f98c,6aa28bc4b6719eca144ac33a3f17859317d5450e4978db9365ce61e7085a617dd386ec18eb436c9056aa1d2d4736c9bffd25803d967fcae916ce1647ccae3d5258b17dfa1cdc7eb99581c48ff2898ef92d3aa1, 223,c0f15820459f64d98e5c48681d13340572c574533dd9f7161b85fcc8224fdf30,682871104d694baca8b9c7990ae6288f49e1ff4feb21dd5cffad67db7752fdfb6c3608d6996c54be04b35feef037da09ee4d9dca2363b343bc2d4f6d0ea609da,56bd0c06f10352c3a1a9f4b4c92f6fa2b26df124b57878353c1fc691c51abea77c8817daeeb9fa546b77c8daf79d89b22b0e1b87574ece42371f00237aa9d83a,0,7e0e78eb6990b059e6cf0ded66ea93ef82e72aa2f18ac24f2fc6ebab561ae557420729da103f64cecfa20527e15f9fb669a49bbbf274ef0389b3e43c8c44e5f60bf2ac38e2b55e7ec4273dba15ba41d21f8f5b3ee1688b3c29951218caf847a97fb50d75a86515d445699497d968164bf740012679b8962de573be941c62b7ef,1,,1,5d673dd0a75ccacf4e1310e9402ecdacdd474d8bbfa6eeefdde2e1b216d41dbe,2dd7b9cc85524f8670f695c3143ac26b45cebcabb2782a85e0fe15aee3956535,1c229ba46fadced7217df782d410961c1399375135e4aa718fa3424ec36539cc,b764f617cf8c8dcf6018e4f5e8ee603a086498a3732621c9b0fc0a485ea0d2f0,e25747c749e78c7a0102352378f7c15566145b57f082f7e10b10a0606b323996,c0547fbf3082c7a0377b4e709b982ecb4710012dcf3b0c073ed3811a2b7c1309,5bb291885bf5b08a4218c2bf3498d3591be93a47412c770b60299c8e740ac560,fdf5a3e3e75afc15a924373e58af505052731efa75c76a1fa3546954d60b50b1,8461c1dc173be7e6a2316d09710ebd8d,dfa2d33623fe80e2347999e6de0f96fd,279a96e6ce08e5074608fcad77d6a78f90c8b618a4520575435b1a37b1c56df9,,5afbd61f6e989833df2f12ff70c98f1a20ebe84acba2a05429cc6a57238dba87cdc432474f378889b2d0e95ade9f892eb1a1f6b03b73f903682476537f653f738f7a9f1cc9856ed75f3d69122bdeb00af48e66a64872f639a67fc109ee5ca124d0ee183da3c2b8f2da828850b50976b491f1add78d7f01e07565570621266852 448,96cb391886681d1d3e23948e51987771a8ec3001b640c18fb994a855cea66b6e,ffffffffffffffffffffffffffffffffffffffffffffffffffffffffdde3a077a6fd73711a27250c439ba78ef63d89cd0918c0a0a75f301ed96aa2a43ecf3f61,ffffffffffffffffffffffffffffffffffffffffffffffffffffffffa7730be30000000000000000000000000000000000000000000000000000000000000000,1,00cf68f8f7ac49ffaa02c4864fdf6dfe7bbf2c740b88d98c50ebafe32c92f3427f57601ffcb21a3435979287db8fee6c302926741f9d5e464c647eeb9b7acaeda46e00abd7506fc9a719847e9a7328215801e96198dac141a15c7c2f68e0690dd1176292a0dded04d1f548aad88f1aebdc0a8f87da4bb22df32dd7c160c225b843e83f6525d6d484f502f16d923124fc538794e21da2eb689d18d87406ecced5b9f92137239ed1d37bcfa7836641a83cf5e0a1cf63f51b06f158e499a459ede41c,1,,0,f7561c791f6f4aa73dcef3cac32f2433b4cfa4ab0666e93552b7cbc7249fb2de,5232c4b6bde9d3d45d7b763ebd7495399bb825cc21de51011761cd81a51bdc84,2651a46a622f79e2ab18819587e7f897e3f8351b1e1b66d8ed4543a1e40bc569,779a18107756169a6b369d043f3ef9a90178c7ab8c8c37b4edcd9b5397e41eca,368c7283e088e40b79e6214046beab64cbac30a89940acbc30d430f941fe7d35,224065c728d5cdabbe209cd52621324471ce8dc229907c018cec05781a9c770d,9ce33c019a081e5f8b62e1f12d652f0b036ed65f5de195d931dfcd92043b5eb2,001e576d8828a6d84913b01cb88e8f5532207f34275017b61650ba1383646cbc,7bf55f6b58f73cdff19ee3292607239f,d121874372c61a48fd87da6d01d89da4,e9515794acced50e0550a3ebd95c170d2abd48b5f23fccca73bc597f00c88cf2,,33953941be2682da1c6d1b167cbf180d7cb8159c94c6ea1c52356716f1057af4df53321f18894c285f7b2fd85b2edc44a13c9295f310962fdfc8d944bd77c5500b10ca68ca5d0977d19d183a7def742c41cfeee763dc09ef985c96ab6e74e464f66992f752c9368e42082ad338705062ddfcad4ca1c9c54004b9345d8df25953 673,4a7065c3ddbf84e29b8e20da0da3aaae1f708eae8ad1af4c4c00f46a7cda7b6b,ffffffffffffffffffffffffffffffffffffffffffffffffffffffff450012ec3aeecf516f4b374af2e7fbb040e92dc3c0f12eafd00c729a137f4e892e5293c3,9652d78baefc028cd37a6a92625b8b8f85fde1e4c944ad3f20e198bef8c02f19fffffffffffffffffffffffffffffffffffffffffffffffffffffffff2e91870,0,5c6272ee55da855bbbf7b1246d9885aa7aa601a715ab86fa46c50da533badf82b97597c968293ae04e,97561,,0,a0ff3dd41ca11036eea75ea08993c938894c7eebca99354ac2e0daa8a1a6b2ca,64c383e0e78ac99476ddff2061683eeefa505e3666673a1371342c3e6c26981d,ca3f58a228c530be63eec8a427d16496776aefb22e693152a3a9394b9a87d097,a993062a328371beecae7e2b05a34355c1cefbad7f855ad48331dcf002972999,24cdf9d8533696a5795cadcf5b94826ddbe5f047ba02c832b3495ac7c1110e31,7b5d1c66668d20d57a4e0a6ba4d9aa3e3ba0f704697aa7edb9ce9471d46647da,e6a808d35ee403b3f4bbcd8fd49fa005a40dfaaf36f9f504318bb94637067060,d6ae42117344fb71cb1817a1dc192a4b5bb35d885005093c3e9bd4576069b217,1fec304dcaacf1f5b088325306272d78,d2d16a8452807baa4f63b059b5804624,dccb606c4f2a0f64bc164dbc00eb0f6cf1474575e89d7928be6346720bb53610,,58daef966f33c036740aeb3f6a4b31c0f0a070b25fd6a1abf82ef56fc2cb3ca8da8c434f23790c69349dd0cb4058f88a7bd0e333c8ceba3c80f21e951b9fdb1c84e2e7f49f43c21087566d58f1bcc42b041e0b462e37e927c0071caa9a2b650dccf448c9f88d73b62e80a3e5d5e4e46992e34b416ceb9590a7c8b7bfaccf37ab 1024,0f69aeffeff6172647ee5aa80bfb418ee742f4e9f1a51b463ac7c120d620e37d,ffffffffffffffffffffffffffffffffffffffffffffffffffffffff04df0e67f9753e2cdb066b3b588a0069fde936a312e0d3f31acb335026b7072d8f2ad24c,12a50f3fafea7c1eeada4cf8d33777704b77361453afc83bda91eef349ae044d20126c6200547ea5a6911776c05dee2a7f1a9ba7dfbabbbd273c3ef29ef46e46,1,5f67d15d22ca9b2804eeab0a66f7f8e3a10fa5de5809a046084348cbc5304e843ef96f59a59c7d7fdfe5946489f3ea297d941bac326225df316a25fc90f0e65b0d31a9c497e960fdbf8c482516bc8a9c1c77b7f6d0e1143810c737f76f9224e6f2c9af5186b4f7259c7e8d165b6e4fe3d38a60bdbdd4d06ecdcaaf62086070dbb68686b802d53dfd7db14b18743832605f5461ad81e2af4b7e8ff0eff0867a25b93cec7becf15c43131895fed09a83bf1ee4a87d44dd0f02a837bf5a1232e201cb882734eb9643dc2dc4d4e8b5690840766212c7ac8f38ad8a9ec47c7a9b3e022ae3eb6a32522128b518bd0d0085dd81c5,69615,,1,115b298a52a9362706ddd1e493de09443dd8ac2b0c3e4e5e8b6bb295598db05d,eef379db9bd4b1aa90fc347fad33f7d53083389e22e971036f59f4e29d325ac2,32e15c20a09591b6600c778752a582fed444444fd0d3317613555c6509ff4b8d,1756deace376ece25da9825fe49f76a9272a89a7b746c83ca2c4016f5a30ead4,15e26b12238d66ebc4cb72d16a62a8bb404c94d31bbe3b1d22a01b851e935010,c135367f39b24a9cc9b73ad628fba1887737f5686062c4c36146e76849828a50,ffa25ddf7cd4cd10a47f6c3b32a54ee882837058e31677d3958539f4f23e4616,12f9b3ebbf743f6b93c7d0f4f20259fac2a27ea6735fd9ef2e2699049af60fcc,4dfac3b0a99401f6aad1a8df3cd7dd05,e5d4905a8b6a5d18ec6cebbdecd703d3,fc2431beb9a666bf888df0662276a4b6a1af5061072992ef408f2b686c86a2ac,,1a7f3fb83ad2b050b663b8df6b7c2cc2d8e169a869a58bf7ef5ab5db97a505c84a812e100d9445da4fc39a1176d6aed3995f6868631224b86f10603217c8d13270e0c6d054ad9e0d0b7dc0c8e59a37cd05a0a45faa14b4ffc8d12b641f62e6f1b71c1f72b737e9ce3fe74be779b25e70bf11d98766b3876d0fa28d3c669087fc ================================================ FILE: bip-0324/reference.py ================================================ """Reference implementation for the cryptographic aspects of BIP-324""" import sys import random import hashlib import hmac ### BIP-340 tagged hash def TaggedHash(tag, data): """Compute BIP-340 tagged hash with specified tag string of data.""" ss = hashlib.sha256(tag.encode('utf-8')).digest() ss += ss ss += data return hashlib.sha256(ss).digest() ### HKDF-SHA256 def hmac_sha256(key, data): """Compute HMAC-SHA256 from specified byte arrays key and data.""" return hmac.new(key, data, hashlib.sha256).digest() def hkdf_sha256(length, ikm, salt, info): """Derive a key using HKDF-SHA256.""" if len(salt) == 0: salt = bytes([0] * 32) prk = hmac_sha256(salt, ikm) t = b"" okm = b"" for i in range((length + 32 - 1) // 32): t = hmac_sha256(prk, t + info + bytes([i + 1])) okm += t return okm[:length] ### secp256k1 field/group elements def modinv(a, n): """Compute the modular inverse of a modulo n using the extended Euclidean Algorithm. See https://en.wikipedia.org/wiki/Extended_Euclidean_algorithm#Modular_integers. """ a = a % n if a == 0: return 0 if sys.hexversion >= 0x3080000: # A more efficient version is available in Python 3.8. return pow(a, -1, n) t1, t2 = 0, 1 r1, r2 = n, a while r2 != 0: q = r1 // r2 t1, t2 = t2, t1 - q * t2 r1, r2 = r2, r1 - q * r2 if r1 > 1: return None if t1 < 0: t1 += n return t1 class FE: """Objects of this class represent elements of the field GF(2**256 - 2**32 - 977). They are represented internally in numerator / denominator form, in order to delay inversions. """ SIZE = 2**256 - 2**32 - 977 def __init__(self, a=0, b=1): """Initialize an FE as a/b; both a and b can be ints or field elements.""" if isinstance(b, FE): if isinstance(a, FE): self.num = (a.num * b.den) % FE.SIZE self.den = (a.den * b.num) % FE.SIZE else: self.num = (a * b.den) % FE.SIZE self.den = b.num else: b = b % FE.SIZE assert b != 0 if isinstance(a, FE): self.num = a.num self.den = (a.den * b) % FE.SIZE else: self.num = a % FE.SIZE self.den = b def __add__(self, a): """Compute the sum of two field elements (second may be int).""" if isinstance(a, FE): return FE(self.num * a.den + self.den * a.num, self.den * a.den) return FE(self.num + self.den * a, self.den) def __radd__(self, a): """Compute the sum of an integer and a field element.""" return FE(self.num + self.den * a, self.den) def __sub__(self, a): """Compute the difference of two field elements (second may be int).""" if isinstance(a, FE): return FE(self.num * a.den - self.den * a.num, self.den * a.den) return FE(self.num - self.den * a, self.den) def __rsub__(self, a): """Compute the difference between an integer and a field element.""" return FE(self.den * a - self.num, self.den) def __mul__(self, a): """Compute the product of two field elements (second may be int).""" if isinstance(a, FE): return FE(self.num * a.num, self.den * a.den) return FE(self.num * a, self.den) def __rmul__(self, a): """Compute the product of an integer with a field element.""" return FE(self.num * a, self.den) def __truediv__(self, a): """Compute the ratio of two field elements (second may be int).""" return FE(self, a) def __rtruediv__(self, a): """Compute the ratio of an integer and a field element.""" return FE(a, self) def __pow__(self, a): """Raise a field element to a (positive) integer power.""" return FE(pow(self.num, a, FE.SIZE), pow(self.den, a, FE.SIZE)) def __neg__(self): """Negate a field element.""" return FE(-self.num, self.den) def __int__(self): """Convert a field element to an integer. The result is cached.""" if self.den != 1: self.num = (self.num * modinv(self.den, FE.SIZE)) % FE.SIZE self.den = 1 return self.num def sqrt(self): """Compute the square root of a field element. Due to the fact that our modulus p is of the form p = 3 (mod 4), the Tonelli-Shanks algorithm (https://en.wikipedia.org/wiki/Tonelli-Shanks_algorithm) is simply raising the argument to the power (p + 1) / 4. To see why: p-1 = 0 (mod 2), so 2 divides the order of the multiplicative group, and thus only half of the non-zero field elements are squares. An element a is a (nonzero) square when Euler's criterion, a^((p-1)/2) = 1 (mod p), holds. We're looking for x such that x^2 = a (mod p). Given a^((p-1)/2) = 1 (mod p), that is equivalent to x^2 = a^(1 + (p-1)/2) (mod p). As (1 + (p-1)/2) is even, this is equivalent to x = a^((1 + (p-1)/2)/2) (mod p), or x = a^((p+1)/4) (mod p).""" v = int(self) s = pow(v, (FE.SIZE + 1) // 4, FE.SIZE) if s**2 % FE.SIZE == v: return FE(s) return None def sqrts(self): """Compute all square roots of a field element, if any.""" s = self.sqrt() if s is None: return [] return [FE(s), -FE(s)] # The cube roots of 1 (mod p). CBRT1 = [ 1, 0x851695d49a83f8ef919bb86153cbcb16630fb68aed0a766a3ec693d68e6afa40, 0x7ae96a2b657c07106e64479eac3434e99cf0497512f58995c1396c28719501ee ] def cbrts(self): """Compute all cube roots of a field element, if any. Due to the fact that our modulus p is of the form p = 7 (mod 9), one cube root can always be computed by raising to the power of (p + 2) / 9. The other roots (if any) can be found by multiplying with the two non-trivial cube roots of 1. To see why: p-1 = 0 (mod 3), so 3 divides the order of the multiplicative group, and thus only 1/3 of the non-zero field elements are cubes. An element a is a (nonzero) cube when a^((p-1)/3) = 1 (mod p). We're looking for x such that x^3 = a (mod p). Given a^((p-1)/3) = 1 (mod p), that is equivalent to x^3 = a^(1 + (p-1)/3) (mod p). As (1 + (p-1)/3) is a multiple of 3, this is equivalent to x = a^((1 + (p-1)/3)/3) (mod p), or x = a^((p+2)/9) (mod p).""" v = int(self) c = pow(v, (FE.SIZE + 2) // 9, FE.SIZE) if pow(c, 3, FE.SIZE) == v: return [FE(c * f) for f in FE.CBRT1] return [] def is_square(self): """Determine if this field element has a square root.""" # Compute the Jacobi symbol of (self / p). Since our modulus is prime, this # is the same as the Legendre symbol, which determines quadratic residuosity. # See https://en.wikipedia.org/wiki/Jacobi_symbol for the algorithm. n, k, t = (self.num * self.den) % FE.SIZE, FE.SIZE, 0 if n == 0: return True while n != 0: while n & 1 == 0: n >>= 1 r = k & 7 t ^= (r in (3, 5)) n, k = k, n t ^= (n & k & 3 == 3) n = n % k assert k == 1 return not t def __eq__(self, a): """Check whether two field elements are equal (second may be an int).""" if isinstance(a, FE): return (self.num * a.den - self.den * a.num) % FE.SIZE == 0 return (self.num - self.den * a) % FE.SIZE == 0 def to_bytes(self): """Convert a field element to 32-byte big endian encoding.""" return int(self).to_bytes(32, 'big') @staticmethod def from_bytes(b): """Convert a 32-byte big endian encoding of a field element to an FE.""" v = int.from_bytes(b, 'big') if v >= FE.SIZE: return None return FE(v) def __str__(self): """Convert this field element to a string.""" return f"{int(self):064x}" def __repr__(self): """Get a string representation of this field element.""" return f"FE(0x{int(self):x})" assert all(pow(c, 3, FE.SIZE) == 1 for c in FE.CBRT1) class GE: """Objects of this class represent points (group elements) on the secp256k1 curve. The point at infinity is represented as None.""" ORDER = 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141 ORDER_HALF = ORDER // 2 def __init__(self, x, y): """Initialize a group element with specified x and y coordinates (must be on curve).""" fx = FE(x) fy = FE(y) assert fy**2 == fx**3 + 7 self.x = fx self.y = fy def double(self): """Compute the double of a point.""" l = 3 * self.x**2 / (2 * self.y) x3 = l**2 - 2 * self.x y3 = l * (self.x - x3) - self.y return GE(x3, y3) def __add__(self, a): """Add two points, or a point and infinity, together.""" if a is None: # Adding point at infinity return self if self.x != a.x: # Adding distinct x coordinates l = (a.y - self.y) / (a.x - self.x) x3 = l**2 - self.x - a.x y3 = l * (self.x - x3) - self.y return GE(x3, y3) if self.y == a.y: # Adding point to itself return self.double() # Adding point to its negation return None def __radd__(self, a): """Add infinity to a point.""" assert a is None return self def __mul__(self, a): """Multiply a point with an integer (scalar multiplication).""" r = None for i in range(a.bit_length() - 1, -1, -1): if r is not None: r = r.double() if (a >> i) & 1: r += self return r def __rmul__(self, a): """Multiply an integer with a point (scalar multiplication).""" return self * a @staticmethod def lift_x(x): """Take an FE, and return the point with that as X coordinate, and square Y.""" y = (FE(x)**3 + 7).sqrt() if y is None: return None return GE(x, y) @staticmethod def is_valid_x(x): """Determine whether the provided field element is a valid X coordinate.""" return (FE(x)**3 + 7).is_square() def __str__(self): """Convert this group element to a string.""" return f"({self.x},{self.y})" def __repr__(self): """Get a string representation for this group element.""" return f"GE(0x{int(self.x)},0x{int(self.y)})" SECP256K1_G = GE( 0x79BE667EF9DCBBAC55A06295CE870B07029BFCDB2DCE28D959F2815B16F81798, 0x483ADA7726A3C4655DA4FBFC0E1108A8FD17B448A68554199C47D08FFB10D4B8) ### ElligatorSwift # Precomputed constant square root of -3 (mod p). MINUS_3_SQRT = FE(-3).sqrt() def xswiftec(u, t): """Decode field elements (u, t) to an X coordinate on the curve.""" if u == 0: u = FE(1) if t == 0: t = FE(1) if u**3 + t**2 + 7 == 0: t = 2 * t X = (u**3 + 7 - t**2) / (2 * t) Y = (X + t) / (MINUS_3_SQRT * u) for x in (u + 4 * Y**2, (-X / Y - u) / 2, (X / Y - u) / 2): if GE.is_valid_x(x): return x assert False def xswiftec_inv(x, u, case): """Given x and u, find t such that xswiftec(u, t) = x, or return None. Case selects which of the up to 8 results to return.""" if case & 2 == 0: if GE.is_valid_x(-x - u): return None v = x s = -(u**3 + 7) / (u**2 + u*v + v**2) else: s = x - u if s == 0: return None r = (-s * (4 * (u**3 + 7) + 3 * s * u**2)).sqrt() if r is None: return None if case & 1 and r == 0: return None v = (-u + r / s) / 2 w = s.sqrt() if w is None: return None if case & 5 == 0: return -w * (u * (1 - MINUS_3_SQRT) / 2 + v) if case & 5 == 1: return w * (u * (1 + MINUS_3_SQRT) / 2 + v) if case & 5 == 4: return w * (u * (1 - MINUS_3_SQRT) / 2 + v) if case & 5 == 5: return -w * (u * (1 + MINUS_3_SQRT) / 2 + v) def xelligatorswift(x): """Given a field element X on the curve, find (u, t) that encode them.""" while True: u = FE(random.randrange(1, GE.ORDER)) case = random.randrange(0, 8) t = xswiftec_inv(x, u, case) if t is not None: return u, t def ellswift_create(): """Generate a (privkey, ellswift_pubkey) pair.""" priv = random.randrange(1, GE.ORDER) u, t = xelligatorswift((priv * SECP256K1_G).x) return priv.to_bytes(32, 'big'), u.to_bytes() + t.to_bytes() def ellswift_decode(ellswift): """Convert ellswift encoded X coordinate to 32-byte xonly format.""" u = FE(int.from_bytes(ellswift[:32], 'big')) t = FE(int.from_bytes(ellswift[32:], 'big')) return xswiftec(u, t).to_bytes() def ellswift_ecdh_xonly(pubkey_theirs, privkey): """Compute X coordinate of shared ECDH point between elswift pubkey and privkey.""" d = int.from_bytes(privkey, 'big') pub = ellswift_decode(pubkey_theirs) return (d * GE.lift_x(FE.from_bytes(pub))).x.to_bytes() ### Poly1305 class Poly1305: """Class representing a running poly1305 computation.""" MODULUS = 2**130 - 5 def __init__(self, key): self.r = int.from_bytes(key[:16], 'little') & 0xffffffc0ffffffc0ffffffc0fffffff self.s = int.from_bytes(key[16:], 'little') self.acc = 0 def add(self, msg, length=None, pad=False): """Add a message of any length. Input so far must be a multiple of 16 bytes.""" length = len(msg) if length is None else length for i in range((length + 15) // 16): chunk = msg[i * 16:i * 16 + min(16, length - i * 16)] val = int.from_bytes(chunk, 'little') + 256**(16 if pad else len(chunk)) self.acc = (self.r * (self.acc + val)) % Poly1305.MODULUS return self def tag(self): """Compute the poly1305 tag.""" return ((self.acc + self.s) & 0xffffffffffffffffffffffffffffffff).to_bytes(16, 'little') ### ChaCha20 CHACHA20_INDICES = ( (0, 4, 8, 12), (1, 5, 9, 13), (2, 6, 10, 14), (3, 7, 11, 15), (0, 5, 10, 15), (1, 6, 11, 12), (2, 7, 8, 13), (3, 4, 9, 14) ) CHACHA20_CONSTANTS = (0x61707865, 0x3320646e, 0x79622d32, 0x6b206574) def rotl32(v, bits): """Rotate the 32-bit value v left by bits bits.""" return ((v << bits) & 0xffffffff) | (v >> (32 - bits)) def chacha20_doubleround(s): """Apply a ChaCha20 double round to 16-element state array s. See https://cr.yp.to/chacha/chacha-20080128.pdf and https://tools.ietf.org/html/rfc8439 """ for a, b, c, d in CHACHA20_INDICES: s[a] = (s[a] + s[b]) & 0xffffffff s[d] = rotl32(s[d] ^ s[a], 16) s[c] = (s[c] + s[d]) & 0xffffffff s[b] = rotl32(s[b] ^ s[c], 12) s[a] = (s[a] + s[b]) & 0xffffffff s[d] = rotl32(s[d] ^ s[a], 8) s[c] = (s[c] + s[d]) & 0xffffffff s[b] = rotl32(s[b] ^ s[c], 7) def chacha20_block(key, nonce, cnt): """Compute the 64-byte output of the ChaCha20 block function. Takes as input a 32-byte key, 12-byte nonce, and 32-bit integer counter. """ # Initial state. init = [0 for _ in range(16)] for i in range(4): init[i] = CHACHA20_CONSTANTS[i] for i in range(8): init[4 + i] = int.from_bytes(key[4 * i:4 * (i+1)], 'little') init[12] = cnt for i in range(3): init[13 + i] = int.from_bytes(nonce[4 * i:4 * (i+1)], 'little') # Perform 20 rounds. state = list(init) for _ in range(10): chacha20_doubleround(state) # Add initial values back into state. for i in range(16): state[i] = (state[i] + init[i]) & 0xffffffff # Produce byte output return b''.join(state[i].to_bytes(4, 'little') for i in range(16)) ### ChaCha20Poly1305 def aead_chacha20_poly1305_encrypt(key, nonce, aad, plaintext): """Encrypt a plaintext using ChaCha20Poly1305.""" ret = bytearray() msg_len = len(plaintext) for i in range((msg_len + 63) // 64): now = min(64, msg_len - 64 * i) keystream = chacha20_block(key, nonce, i + 1) for j in range(now): ret.append(plaintext[j + 64 * i] ^ keystream[j]) poly1305 = Poly1305(chacha20_block(key, nonce, 0)[:32]) poly1305.add(aad, pad=True).add(ret, pad=True) poly1305.add(len(aad).to_bytes(8, 'little') + msg_len.to_bytes(8, 'little')) ret += poly1305.tag() return bytes(ret) def aead_chacha20_poly1305_decrypt(key, nonce, aad, ciphertext): """Decrypt a ChaCha20Poly1305 ciphertext.""" if len(ciphertext) < 16: return None msg_len = len(ciphertext) - 16 poly1305 = Poly1305(chacha20_block(key, nonce, 0)[:32]) poly1305.add(aad, pad=True) poly1305.add(ciphertext, length=msg_len, pad=True) poly1305.add(len(aad).to_bytes(8, 'little') + msg_len.to_bytes(8, 'little')) if ciphertext[-16:] != poly1305.tag(): return None ret = bytearray() for i in range((msg_len + 63) // 64): now = min(64, msg_len - 64 * i) keystream = chacha20_block(key, nonce, i + 1) for j in range(now): ret.append(ciphertext[j + 64 * i] ^ keystream[j]) return bytes(ret) ### FSChaCha20{,Poly1305} REKEY_INTERVAL = 224 # packets class FSChaCha20Poly1305: """Rekeying wrapper AEAD around ChaCha20Poly1305.""" def __init__(self, initial_key): self.key = initial_key self.packet_counter = 0 def crypt(self, aad, text, is_decrypt): """Encrypt or decrypt the specified (plain/cipher)text.""" nonce = ((self.packet_counter % REKEY_INTERVAL).to_bytes(4, 'little') + (self.packet_counter // REKEY_INTERVAL).to_bytes(8, 'little')) if is_decrypt: ret = aead_chacha20_poly1305_decrypt(self.key, nonce, aad, text) else: ret = aead_chacha20_poly1305_encrypt(self.key, nonce, aad, text) if (self.packet_counter + 1) % REKEY_INTERVAL == 0: rekey_nonce = b"\xFF\xFF\xFF\xFF" + nonce[4:] newkey1 = aead_chacha20_poly1305_encrypt(self.key, rekey_nonce, b"", b"\x00" * 32)[:32] newkey2 = chacha20_block(self.key, rekey_nonce, 1)[:32] assert newkey1 == newkey2 self.key = newkey1 self.packet_counter += 1 return ret def encrypt(self, aad, plaintext): """Encrypt the specified plaintext with provided AAD.""" return self.crypt(aad, plaintext, False) def decrypt(self, aad, ciphertext): """Decrypt the specified ciphertext with provided AAD.""" return self.crypt(aad, ciphertext, True) class FSChaCha20: """Rekeying wrapper stream cipher around ChaCha20.""" def __init__(self, initial_key): self.key = initial_key self.block_counter = 0 self.chunk_counter = 0 self.keystream = b'' def get_keystream_bytes(self, nbytes): """Generate nbytes keystream bytes.""" while len(self.keystream) < nbytes: nonce = ((0).to_bytes(4, 'little') + (self.chunk_counter // REKEY_INTERVAL).to_bytes(8, 'little')) self.keystream += chacha20_block(self.key, nonce, self.block_counter) self.block_counter += 1 ret = self.keystream[:nbytes] self.keystream = self.keystream[nbytes:] return ret def crypt(self, chunk): """Encrypt or decrypt chunk.""" ks = self.get_keystream_bytes(len(chunk)) ret = bytes([ks[i] ^ chunk[i] for i in range(len(chunk))]) if ((self.chunk_counter + 1) % REKEY_INTERVAL) == 0: self.key = self.get_keystream_bytes(32) self.block_counter = 0 self.chunk_counter += 1 return ret def encrypt(self, chunk): """Encrypt chunk.""" return self.crypt(chunk) def decrypt(self, chunk): """Decrypt chunk.""" return self.crypt(chunk) ### Shared secret computation def v2_ecdh(priv, ellswift_theirs, ellswift_ours, initiating): """Compute BIP324 shared secret.""" ecdh_point_x32 = ellswift_ecdh_xonly(ellswift_theirs, priv) if initiating: # Initiating, place our public key encoding first. return TaggedHash("bip324_ellswift_xonly_ecdh", ellswift_ours + ellswift_theirs + ecdh_point_x32) # Responding, place their public key encoding first. return TaggedHash("bip324_ellswift_xonly_ecdh", ellswift_theirs + ellswift_ours + ecdh_point_x32) ### Key derivation NETWORK_MAGIC = b'\xf9\xbe\xb4\xd9' def initialize_v2_transport(ecdh_secret, initiating): """Return a peer object with various BIP324 derived keys and ciphers.""" peer = {} salt = b'bitcoin_v2_shared_secret' + NETWORK_MAGIC for name, length in ( ('initiator_L', 32), ('initiator_P', 32), ('responder_L', 32), ('responder_P', 32), ('garbage_terminators', 32), ('session_id', 32)): peer[name] = hkdf_sha256( salt=salt, ikm=ecdh_secret, info=name.encode('utf-8'), length=length) peer['initiator_garbage_terminator'] = peer['garbage_terminators'][:16] peer['responder_garbage_terminator'] = peer['garbage_terminators'][16:] del peer['garbage_terminators'] if initiating: peer['send_L'] = FSChaCha20(peer['initiator_L']) peer['send_P'] = FSChaCha20Poly1305(peer['initiator_P']) peer['send_garbage_terminator'] = peer['initiator_garbage_terminator'] peer['recv_L'] = FSChaCha20(peer['responder_L']) peer['recv_P'] = FSChaCha20Poly1305(peer['responder_P']) peer['recv_garbage_terminator'] = peer['responder_garbage_terminator'] else: peer['send_L'] = FSChaCha20(peer['responder_L']) peer['send_P'] = FSChaCha20Poly1305(peer['responder_P']) peer['send_garbage_terminator'] = peer['responder_garbage_terminator'] peer['recv_L'] = FSChaCha20(peer['initiator_L']) peer['recv_P'] = FSChaCha20Poly1305(peer['initiator_P']) peer['recv_garbage_terminator'] = peer['initiator_garbage_terminator'] return peer ### Packet encryption LENGTH_FIELD_LEN = 3 HEADER_LEN = 1 IGNORE_BIT_POS = 7 def v2_enc_packet(peer, contents, aad=b'', ignore=False): """Encrypt a BIP324 packet.""" assert len(contents) <= 2**24 - 1 header = (ignore << IGNORE_BIT_POS).to_bytes(HEADER_LEN, 'little') plaintext = header + contents aead_ciphertext = peer['send_P'].encrypt(aad, plaintext) enc_plaintext_len = peer['send_L'].encrypt(len(contents).to_bytes(LENGTH_FIELD_LEN, 'little')) return enc_plaintext_len + aead_ciphertext ================================================ FILE: bip-0324/run_test_vectors.py ================================================ """Run the BIP-324 test vectors.""" import csv import os import sys import reference FILENAME_PACKET_TEST = os.path.join(sys.path[0], 'packet_encoding_test_vectors.csv') FILENAME_XSWIFTEC_INV_TEST = os.path.join(sys.path[0], 'xswiftec_inv_test_vectors.csv') FILENAME_ELLSWIFT_DECODE_TEST = os.path.join(sys.path[0], 'ellswift_decode_test_vectors.csv') with open(FILENAME_PACKET_TEST, newline='', encoding='utf-8') as csvfile: print(f"Running {FILENAME_PACKET_TEST} tests...") reader = csv.DictReader(csvfile) for row in reader: in_initiating = int(row['in_initiating']) bytes_priv_ours = bytes.fromhex(row['in_priv_ours']) int_priv_ours = int.from_bytes(bytes_priv_ours, 'big') assert row['mid_x_ours'] == (int_priv_ours * reference.SECP256K1_G).x.to_bytes().hex() bytes_ellswift_ours = bytes.fromhex(row['in_ellswift_ours']) assert row['mid_x_ours'] == reference.ellswift_decode(bytes_ellswift_ours).hex() bytes_ellswift_theirs = bytes.fromhex(row['in_ellswift_theirs']) assert row['mid_x_theirs'] == reference.ellswift_decode(bytes_ellswift_theirs).hex() x_shared = reference.ellswift_ecdh_xonly(bytes_ellswift_theirs, bytes_priv_ours) assert row['mid_x_shared'] == x_shared.hex() shared_secret = reference.v2_ecdh(bytes_priv_ours, bytes_ellswift_theirs, bytes_ellswift_ours, in_initiating) assert row['mid_shared_secret'] == shared_secret.hex() peer = reference.initialize_v2_transport(shared_secret, in_initiating) assert row['mid_initiator_l'] == peer['initiator_L'].hex() assert row['mid_initiator_p'] == peer['initiator_P'].hex() assert row['mid_responder_l'] == peer['responder_L'].hex() assert row['mid_responder_p'] == peer['responder_P'].hex() assert row['mid_send_garbage_terminator'] == peer['send_garbage_terminator'].hex() assert row['mid_recv_garbage_terminator'] == peer['recv_garbage_terminator'].hex() assert row['out_session_id'] == peer['session_id'].hex() for _ in range(int(row['in_idx'])): reference.v2_enc_packet(peer, b"") ciphertext = reference.v2_enc_packet( peer, bytes.fromhex(row['in_contents']) * int(row['in_multiply']), bytes.fromhex(row['in_aad']), int(row['in_ignore'])) if len(row['out_ciphertext']): assert row['out_ciphertext'] == ciphertext.hex() if len(row['out_ciphertext_endswith']): assert ciphertext.hex().endswith(row['out_ciphertext_endswith']) with open(FILENAME_XSWIFTEC_INV_TEST, newline='', encoding='utf-8') as csvfile: print(f"Running {FILENAME_XSWIFTEC_INV_TEST} tests...") reader = csv.DictReader(csvfile) for row in reader: u = reference.FE.from_bytes(bytes.fromhex(row['u'])) x = reference.FE.from_bytes(bytes.fromhex(row['x'])) for case in range(8): ret = reference.xswiftec_inv(x, u, case) if ret is None: assert row[f"case{case}_t"] == "" else: assert row[f"case{case}_t"] == ret.to_bytes().hex() assert reference.xswiftec(u, ret) == x with open(FILENAME_ELLSWIFT_DECODE_TEST, newline='', encoding='utf-8') as csvfile: print(f"Running {FILENAME_ELLSWIFT_DECODE_TEST} tests...") reader = csv.DictReader(csvfile) for row in reader: ellswift = bytes.fromhex(row['ellswift']) assert reference.ellswift_decode(ellswift).hex() == row['x'] ================================================ FILE: bip-0324/secp256k1_test_vectors.py ================================================ """Convert the BIP-324 test vectors to secp256k1 code.""" import csv import reference import os import sys FILENAME_XSWIFTEC_INV_TEST = os.path.join(sys.path[0], 'xswiftec_inv_test_vectors.csv') FILENAME_ELLSWIFT_DECODE_TEST = os.path.join(sys.path[0], 'ellswift_decode_test_vectors.csv') def format_int(v): """Format 0 as "0", but other integers as 0x%08x.""" if v == 0: return "0" return f"0x{v:08x}" def format_fe(fe): """Format a field element constant as SECP256K1_FE_CONST code.""" vals = [(int(fe) >> (32 * (7 - i))) & 0xffffffff for i in range(8)] strs = ", ".join(format_int(v) for v in vals) return f"SECP256K1_FE_CONST({strs})" def output_xswiftec_inv_cases(): """Generate lines corresponding to the xswiftec_inv test cases.""" with open(FILENAME_XSWIFTEC_INV_TEST, newline='', encoding='utf-8') as csvfile: reader = csv.DictReader(csvfile) print("xswiftec_inv cases:") for row in reader: u = int.from_bytes(bytes.fromhex(row['u']), 'big') x = int.from_bytes(bytes.fromhex(row['x']), 'big') pat = sum(1< BIP: 324 Layer: Peer Services Title: Version 2 P2P Encrypted Transport Protocol Authors: Dhruv Mehta Tim Ruffing Jonas Schnelli Pieter Wuille Status: Deployed Type: Specification Assigned: 2019-03-08 License: BSD-3-Clause Version: 1.0.2 Replaces: 151 == Introduction == === Abstract === This document proposes a new Bitcoin P2P transport protocol, which features opportunistic encryption, a mild bandwidth reduction, and the ability to negotiate upgrades before exchanging application messages. === Copyright === This document is licensed under the 3-clause BSD license. === Motivation === Bitcoin is a permissionless network whose purpose is to reach consensus over public data. Since all data relayed in the Bitcoin P2P network is inherently public, and the protocol lacks a notion of cryptographic identities, peers talk to each other over unencrypted and unauthenticated connections. Nevertheless, this plaintext nature of the current P2P protocol (referred to as v1 in this document) has severe drawbacks in the presence of attackers: * While the relayed data itself is public in nature, the associated metadata may reveal private information and hamper privacy of users. For example, a global passive attacker eavesdropping on all Bitcoin P2P connections can trivially identify the source and timing of a transaction. * Since connections are unauthenticated, they can be tampered with at a low cost and often even with a low risk of detection. For example, an attacker can alter specific bytes of a connection (such as node flags) on-the-fly without the need to keep any state. * The protocol is self-revealing. For example, deep packet inspection can identify a P2P connection trivially because connections start with a fixed sequence of magic bytes. The ability to detect connections enables censorship and facilitates the aforementioned attacks as well as other attacks which require the attacker to control the connections of victims, e.g., eclipse attacks targeted at miners. This proposal for a new P2P protocol version (v2) aims to improve upon this by raising the costs for performing these attacks substantially, primarily through the use of unauthenticated, opportunistic transport encryption. In addition, the bytestream on the wire is made pseudorandom (i.e., indistinguishable from uniformly random bytes) to a passive eavesdropper. * Encryption, even when it is unauthenticated and only used when both endpoints support v2, impedes eavesdropping by forcing the attacker to become active: either by performing a persistent man-in-the-middle (MitM) attack, by downgrading connections to v1, or by spinning up their own nodes and getting honest nodes to make connections to them. Active attacks at scale are more resource intensive in general, but in the case of manual, deliberate connections (as opposed to automatic, random ones), they are also in principle detectable: even very basic checks, e.g., operators manually comparing protocol versions and session IDs (as supported by the proposed protocol), will expose the attacker. * Tampering, while already an inherently active attack, is costlier if the attacker is forced to maintain the state necessary for a full MitM interception. * A pseudorandom bytestream excludes identification techniques based on pattern matching, and makes it easier to shape the bytestream in order to mimic other protocols used on the Internet. This raises the cost of a connection censoring firewall, forcing them to either resort to a full MitM attack, or operate on a more obvious allowlist basis, rather than a blocklist basis. ''' Why encrypt without authentication?''' As we have argued above, unauthenticated encryption'''What does ''authentication'' mean in this context?''' Unfortunately, the term authentication in the context of secure channel protocols is ambiguous. It can refer to: * The encryption scheme guaranteeing that a message obtained via successful decryption was encrypted by someone having access to the (symmetric) encryption key, and not modified after encryption by a third party. The proposal in this document achieves that property through the use of an AEAD. * The communication protocol establishing that the communication partner's identity matches who we expect them to be, through some public key mechanism. The proposal in this document does '''not''' include such a mechanism. provides strictly better security than no encryption. Thus, all connections should use encryption, even if they are unauthenticated. When it comes to authentication, the situation is not as clear as for encryption. Due to Bitcoin's permissionless nature, authentication will always be restricted to specific scenarios (e.g., connections between peers belonging to the same operator), and whether some form of (possibly partially anonymous) authentication is desired depends on the specific requirements of the involved peers. As a consequence, we believe that authentication should be addressed separately (if desired), and this proposal aims to provide a solid technical basis for future protocol upgrades, including the addition of optional authentication (see [https://github.com/sipa/writeups/tree/main/private-authentication-protocols Private authentication protocols]). ''' Why have a pseudorandom bytestream when traffic analysis is still possible? ''' Traffic analysis, e.g., observing packet lengths and timing, as well as active attacks can still reveal that the Bitcoin v2 P2P protocol is in use. Nevertheless, a pseudorandom bytestream raises the cost of fingerprinting the protocol substantially, and may force some intermediaries to attack any protocol they cannot identify, causing collateral cost. A pseudorandom bytestream is not self-identifying. Moreover, it is unopinionated and thus a canonical choice for similar protocols. As a result, Bitcoin P2P traffic will be indistinguishable from traffic of other protocols which make the same choice (e.g., [https://gitlab.com/yawning/obfs4 obfs4] and a recently proposed [https://datatracker.ietf.org/doc/draft-cpbs-pseudorandom-ctls/ cTLS extension]). Moreover, traffic shapers and protocol wrappers (for example, making the traffic look like HTTPS or SSH) can further mitigate traffic analysis and active attacks but are out of scope for this proposal. ''' Why not use a secure tunnel protocol? ''' Our goal includes making opportunistic encryption ubiquitously available, as that provides the best defense against large-scale attacks. That implies protecting both the manual, deliberate connections node operators instruct their software to make, and the automatic connections Bitcoin nodes make with each other based on IP addresses obtained via gossip. While encryption per se is already possible with proxy networks or VPN protocols, these are not desirable or applicable for automatic connections at scale: * Proxy networks like Tor or I2P introduce a separate address space, independent of network topology, with a very low cost per address making eclipse attacks cheaper. In comparison, clearnet IPv4 and IPv6 networks make obtaining multiple network identities in distinct, well-known network partitions carry a non-trivial cost. Thus, it is not desirable to have a substantial portion of nodes be exclusively connected this way, as this would significantly reduce Eclipse attack costs.'''Why is it a bad idea to have nodes exclusively connected over Tor?''' See the [https://arxiv.org/abs/1410.6079 Bitcoin over Tor isn't a Good Idea] paper Additionally, Tor connections come with significant bandwidth and latency costs that may not be desirable for all network users. * VPN protocols like WireGuard or OpenVPN inherently define a private network, which requires manual configuration and therefore is not a realistic avenue for automatic connections. Thus, to achieve our goal, we need a solution that has minimal costs, works without configuration, and is always enabled – on top of any network layer rather than be part of the network layer. ''' Why not use a general-purpose transport encryption protocol? ''' While it would be possible to rely on an off-the-shelf transport encryption protocol such as TLS or Noise, the specific requirements of the Bitcoin P2P network laid out above make these protocols an unsuitable choice. The primary requirement which existing protocols fail to meet is a sufficiently modular treatment of encryption and authentication. As we argue above, whether and which form of authentication is desired in the Bitcoin P2P network will depend on the specific requirements of the involved peers (resulting in a mix of authenticated and unauthenticated connections), and thus the question of authentication should be decoupled from encryption. However, native support for a handful of standard authentication scenarios (e.g., using digital signatures and certificates) is at the core of the design of existing general-purpose transport encryption protocols. This focus on authentication would not provide clear benefits for the Bitcoin P2P network but would come with a large amount of additional complexity. In contrast, our proposal instead aims for a simple modular design that makes it possible to address authentication separately. Our proposal provides a foundation for authentication by exporting a ''session ID'' that uniquely identifies the encrypted channel. After an encrypted channel has been established, the two endpoints are able to use any authentication protocol to confirm that they have the same session ID. (This is sometimes called ''channel binding'' because the session ID binds the encrypted channel to the authentication protocol.) Since in our proposal, any authentication needs to run after an encrypted connection has been established, the price we pay for this modularity is a possibly higher number of roundtrips as opposed to other protocols that perform authentication alongside the Diffie-Hellman key exchange.'''Do other protocols not support exporting a session ID?''' While [https://noiseprotocol.org/noise.html#channel-binding Noise] and [https://datatracker.ietf.org/doc/draft-ietf-kitten-tls-channel-bindings-for-tls13/ TLS (as a draft)] offer similar protocol extensions for exporting session IDs, using channel binding for authentication is not at the focus of their design and would not avoid the bulk of additional complexity due to the native support of authentication methods. However, the resulting increase in connection establishment latency is a not a concern for Bitcoin's long-lived connections, [https://www.dsn.kastel.kit.edu/bitcoin/ which typically live for hours or even weeks]. Besides this fundamentally different treatment of authentication, further technical issues arise when applying TLS or Noise to our desired use case: * Neither offers a pseudorandom bytestream. * Neither offers native support for elliptic curve cryptography on the curve secp256k1 as otherwise used in Bitcoin. While using secp256k1 is not strictly necessary, it is the obvious choice is for any new asymmetric cryptography in Bitcoin because it minimizes the cryptographic hardness assumptions as well as the dependencies that Bitcoin software will need. * Neither offers shapability of the bytestream. * Both provide a stream-based interface to the application layer, whereas Bitcoin requires a packet-based interface, resulting in the need for an additional thin layer to perform packet serialization and deserialization. While existing protocols could be amended to address all of the aforementioned issues, this would negate the benefits of using them as off-the-shelf solution, e.g., the possibility to re-use existing implementations and security analyses. == Goals == This proposal aims to achieve the following properties: * Confidentiality against passive attacks: A passive attacker having recorded a v2 P2P bytestream (without timing and fragmentation information) must not be able to determine the plaintext being exchanged by the nodes. * Observability of active attacks: A session ID identifying the encrypted channel uniquely is derived deterministically from a Diffie-Hellman negotiation. An active man-in-the-middle attacker is forced to incur a risk of being detected as peer operators can compare session IDs manually, or using optional authentication methods possibly introduced in future protocol versions. * Pseudorandom bytestream: A passive attacker having recorded a v2 P2P bytestream (without timing information and fragmentation information) must not be able to distinguish it from a uniformly random bytestream. * Shapable bytestream: It should be possible to shape the bytestream to increase resistance to traffic analysis (for example, to conceal block propagation), or censorship avoidance.'''How can shapability help circumvent fragmentation-pattern based censoring?''' See [https://gitlab.torproject.org/legacy/trac/-/issues/20348#note_2229522 this Tor issue] as an example. * Forward secrecy: An eavesdropping attacker who compromises a peer's sessions secrets should not be able to decrypt past session traffic, except for the latest few packets. * Upgradability: The proposal provides an upgrade path using transport versioning which can be used to add features like authentication, PQC handshake upgrade, etc. in the future. * Compatibility: v2 clients will allow inbound v1 connections to minimize risk of network partitions. * Low overhead: the introduction of a new P2P transport protocol should not substantially increase computational cost or bandwidth for nodes that implement it, compared to the current protocol. == Specification == The specification consists of three parts: * The '''Transport layer''' concerns how to set up an encrypted connection between two nodes, capable of transporting application-level messages between them. * The '''Application layer''' concerns how to encode Bitcoin P2P messages and commands for transport by the Transport Layer. * The '''Signaling''' concerns how v2 nodes advertise their support for the v2 protocol to potential peers. === Transport layer specification === In this section, we define the encryption protocol for messages between peers. ==== Overview and design ==== We first give an informal overview of the entire protocol flow and packet encryption. '''Protocol flow overview''' Given a newly established connection (typically TCP/IP) between two v2 P2P nodes, there are 3 phases the connection goes through. The first starts immediately, i.e. there are no v1 messages or any other bytes exchanged on the link beforehand. The two parties are called the '''initiator''' (who established the connection) and the '''responder''' (who accepted the connection). # The '''Key exchange phase''', where nodes exchange data to establish shared secrets. #* The initiator: #** Generates a random ephemeral secp256k1 private key and sends a corresponding 64-byte ElligatorSwift'''What is ElligatorSwift and why use it?''' The [https://eprint.iacr.org/2022/759.pdf SwiftEC paper] describes a method called ElligatorSwift which allows encoding elliptic curve points in a way that is indistinguishable from a uniformly distributed bitstream. While a random 256-bit string has about 50% chance of being a valid X coordinate on the secp256k1 curve, every 512-bit string is a valid ElligatorSwift encoding of a curve point, making the encoded point indistinguishable from random when using an encoder that can sample uniformly.'''How fast is ElligatorSwift?''' Our benchmarks show that ElligatorSwift encoded ECDH is about 50% more expensive than unencoded ECDH. Given the fast performance of ECDH and the low frequency of new connections, we found the performance trade-off acceptable for the pseudorandom bytestream and future censorship resistance it can enable.-encoded public key to the responder. #** May send up to 4095'''How was the limit of 4095 bytes garbage chosen?''' It is a balance between having sufficient freedom to hide information, and allowing it to be large enough so that the necessary 64 bytes of public key is small compared to it on the one hand, and bandwidth waste on the other hand. bytes of arbitrary data after their public key, called '''garbage''', providing a form of shapability and avoiding a recognizable pattern of exactly 64 bytes.'''Why does the affordance for garbage exist in the protocol?''' The garbage strings after the public keys are needed for shapability of the handshake. Neither peer can send decoy packets before having received at least the other peer's public key, i.e., neither peer can send more than 64 bytes before having received 64 bytes. #* The responder: #** Waits until one byte is received which does not match the 16 bytes consisting of the network magic followed by "version\x00\x00\x00\x00\x00". If the first 16 bytes do match, the connection is treated as using the v1 protocol instead.'''What if a v2 initiator's public key starts accidentally with these 16 bytes?''' This is so unlikely (probability of ''2-128'') to happen randomly in the v2 protocol that the initiator does not need to specifically avoid it. The optional detection of wrong-network v1 peers has a probability of ''2-96'', which is still negligible compared to random network failures.Bitcoin Core versions <=0.4.0 and >=22.0 ignore valid P2P messages that are received prior to a VERSION message. Bitcoin Core versions between 0.4.0 and 22.0 assign a misbehavior score to the peer upon receiving such messages. v2 clients implementing this proposal will interpret any message other than VERSION received as the first message to be the initiation of a v2 connection, and will result in disconnection for v1 initiators that send any message type other than VERSION as the first message. We are not aware of any implementations where this could pose a problem. #** If the first 4 received bytes do not match the network magic, but the 12 bytes after that do match the version message encoding above, implementations may interpret this as a v1 peer of a different network, and disconnect them. #** Similarly generates a random ephemeral private key and sends a corresponding 64-byte ElligatorSwift-encoded public key to the initiator. #** Similarly may send up to 4095 bytes of garbage data after their public key. #* Both parties: #** Receive (the remainder of) the full 64-byte public key from the other side. #** Use X-only'''Why use X-only ECDH?''' Using only the X coordinate provides the same security as using a full encoding of the secret curve point but allows for more efficient implementation by avoiding the need for square roots to compute Y coordinates. ECDH to compute a shared secret from their private key and the exchanged public keys'''Why is the shared secret computation a function of the exact 64-byte public encodings sent?''' This makes sure that an attacker cannot modify the public key encoding used without modifying the rest of the stream. If a third party wants the ability to modify stream bytes, they need to perform a full MitM attack on the connection., and deterministically derive from the secret 4 '''encryption keys''' (two in each direction: one for packet lengths, one for content encryption), a '''session id''', and two 16-byte '''garbage terminators''''''What length is sufficient for garbage terminators?''' The length of the garbage terminators determines the probability of accidental termination of a legitimate v2 connection due to garbage bytes (sent prior to ECDH) inadvertently including the terminator. 16 byte terminators with 4095 bytes of garbage yield a negligible probability of such collision which is likely orders of magnitude lower than random connection failure on the Internet.'''What does a garbage terminator in the wild look like?'''
[[File:bip-0324/garbage_terminator.png|none|256px|A garbage terminator model TX-v2 in the wild... sent by the responder]]
(one in each direction) using HKDF-SHA256. #** Send their 16-byte garbage terminator.'''Why does the protocol need a garbage terminator?''' While it is in principle possible to use the first packet after the garbage directly as a terminator (scan until a valid packet follows), this would be significantly slower than just scanning for a fixed byte sequence, as it would require recomputing a Poly1305 tag after every received byte. #** Receive up to 4111 bytes, stopping when encountering the garbage terminator. #* At this point, both parties have the same keys, and all further communication proceeds in the form of '''encrypted packets'''. #** Encrypted packets have an '''ignore bit''', which makes them '''decoy packets''' if set. Decoy packets are to be ignored by the receiver apart from verifying they decrypt correctly. Either peer may send such decoy packets at any point from here on. These form the primary shapability mechanism in the protocol. How and when to use them is out of scope for this document. #** For each of the two directions, the first encrypted packet that will be sent in that direction (regardless of it being a decoy packet or not) will make use of the associated authenticated data (AAD) feature of the AEAD to authenticate the garbage that has been sent in that direction.'''Why does the protocol authenticate the garbage?''' Without garbage authentication, the garbage would be modifiable by a third party without consequences. We want to force any active attacker to have to maintain a full protocol state. In addition, such malleability without the consequence of connection termination could enable protocol fingerprinting. # The '''Version negotiation phase''', where parties negotiate what transport version they will use, as well as data defined by that version.'''What features could be added in future protocol versions?''' Examples of features that could be added in future versions include post-quantum cryptography upgrades to the handshake, and optional authentication. #* The responder: #** Sends a '''version packet''' with empty content, to indicate support for the v2 P2P protocol proposed by this document. Any other value for content is reserved for future versions. #* The initiator: #** Receives a packet, ignores its contents. The idea is that features added by future versions get negotiated based on what is supported by both parties. Since there is just one version so far, the contents here can simply be ignored. But in the future, receiving a non-empty contents here may trigger other behavior; we defer specifying the encoding for such version content until there is a need for it.'''How will future versions encode version numbers in the version packet?''' Future versions could, for example, specify that the contents of the version packet is to be interpreted as an integer version number (with empty representing 0), and if the minimum of both numbers is N, that being interpreted as choosing a "v2.N" protocol version. Alternatively, certain bytes of the version packet contents could be interpreted as a bitvector of optional features. #** Sends a '''version packet''' with empty content as well, to indicate support for the v2 P2P protocol. #* The responder: #** Receives a packet, ignores its contents. # The '''Application phase''', where the packets exchanged have contents to be interpreted as application data. #* Whenever either peer has a message to send, it sends a packet with that application message as '''contents'''. To avoid the recognizable pattern of first messages being at least 64 bytes, a future backwards-compatible upgrade to this protocol may allow both peers to send their public key + garbage + garbage terminator in multiple rounds, slicing those bytes up into messages arbitrarily, as long as progress is guaranteed.'''How can progress be guaranteed in a backwards-compatible way?''' In order to guarantee progress, it must be ensured that no deadlock occurs, i.e., no state is reached in which each party waits for the other party indefinitely. For example, any upgrade that adheres to the following conditions will guarantee progress: * The initiator must start by sending at least as many bytes as necessary to mismatch the magic/version 16 bytes prefix. * The responder must start sending after having received at least one byte that mismatches that 16-byte prefix. * As soon as either party has received the other peer's garbage terminator, or has received 4095 bytes of garbage, they must send their own garbage terminator. (When either of these conditions is met, the other party has nothing to respond with anymore that would be needed to guarantee progress otherwise.) * Whenever either party receives any nonzero number of bytes, while not having sent their garbage terminator completely yet, they must send at least one byte in response without waiting for more bytes. * After either party has sent their garbage terminator, they must transition to the version negotiation phase without waiting for more bytes. Since the protocol as specified here adheres to these conditions, any upgrade which also adheres to these conditions will be backwards-compatible. Note that the version negotiation phase does not need to wait for the key exchange phase to complete; version packets can be sent immediately after sending the garbage terminator. So the first two phases together, jointly called '''the handshake''', comprise just 1.5 roundtrips: * the initiator sends public key + garbage * the responder sends public key + garbage + garbage terminator + decoy packets (optional) + version packet * the initiator sends garbage terminator + decoy packets (optional) + version packet '''Packet encryption overview''' All data on the wire after the garbage terminators takes the form of encrypted packets. Every packet encodes an encrypted variable-length byte array, called the '''contents''', as well as an '''ignore bit''' as mentioned before. The total size of a packet is 20 bytes plus the length of its contents. Each packet consists of: * A 3-byte encrypted '''length''' field, encoding the length of the '''contents''' (between ''0'' and ''224-1'''''Is ''224-1'' bytes sufficient as maximum content size?''' The current Bitcoin P2P protocol has no messages which support more than 4000000 bytes of application payload. By supporting up to ''224-1'' we can accommodate future evolutions needing more than 4 times that value. Hypothetical protocol changes that have even more data to exchange than that should probably use multiple separate messages anyway, because of the per-peer receive buffer sizes involved, and the inability to start processing a message before it is fully received. Of course, future versions of the transport protocol could change the size of the length field, if this were really needed., inclusive). * An authenticated encryption of the '''plaintext''', which consists of: ** A 1-byte '''header''' which consists of transport layer protocol flags. Currently, only the highest bit is defined as the '''ignore bit'''. The other bits are ignored, but this may change in future versions'''Why is the header a part of the plaintext and not included alongside the length field?''' The packet length field is the minimum information that must be available before we can leverage the standard RFC8439 AEAD. Any other data, including metadata like the header being in the content encryption makes it easier to reason about the protocol security w.r.t. data being used before it is authenticated. If the ignore bit was not part of the content, another mechanism would be needed to authenticate it; for example, it could be fed as AAD to the AEAD cipher. We feel the complexity of such an approach outweighs the benefit of saving one byte per message.. ** The variable-length '''contents'''. The encryption of the plaintext uses '''[https://en.wikipedia.org/wiki/ChaCha20-Poly1305 ChaCha20Poly1305]''''''Why is ChaCha20Poly1305 chosen as the basis for packet encryption?''' It is a very widely used authenticated encryption cipher (used among others in SSH, TLS 1.2, TLS 1.3, [https://en.wikipedia.org/wiki/QUIC QUIC], Noise, and [https://www.wireguard.com/protocol/ WireGuard]; in the latter it is currently even the only supported cipher), with very good performance in general purpose software implementations. While AES-based ciphers (including the winners in the [https://competitions.cr.yp.to/caesar.html CAESAR] competition in non-lightweight categories) perform significantly better on systems with AES hardware acceleration, they are also significantly slower in pure software implementations. We choose to optimize for the weakest hardware., an [https://en.wikipedia.org/wiki/Authenticated_encryption authenticated encryption with associated data] (AEAD) cipher specified in [https://datatracker.ietf.org/doc/html/rfc8439 RFC 8439]. Every packet's plaintext is treated as a separate AEAD message, with a different nonce for each. The length must be dealt with specially, as it is needed to determine packet boundaries before the whole packet is received and authenticated. As we want a stream that is pseudorandom to a passive attacker, it still needs encryption. We use unauthenticated'''Why is the length encryption not separately authenticated?''' Informally, the relevant security goal we aim for is to hide the number of packets and their lengths (i.e., the packet boundaries) against a passive attacker that receives the bytestream without timing or fragmentation information. (A formal definition can be found for example in [https://himsen.github.io/pdf/thesis.pdf Hansen 2016 (Definition 22)] under the name "boundary hiding against chosen-plaintext attacks (BH-CPA)".) However, we do not aim to hide packet boundaries against active attackers because active attackers can always exploit the fact that the Bitcoin P2P protocol is largely query-response based: they can trickle the bytes on the stream one-by-one unmodified and observe when a response comes (see [https://himsen.github.io/pdf/thesis.pdf Hansen 2016 (Section 3.9)] for a in-depth discussion). With that in mind, we accept that an active (non-MitM) attacker is able to figure out some information about packet boundaries by flipping certain bits in the unauthenticated length field, and observing the other side disconnecting immediately or later. Thus, we choose to use unauthenticated encryption for the length data, which is sufficient to achieve boundary hiding against passive attackers, and saves 16 bytes of bandwidth per packet. '''ChaCha20''' encryption for this, with an independent key. Note that the plaintext length is still implicitly authenticated by the encryption of the plaintext, but this can only be verified after receiving the whole packet. This design is inspired by that of the ChaCha20Poly1305 cipher suite in [http://bxr.su/OpenBSD/usr.bin/ssh/PROTOCOL.chacha20poly1305 OpenSSH].'''How does packet encryption differ from the OpenSSH design?''' The differences are: * The length field is only 3 bytes instead of 4, as that is sufficient for our purposes. * Length encryption keeps drawing pseudorandom bytes from the same ChaCha20 cipher for multiple packets, rather than incrementing the nonce for every packet. * The Poly1305 authentication tag only covers the encrypted plaintext, and not the encrypted length field. This means that plaintext encryption uses the standard ChaCha20Poly1305 construction without any modifications, maximizing applicability of analysis and review of that cipher. The length encryption can be seen as a separate layer, using a separate key, and thus cannot affect any of the confidentiality or integrity guarantees of the plaintext encryption. On the other hand, this change w.r.t. OpenSSH also does not worsen any properties, as incorrect lengths will still trigger authentication failure for the overall packet (the plaintext length is implicitly authenticated by ChaCha20Poly1305). * A hash step is performed every 224'''How was the rekeying interval 224 chosen?''' Assuming a node sends only ping messages every 20 minutes (the timeout interval for post-[https://github.com/bitcoin/bips/blob/master/bip-0031.mediawiki BIP31] connections) on a connection, the node will transmit 224 packets in about 3.11 days. This means ''soft rekeying'' after a fixed number of packets automatically translates to an upper-bound of time interval for rekeying, while being much simpler to coordinate than an actual time-based rekeying regime. At the same time, doing it once every 224 messages is sufficiently infrequent that it has only negligible impact on performance. Furthermore, 224 times 3 bytes (the number of bytes consumed by each length encryption) is 672, which is a multiple of 64 minus 32. This means that at the end of 224 length encryptions, exactly 32 bytes of keystream data remain that can be used as next key. messages to rekey the encryption ciphers, in order to provide forward security. Because only fixed-length chunks (3-byte length fields) are encrypted, we do not need to treat all length chunks as separate messages. Instead, a single cipher (with the same nonce) is used for multiple consecutive length fields. This avoids wasting 61 pseudorandom bytes per packet, and makes the cost of having a separate cipher for length encryption negligible.'''Is it acceptable to use a less standard construction for length encryption?''' The fact that multiple (non-overlapping) bytes generated by a single ChaCha20 cipher are used for the encryption of multiple consecutive length fields is uncommon. We feel the performance cost gained by this deviation is worth it (especially for small packets, which are very common in Bitcoin's P2P protocol), given the low guarantees that are feasible for length encryption in the first place, and the result is still sufficient to provide pseudorandomness from the view of passive attackers. For plaintext encryption, we independently use a very standard construction, as the stakes for confidentiality and integrity there are much higher. In order to provide forward security'''What value does forward security provide?''' Re-keying ensures [https://eprint.iacr.org/2001/035.pdf forward secrecy within a session], i.e., an attacker compromising the current session secrets cannot derive past encryption keys in the same session.'''Why have a cipher with forward secrecy but no periodical refresh of the ECDH key exchange?''' Our cipher ratchets encryption keys forward in order to protect messages encrypted under ''past'' encryption keys. In contrast, re-performing ECDH key exchange would protect messages encrypted under ''future'' encryption keys, i.e., it would re-establish security after the attacker had compromised one of the peers ''temporarily'' (e.g., the attacker obtains a memory dump). We do not believe protecting against that is a priority: an attacker that, for whatever reason, is capable of an attack that reveals encryption keys (or other session secrets) of a peer once is likely capable of performing the same attack again after peers have re-performed the ECDH key exchange. Thus, we do not believe the benefits of re-performing key exchange outweigh the additional complexity that comes with the necessary coordination between the peers. We note that the initiator could choose to close and re-open the entire connection to force a refresh of the ECDH key exchange, but that introduces other issues: a connection slot needs to be kept open at the responder side, it is not cryptographically guaranteed that really the same initiator will use it, and the observable TCP reset and handshake may create a detectable pattern., the encryption keys for both plaintext and length encryption are cycled every 224 messages, by switching to a new key that is generated by the key stream using the old key. ==== Handshake: key exchange and version negotiation ==== Next we specify the handshake of a connection in detail. As explained before, these messages are sent to set up the connection:
 ----------------------------------------------------------------------------------------------------
 | Initiator                         Responder                                                      |
 |                                                                                                  |
 | x, ellswift_X = ellswift_create()                                                                |
 |                                                                                                  |
 |    ---- ellswift_X + initiator_garbage (initiator_garbage_len bytes; max 4095) --->              |
 |                                                                                                  |
 |                                   y, ellswift_Y = ellswift_create()                              |
 |                                   ecdh_secret = v2_ecdh(                                         |
 |                                                     y, ellswift_X, ellswift_Y, initiating=False) |
 |                                   v2_initialize(initiator, ecdh_secret, initiating=False)        |
 |                                                                                                  |
 |    <--- ellswift_Y + responder_garbage (responder_garbage_len bytes; max 4095) +                 |
 |             responder_garbage_terminator (16 bytes) +                                            |
 |             v2_enc_packet(initiator, RESPONDER_TRANSPORT_VERSION, aad=responder_garbage) ----    |
 |                                                                                                  |
 | ecdh_secret = v2_ecdh(x, ellswift_Y, ellswift_X, initiating=True)                                |
 | v2_initialize(responder, ecdh_secret, initiating=True)                                           |
 |                                                                                                  |
 |     ---- initiator_garbage_terminator (16 bytes) +                                               |
 |              v2_enc_packet(responder, INITIATOR_TRANSPORT_VERSION, aad=initiator_garbage) --->   |
 |                                                                                                  |
 ----------------------------------------------------------------------------------------------------
===== Shared secret computation ===== The peers derive their shared secret through X-only ECDH, hashed together with the exactly 64-byte public keys' encodings sent over the wire.
def v2_ecdh(priv, ellswift_theirs, ellswift_ours, initiating):
    ecdh_point_x32 = ellswift_ecdh_xonly(ellswift_theirs, priv)
    if initiating:
        # Initiating, place our public key encoding first.
        return sha256_tagged("bip324_ellswift_xonly_ecdh", ellswift_ours + ellswift_theirs + ecdh_point_x32)
    else:
        # Responding, place their public key encoding first.
        return sha256_tagged("bip324_ellswift_xonly_ecdh", ellswift_theirs + ellswift_ours + ecdh_point_x32)
Here, sha256_tagged(tag, x) returns a tagged hash value SHA256(SHA256(tag) || SHA256(tag) || x) as in [https://github.com/bitcoin/bips/blob/master/bip-0340.mediawiki#specification BIP340]. ===== ElligatorSwift encoding of curve X coordinates ===== The functions ellswift_create and ellswift_ecdh_xonly encapsulate the construction of ElligatorSwift-encoded public keys, and the computation of X-only ECDH with ElligatorSwift-encoded public keys. First we define a constant: * Let ''c = 0xa2d2ba93507f1df233770c2a797962cc61f6d15da14ecd47d8d27ae1cd5f852''.'''What is the ''c'' constant used in ''XSwiftEC''?''' The algorithm requires a constant ''√-3 (mod p)''; in other words, a number ''c'' such that ''-c2 mod p = 3''. There are two solutions to this equation, one which is itself a square modulo ''p'', and its negation. We choose the square one. To define the needed functions, we first introduce a helper function, matching the XSwiftEC function from the [https://eprint.iacr.org/2022/759.pdf SwiftEC] paper, instantiated for the secp256k1 curve, with minor modifications. It maps pairs of integers ''(u, t)'' (both in range ''0..p-1'') to valid X coordinates on the curve. Note that the specification here does not attempt to be constant time, as it does not operate on secret data. In what follows, we use the notation from [https://github.com/bitcoin/bips/blob/master/bip-0340.mediawiki#specification BIP340]. * ''XSwiftEC(u, t)'': ** Alter the inputs to guarantee an X coordinate on the curve:'''Why do the inputs to the XSwiftEC algorithm need to be altered?''' This step deviates from the paper, which maps a negligibly small subset of inputs (around ''3/2256'') to the point at infinity. To avoid the need to deal with the case where a peer could craft encodings that intentionally trigger this edge case, we remap them to inputs that yield a valid X coordinate. *** If ''u mod p = 0'', let ''u = 1'' instead. *** If ''t mod p = 0'', let ''t = 1'' instead. *** If ''(u3 + t2 + 7) mod p = 0'', let ''t = 2t (mod p)'' instead. ** Let ''X = (u3 + 7 - t2)/(2t) (mod p).'''''What does the division (/) sign in modular arithmetic refer to?''' Note that the division in these expressions corresponds to multiplication with the modular inverse modulo ''p'', i.e. ''a / b (mod p)'' with nonzero ''b'' is the unique solution ''x'' for which ''bx = a (mod p)''. It can be computed as ''abp-2 (mod p)'', but more efficient algorithms exist. ** Let ''Y = (X + t)/(cu) (mod p)''. ** For every ''x'' in ''{u + 4Y2, (-X/Y - u)/2, (X/Y - u)/2}'' (all ''mod p''; the order matters): *** If ''lift_x(x)'' succeeds, return ''x''. There is at least one such ''x''. To find encodings of a given X coordinate ''x'', we first need the inverse of ''XSwiftEC''. The function ''XSwiftECInv(x, u, case)'' either returns ''t'' such that ''XSwiftEC(u, t) = x'', or ''None''. The ''case'' variable is an integer in range ''0..7'', which selects which of the up to 8 valid such ''t'' values to return: * ''XSwiftECInv(x, u, case)'': ** If ''case & 2 = 0'': *** If ''lift_x(-x - u)'' succeeds, return ''None''. *** Let ''v = x''. *** Let ''s = -(u3 + 7)/(u2 + uv + v2) (mod p)''. ** Else (''case & 2 = 2''): *** Let ''s = x - u (mod p)''. *** If ''s = 0'', return ''None''. *** Let ''r'' be the square root of ''-s(4(u3 + 7) + 3u2s) (mod p).'''''How to compute a square root mod ''p''?''' Due to the structure of ''p'', a candidate for the square root of ''a'' mod ''p'' can be computed as ''x = a(p+1)/4 mod p''. If ''a'' is not a square mod ''p'', this formula returns the square root of ''-a mod p'' instead, so it is necessary to verify that ''x2 mod p = a''. If that is the case ''-x mod p'' is a solution too, but we define "the" square root to be equal to that expression (the square root will therefore always be a square itself, as ''(p+1)/4'' is even). This algorithm is a specialization of the [https://en.wikipedia.org/wiki/Tonelli%E2%80%93Shanks_algorithm Tonelli-Shanks algorithm]. Return ''None'' if it does not exist. *** If ''case & 1 = 1'' and ''r = 0'', return ''None''. *** Let ''v = (r/s - u)/2''. ** Let ''w'' be the square root of ''s (mod p)''. Return ''None'' if it does not exist. ** If ''case & 5 = 0'', return ''-w(u(1 - c)/2 + v)''. ** If ''case & 5 = 1'', return ''w(u(1 + c)/2 + v)''. ** If ''case & 5 = 4'', return ''w(u(1 - c)/2 + v)''. ** If ''case & 5 = 5'', return ''-w(u(1 + c)/2 + v)''. The overall ''XElligatorSwift'' algorithm, matching the name used in the paper, then uses this inverse to randomly'''''Can the ElligatorSwift encoding be used to construct public key encodings that satisfy a certain structure (and not pseudorandom)?''' The algorithm chooses the first 32 bytes (i.e., the value ''u'') and then computes a corresponding ''t'' such that the mapping to the curve point holds. In general, picking ''u'' from a uniformly random distribution provides pseudorandomness. But we can also fix any of the 32 bytes in ''u'', and the algorithm will still find a corresponding ''t''. The fact that it is possible to fix the first 32 bytes, combined with the garbage bytes in the handshake, provides a limited but very simple method of parroting other protocols such as [https://tls13.xargs.org/ TLS 1.3], which can be deployed by one of the peers without explicit support from the other peer. More general methods of parroting, e.g., introduced by defining new protocol or a protocol upgrade, are not precluded. sample encodings of ''x'': * ''XElligatorSwift(x)'': ** Loop: *** Let ''u'' be a random non-zero integer in range ''1..p-1'' inclusive. *** Let ''case'' be a random integer in range ''0..7'' inclusive. *** Compute ''t = XSwiftECInv(x, u, case)''. *** If ''t'' is not ''None'', return ''(u, t)''. Otherwise, restart loop. This is used to define the ellswift_create algorithm used in the previous section; it generates a random private key, along with a uniformly sampled 64-byte ElligatorSwift-encoded public key corresponding to it: * ''ellswift_create()'': ** Generate a random private key ''priv'' in range ''1..p-1''. ** Let ''P = priv⋅G'', the corresponding public key point to ''priv''. ** Let ''(u, t) = XElligatorSwift(x(P))'', an encoding of ''x(P)''. ** ''ellswift_pub = bytes(u) || bytes(t)'', its encoding as 64 bytes. ** Return ''(priv, ellswift_pub)''. Finally the ellswift_ecdh_xonly algorithm is: * ''ellswift_ecdh_xonly(ellswift_theirs, priv)'': ** Let ''u = int(ellswift_theirs[:32]) mod p''. ** Let ''t = int(ellswift_theirs[32:]) mod p''. ** Return ''bytes(x(priv⋅lift_x(XSwiftEC(u, t))))''.'''Does it matter which point ''lift_x'' maps to?''' Either point is valid, as they are negations of each other, and negations do not affect the output X coordinate. ===== Keys and session ID derivation ===== The authenticated encryption construction proposed here requires two 32-byte keys per communication direction. These (in addition to a session ID) are computed using HKDF'''Why use HKDF for deriving key material?''' The shared secret already involves a hash function to make sure the public key encodings contribute to it, which negates some of the need for HKDF already. We still use it as it is the standard mechanism for deriving many keys from a single secret, and its computational cost is low enough to be negligible compared to the rest of a connection setup. as specified in [https://tools.ietf.org/html/rfc5869 RFC 5869] with SHA256 as the hash function:
def initialize_v2_transport(peer, ecdh_secret, initiating):
    # Include NETWORK_MAGIC to ensure a connection between nodes on different networks will immediately fail
    prk = HKDF_Extract(Hash=sha256, salt=b'bitcoin_v2_shared_secret' + NETWORK_MAGIC, ikm=ecdh_secret)

    peer.session_id = HKDF_Expand(Hash=sha256, PRK=prk, info=b'session_id', L=32)

    # Initialize the packet encryption ciphers.
    initiator_L = HKDF_Expand(Hash=sha256, PRK=prk, info=b'initiator_L', L=32)
    initiator_P = HKDF_Expand(Hash=sha256, PRK=prk, info=b'initiator_P', L=32)
    responder_L = HKDF_Expand(Hash=sha256, PRK=prk, info=b'responder_L', L=32)
    responder_P = HKDF_Expand(Hash=sha256, PRK=prk, info=b'responder_P', L=32)
    garbage_terminators = HKDF_Expand(Hash=sha256, PRK=prk, info=b'garbage_terminators', L=32)
    initiator_garbage_terminator = garbage_terminators[:16]
    responder_garbage_terminator = garbage_terminators[16:]

    if initiating:
        peer.send_L = FSChaCha20(initiator_L)
        peer.send_P = FSChaCha20Poly1305(initiator_P)
        peer.send_garbage_terminator = initiator_garbage_terminator
        peer.recv_L = FSChaCha20(responder_L)
        peer.recv_P = FSChaCha20Poly1305(responder_P)
        peer.recv_garbage_terminator = responder_garbage_terminator
    else:
        peer.send_L = FSChaCha20(responder_L)
        peer.send_P = FSChaCha20Poly1305(responder_P)
        peer.send_garbage_terminator = responder_garbage_terminator
        peer.recv_L = FSChaCha20(initiator_L)
        peer.recv_P = FSChaCha20Poly1305(initiator_P)
        peer.recv_garbage_terminator = initiator_garbage_terminator

    # To achieve forward secrecy we must wipe the key material used to initialize the ciphers:
    memory_cleanse(ecdh_secret, prk, initiator_L, initiator_P, responder_L, responder_K)
The session ID uniquely identifies the encrypted channel. v2 clients supporting this proposal may present the entire session ID (encoded as a hex string) to the node operator to allow for manual, out of band comparison with the peer node operator. Future transport versions may introduce optional authentication methods that compare the session ID as seen by the two endpoints in order to bind the encrypted channel to the authentication. ===== Overall handshake pseudocode ===== To establish a v2 encrypted connection, the initiator generates an ephemeral secp256k1 keypair and sends an unencrypted ElligatorSwift encoding of the public key to the responding peer followed by unencrypted pseudorandom bytes initiator_garbage of length garbage_len < 4096.
def initiate_v2_handshake(peer, garbage_len):
    peer.privkey_ours, peer.ellswift_ours = ellswift_create()
    peer.sent_garbage = rand_bytes(garbage_len)
    send(peer, peer.ellswift_ours + peer.sent_garbage)
The responder generates an ephemeral keypair for itself and derives the shared ECDH secret (using the first 64 received bytes) which enables it to instantiate the encrypted transport. It then sends 64 bytes of the unencrypted ElligatorSwift encoding of its own public key and its own responder_garbage also of length garbage_len < 4096. If the first 16 bytes received match the v1 prefix, the v1 protocol is used instead.
TRANSPORT_VERSION = b''
NETWORK_MAGIC = b'\xf9\xbe\xb4\xd9' # Mainnet network magic; differs on other networks.
V1_PREFIX = NETWORK_MAGIC + b'version\x00\x00\x00\x00\x00'

def respond_v2_handshake(peer, garbage_len):
    peer.received_prefix = b""
    while len(peer.received_prefix) < len(V1_PREFIX):
        peer.received_prefix += receive(peer, 1)
        if peer.received_prefix[-1] != V1_PREFIX[len(peer.received_prefix) - 1]:
            peer.privkey_ours, peer.ellswift_ours = ellswift_create()
            peer.sent_garbage = rand_bytes(garbage_len)
            send(peer, ellswift_Y + peer.sent_garbage)
            return
    use_v1_protocol()
Upon receiving the encoded responder public key, the initiator derives the shared ECDH secret and instantiates the encrypted transport. It then sends the derived 16-byte initiator_garbage_terminator, optionally followed by an arbitrary number of decoy packets. Afterwards, it receives the responder's garbage (delimited by the garbage terminator). The responder performs very similar steps but includes the earlier received prefix bytes in the public key. Both the initiator and the responder set the AAD of the first encrypted packet they send after the garbage terminator (i.e., either an optional decoy packet or the version packet) to the garbage they have just sent, not including the garbage terminator.
def complete_handshake(peer, initiating, decoy_content_lengths=[]):
    received_prefix = b'' if initiating else peer.received_prefix
    ellswift_theirs = receive(peer, 64 - len(received_prefix))
    if not initiating and ellswift_theirs[4:16] == V1_PREFIX[4:16]:
        # Looks like a v1 peer from the wrong network.
        disconnect(peer)
    ecdh_secret = v2_ecdh(peer.privkey_ours, ellswift_theirs, peer.ellswift_ours,
                          initiating=initiating)
    initialize_v2_transport(peer, ecdh_secret, initiating=True)
    # Send garbage terminator
    send(peer, peer.send_garbage_terminator)
    # Optionally send decoy packets after garbage terminator.
    aad = peer.sent_garbage
    for decoy_content_len in decoy_content_lengths:
        send(v2_enc_packet(peer, decoy_content_len * b'\x00', aad=aad))
        aad = b''
    # Send version packet.
    send(v2_enc_packet(peer, TRANSPORT_VERSION, aad=aad))
    # Skip garbage, until encountering garbage terminator.
    received_garbage = recv(peer, 16)
    for i in range(4096):
        if received_garbage[-16:] == peer.recv_garbage_terminator:
            # Receive, decode, and ignore version packet.
            # This includes skipping decoys and authenticating the received garbage.
            v2_receive_packet(peer, aad=received_garbage[:-16])
            return
        else:
            received_garbage += recv(peer, 1)
    # Garbage terminator was not seen after 4 KiB of garbage.
    disconnect(peer)
==== Packet encryption ==== Lastly, we specify the packet encryption cipher in detail. ===== Existing cryptographic primitives ===== Packet encryption is built on two existing primitives: * '''ChaCha20Poly1305''' is specified as AEAD_CHACHA20_POLY1305 in [https://datatracker.ietf.org/doc/html/rfc8439#section-2.8 RFC 8439 section 2.8]. It is an authenticated encryption protocol with associated data (AEAD), taking a 256-bit key, 96-bit nonce, and an arbitrary-length byte array of associated authenticated data (AAD). Due to the built-in authentication tag, ciphertexts are 16 bytes longer than the corresponding plaintext. In what follows: ** aead_chacha20_poly1305_encrypt(key, nonce, aad, plaintext) refers to a function that takes as input a 32-byte array ''key'', a 12-byte array ''nonce'', an arbitrary-length byte array ''aad'', and an arbitrary-length byte array ''plaintext'', and returns a byte array ''ciphertext'', 16 bytes longer than the plaintext. ** aead_chacha20_poly1305_decrypt(key, nonce, aad, ciphertext) refers to a function that takes as input a 32-byte array ''key'', a 12-byte array ''nonce'', an arbitrary-length byte array ''aad'', and an arbitrary-length byte array ''ciphertext'', and returns either a byte array ''plaintext'' (16 bytes shorter than the ciphertext), or ''None'' in case the ciphertext was not a valid ChaCha20Poly1305 encryption of any plaintext with the specified ''key'', ''nonce'', and ''aad''. * The '''ChaCha20 Block Function''' is specified in [https://datatracker.ietf.org/doc/html/rfc8439#section-2.3 RFC 8439 section 2.3]. It is a pseudorandom function (PRF) taking a 256-bit key, 96-bit nonce, and 32-bit counter, and outputs 64 pseudorandom bytes. It is the underlying building block on which ChaCha20 (and ultimately, ChaCha20Poly1305) is built. In what follows: ** chacha20_block(key, nonce, count) refers to a function that takes as input a 32-byte array ''key'', a 12-byte array ''nonce'', and an integer ''count'' in range ''0..232-1'', and returns a byte array of length 64. These will be used for plaintext encryption and length encryption, respectively. ===== Rekeying wrappers: FSChaCha20Poly1305 and FSChaCha20 ===== To provide re-keying every 224 packets, we specify two wrappers. The first is '''FSChaCha20Poly1305''', which represents a ChaCha20Poly1305 AEAD, which automatically changes the nonce after every message, and rekeys every 224 messages by encrypting 32 zero bytes'''Why is rekeying implemented in terms of an invocation of the AEAD?''' This means the FSChaCha20Poly1305 wrapper can be thought of as a pure layer around the ChaCha20Poly1305 AEAD. Actual implementations can take advantage of the fact that this formulation is equivalent to using byte 64 through 95 of the keystream output of the underlying ChaCha20 cipher as new key, avoiding the need for Poly1305 in the process., and using the first 32 bytes of the result. Each message will be used for one packet. Note that in our protocol, any FSChaCha20Poly1305 instance is always either exclusively encryption or exclusively decryption, as separate instances are used for each direction of the protocol. The nonce used for a message is composed of the 32-bit little-endian encoding of the number of messages with the current key, followed by the 64-bit little-endian encoding of the number of rekeyings performed. For rekeying, the first 32-bit integer is set to ''0xffffffff''.
REKEY_INTERVAL = 224

class FSChaCha20Poly1305:
    """Rekeying wrapper AEAD around ChaCha20Poly1305."""

    def __init__(self, initial_key):
        self.key = initial_key
        self.packet_counter = 0

    def crypt(self, aad, text, is_decrypt):
        nonce = ((self.packet_counter % REKEY_INTERVAL).to_bytes(4, 'little') +
                 (self.packet_counter // REKEY_INTERVAL).to_bytes(8, 'little'))
        if is_decrypt:
            ret = aead_chacha20_poly1305_decrypt(self.key, nonce, aad, text)
        else:
            ret = aead_chacha20_poly1305_encrypt(self.key, nonce, aad, text)
        if (self.packet_counter + 1) % REKEY_INTERVAL == 0:
            rekey_nonce = b"\xFF\xFF\xFF\xFF" + nonce[4:]
            self.key = aead_chacha20_poly1305_encrypt(self.key, rekey_nonce, b"", b"\x00" * 32)[:32]
        self.packet_counter += 1
        return ret

    def decrypt(self, aad, ciphertext):
        return self.crypt(aad, ciphertext, True)

    def encrypt(self, aad, plaintext):
        return self.crypt(aad, plaintext, False)
The second is '''FSChaCha20''', a (single) stream cipher which is used for the lengths of all packets. Encryption and decryption are identical here, so a single function crypt is exposed. It XORs the input with bytes generated using the ChaCha20 block function, rekeying every 224 chunks using the next 32 bytes of the block function output as new key. A ''chunk'' refers here to a single invocation of crypt. As explained before, the same cipher is used for 224 consecutive chunks, to avoid wasting cipher output. The nonce used for these batches of 224 chunks is composed of 4 zero bytes followed by the 64-bit little-endian encoding of the number of rekeyings performed. The block counter is reset to 0 after every rekeying.
class FSChaCha20:
    """Rekeying wrapper stream cipher around ChaCha20."""

    def __init__(self, initial_key):
        self.key = initial_key
        self.block_counter = 0
        self.chunk_counter = 0
        self.keystream = b''

    def get_keystream_bytes(self, nbytes):
        while len(self.keystream) < nbytes:
            nonce = ((0).to_bytes(4, 'little') +
                     (self.chunk_counter // REKEY_INTERVAL).to_bytes(8, 'little'))
            self.keystream += chacha20_block(self.key, nonce, self.block_counter)
            self.block_counter += 1
        ret = self.keystream[:nbytes]
        self.keystream = self.keystream[nbytes:]
        return ret

    def crypt(self, chunk):
        ks = self.get_keystream_bytes(len(chunk))
        ret = bytes([ks[i] ^ chunk[i] for i in range(len(chunk))])
        if ((self.chunk_counter + 1) % REKEY_INTERVAL) == 0:
            self.key = self.get_keystream_bytes(32)
            self.block_counter = 0
        self.chunk_counter += 1
        return ret
===== Overall packet encryption and decryption pseudocode ===== Encryption and decryption of packets then follow by composing the ciphers from the previous section as building blocks.
LENGTH_FIELD_LEN = 3
HEADER_LEN = 1
IGNORE_BIT_POS = 7

def v2_enc_packet(peer, contents, aad=b'', ignore=False):
    assert len(contents) <= 2**24 - 1
    header = (ignore << IGNORE_BIT_POS).to_bytes(HEADER_LEN, 'little')
    plaintext = header + contents
    aead_ciphertext = peer.send_P.encrypt(aad, plaintext)
    enc_contents_len = peer.send_L.encrypt(len(contents).to_bytes(LENGTH_FIELD_LEN, 'little'))
    return enc_contents_len + aead_ciphertext
CHACHA20POLY1305_EXPANSION = 16

def v2_receive_packet(peer, aad=b''):
    while True:
        enc_contents_len = receive(peer, LENGTH_FIELD_LEN)
        contents_len = int.from_bytes(peer.recv_L.crypt(enc_contents_len), 'little')
        aead_ciphertext = receive(peer, HEADER_LEN + contents_len + CHACHA20POLY1305_EXPANSION)
        plaintext = peer.recv_P.decrypt(aad, aead_ciphertext)
        if plaintext is None:
            disconnect(peer)
            break
        # Only the first packet is expected to have non-empty AAD.
        aad = b''
        header = plaintext[:HEADER_LEN]
        if not (header[0] & (1 << IGNORE_BIT_POS)):
            return plaintext[HEADER_LEN:]
==== Performance ==== Each v1 P2P message uses a double-SHA256 checksum truncated to 4 bytes. Roughly the same amount of computation power is required for encrypting and authenticating a v2 P2P message as proposed. === Application layer specification === ==== v2 Bitcoin P2P message structure ==== v2 Bitcoin P2P transport layer packets use the encrypted message structure shown above. An unencrypted application layer '''contents''' is composed of: {|class="wikitable" ! Field !! Size in bytes !! Comments |- | message_type || 1 or 13 || either a one byte ID in range ''1..255'' or b'\x00' followed by a 12-byte ASCII message type (as in the v1 P2P protocol) |- | message_payload || message_length || message payload |} If the first byte of message_type is b'\x00', the following 12 bytes are interpreted as an ASCII message type (as in the v1 P2P protocol), trailing padded with b'\x00' as necessary. If the first byte of message_type is in the range ''1..255'', it is interpreted as a message type ID. This structure results in smaller messages than the v1 protocol, as most messages sent/received will have a message type ID. We recommend reserving 1-byte type IDs for message types that are sent more than once per direction per connection.'''How do the lengths between v1 and v2 compare?''' For messages that use the 1-byte short message type ID, v2 packets use 3 bytes less per message than v1.'''Why not allow variable length long message type IDs?''' Allowing for variable length long IDs reduces the available 1-byte ID space by 12 (to encode the length itself) and incentivizes less descriptive message types. In addition, limiting message types to fixed lengths of 1 or 13 hampers traffic analysis. The value of message_length is '''length''' minus the size of the message_type. The following table lists currently defined message type IDs and the 12-byte ASCII message type (trimmed of trailing padding) that they are treated as equivalent to: {| class="wikitable" |- ! !0 !1 !2 !3 |- !+0 |(12 bytes follow)||addr||block||blocktxn |- !+4 |cmpctblock||feefilter||filteradd||filterclear |- !+8 |filterload||getblocks||getblocktxn||getdata |- !+12 |getheaders||headers||inv||mempool |- !+16 |merkleblock||notfound||ping||pong |- !+20 |sendcmpct||tx||getcfilters||cfilter |- !+24 |getcfheaders||cfheaders||getcfcheckpt||cfcheckpt |- !+28 |addrv2 |- !≥29 || colspan="4" | (undefined) |} When a message type has both a 1-byte encoding and a 13-byte encoding defined, peers that support receiving that message type should accept messages using either encoding (e.g., if the "getblocktxn" message type is supported, then both the 1-byte b'\x0a' encoding and the 13-byte b'\x00getblocktxn\x00' should be supported, and behavior should not depend on which of the two encodings is received). Additional message type IDs may be defined by other BIPs. They should be added to the [[bip-0324/message_type_ids.md|message type IDs table]] to ease coordination. === Signaling specification === ==== Signaling v2 support ==== Peers supporting the v2 transport protocol signal support by advertising the NODE_P2P_V2 = (1 << 11) service flag in addr relay. If met with immediate disconnection when establishing a v2 connection, clients implementing this proposal are encouraged to retry connecting using the v1 protocol.'''Why are v2 clients met with immediate disconnection encouraged to retry with a v1 connection?''' Service flags propagated through untrusted intermediaries using ADDR and ADDRV2 P2P messages and are OR'ed when received from multiple sources. An untrusted intermediary could falsely advertise a potential peer as supportive of v2 connections. Connection downgrades to v1 mitigate the risk of a network participant being blackholed via false advertising. == Test Vectors == For development and testing purposes, we provide a collection of test vectors in CSV format, and a naive, highly inefficient, [[bip-0324/reference.py|reference implementation]] of the relevant algorithms. This code is for demonstration purposes only: * [[bip-0324/ellswift_decode_test_vectors.csv|XElligatorSwift decoding vectors]] provide examples of ElligatorSwift-encoded public keys, and the X coordinate they map to. * [[bip-0324/xswiftec_inv_test_vectors.csv|XSwiftECInv vectors]] provide examples of ''(u, x)'' pairs, and the various ''t'' values that ''xswiftec_inv'' maps them to. * [[bip-0324/packet_encoding_test_vectors.csv|Packet encoding vectors]] illustrate the lifecycle of the authenticated encryption scheme proposed in this document. == Changelog == * 1.0.2 (2026-01-30) * Add message type ID table in auxiliary file * 1.0.1 (2026-01-16) * Specify equivalence of 1-byte and 13-byte `message_type` * 1.0.0 (2024-07-10) * Marked as Final == Rationale and References == == Acknowledgements == Thanks to everyone (last name order) that helped invent and develop the ideas in this proposal: * Matt Corallo * Lloyd Fournier * Gregory Maxwell * Anthony Towns ================================================ FILE: bip-0325.mediawiki ================================================
  BIP: 325
  Layer: Applications
  Title: Signet
  Authors: Karl-Johan Alm 
           Anthony Towns 
  Status: Complete
  Type: Specification
  Assigned: 2019-03-20
  License: CC0-1.0
== Abstract == A new type of test network where signatures are used in addition to proof of work for block progress, enabling much better coordination and robustness (be reliably unreliable), for persistent, longer-term testing scenarios involving multiple independent parties. == Motivation == Testnet is a great place to try out new things without risking real money, but it is notoriously unreliable. Huge block reorgs, long gaps in between blocks being mined or sudden bursts of blocks in rapid succession mean that realistic testing of software, especially involving multiple independent parties running software over an extended period of time, becomes infeasible in practice. A new type of test network would be more suitable for integration testing by organizations such as exchanges, or testing of next generation Layer-2 protocols like Eltoo or sidechain pegs. The goal is not to be perfectly reliable but rather to have a predictable amount of unreliability. You want a test network to behave like mainnet (i.e. no thousands of block reorgs) while also making it easier to trigger expected but rare events like a 6-block reorg. Regtest is not suitable for longer-term scenarios involving multiple independent parties because creating blocks costs nothing, so any party can completely control the test network. == Specification == A new type of network ("signet"), which takes an additional consensus parameter called the challenge (scriptPubKey). The challenge can be a simple pubkey (P2PKH style), or a k-of-n multisig, or any other script you would want. Signet requires all blocks to have a BIP 141 commitment in the coinbase transaction. In order to provide a non-empty solution to the block challenge the block's BIP 141 commitment's optional data must include an additional commitment of the signature/solution for the block: 1-5 bytes - Push the following (4 + x + y) bytes 4 bytes - Signet header (0xecc7daa2) x bytes - scriptSig y bytes - scriptWitness In the special case where an empty solution is valid (ie scriptSig and scriptWitness are both empty) this additional commitment can optionally be left out. This special case is to allow non-signet-aware block generation code to be used to test a custom signet chain where the challenge is trivially true. The scriptSig is serialized by first encoding its length as CompactSize. The scriptWitness stack is serialized as described in BIP 141. Any push operations that do not start with the 4 byte Signet header are ignored. Multiple push operations with the 4 byte Signet header are ignored except for the first instance of the header. To sign the block or verify a block signature, two virtual transactions, each with a single input and output are constructed from the block as follows. The "to_spend" transaction is: nVersion = 0 nLockTime = 0 vin[0].prevout.hash = 0000...000 vin[0].prevout.n = 0xFFFFFFFF vin[0].nSequence = 0 vin[0].scriptSig = OP_0 PUSH72[ block_data ] vin[0].scriptWitness = [] vout[0].nValue = 0 vout[0].scriptPubKey = signet_challenge where block_data is the serialization of the block's nVersion, hashPrevBlock, signet_merkle_root, and nTime. The signet_merkle_root is obtained by generating the merkle root of the block transactions, after modifying the coinbase witness commitment by replacing the signet solution with an empty solution (that is, the witness commitment includes a four byte push of the Signet header with no additional solution data, and no prior pushes beginning with the Signet header). This means the merkle root of the block is different from the merkle root in the signet commitment. This is needed, because the signature can never be included in the very message (in this case, a block) that is being signed. The "to_sign" transaction is: nVersion = 0 nLockTime = 0 vin[0].prevout.hash = to_spend.txid vin[0].prevout.n = 0 vin[0].nSequence = 0 vin[0].sigScript = [ signet_solution sigScript (x bytes), if any ] vin[0].scriptWitness = [ signet_solution scriptWitness (y bytes), if any ] vout[0].nValue = 0 vout[0].scriptPubKey = OP_RETURN The scriptSig and/or scriptWitness for vin[0] are filled in from the Signet header push above. To simplify block generation (mining), the signature also does not commit to the block nonce value, so that rolling the nonce to generate proof-of-work does not also require regenerating signatures. When grinding proof of work, the extended nonce cannot be used as it would invalidate the signature. Instead, simply resigning the same (or an updated) block will give a new search space. A block is considered fully validated only if the to_sign transaction is a valid spend of the to_spend transaction. It is recommended that this verification is done directly before or after the witness commitment verification, as the data required to do both is approximately the same. There is one other acceptable special case: if a block's challenge is e.g. `OP_TRUE` (`0x51`), where an empty solution would result in success, the block is also considered valid if the signet commitment is absent. === Minimum Difficulty === The minimum difficulty for blocks in signet is approximately 0.0011265, corresponding to a maximum target of 00000377ae000000000000000000000000000000000000000000000000000000 which is represented by an nBits value of 0x1e0377ae. This value is chosen so that multiplying the maximum target by maximum retarget timespan (8 weeks measured in seconds) does not overflow a uint256, making it easier to do difficulty adjustment calculations. == Genesis Block and Message Start == The genesis block is the same for all signet networks, whereas the message start is defined as the first four bytes of the sha256d of the challenge script as a single data push (see below). === Genesis Block === * Time stamp: 1598918400 * Nonce: 52613770 * Difficulty: 0x1e0377ae * Version: 1 The resulting genesis block hash is 00000008819873e925422c1ff0f99f7cc9bbb232af63a077a480a3633bee1ef6, and the block hex is 0100000000000000000000000000000000000000000000000000000000000000000000003ba3edfd7a7b12b27ac72c3e67768f617fc81bc3888a51323a9fb8aa4b1e5e4a008f4d5fae77031e8ad222030101000000010000000000000000000000000000000000000000000000000000000000000000ffffffff4d04ffff001d0104455468652054696d65732030332f4a616e2f32303039204368616e63656c6c6f72206f6e206272696e6b206f66207365636f6e64206261696c6f757420666f722062616e6b73ffffffff0100f2052a01000000434104678afdb0fe5548271967f1a67130b7105cd6a828e03909a67962e0ea1f61deb649f6bc3f4cef38c4f35504e51ec112de5c384df7ba0b8d578a4c702b6bf11d5fac00000000. === Message Start === The message start is defined as the first four bytes of the sha256d of the challenge script, as a single push (i.e. prefixed with the challenge script length). Example: * Challenge script = 512103ad5e0edad18cb1f0fc0d28a3d4f1f3e445640337489abb10404f2d1e086be43051ae * Sha256d(len || challenge script) = sha256d(25512103ad...51ae) = 7ec653a59b1912f9db10da2c461ed827d48f9404d5ef0346a6c94aadd4203646 * First four bytes = the message start = 7ec653a5 == Compatibility == This specification is backwards compatible in the sense that existing software can use Signet out of the box. Simply by adding the network parameters for signet (magic number, etc), a client can connect to and use any signet network without further modifications. The block headers have valid proof of work, so clients can trivially check that blocks are "probably" valid. However, anyone can mine blocks that are accepted by the client for any given signet network. These blocks do not contain the required signatures, however, so any fully validating node will promptly reject them. As such, clients need to either validate the block signature inside the coinbase transaction, or connect to trusted peers. Other software need not add block signature validation code that they will not use in production. This is adequate for non-production test purposes where the goal is to have a network behave as much like mainnet as possible. == Reference implementation == Pull request at https://github.com/bitcoin/bitcoin/pull/18267 == References == # Original mailing list thread: https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2019-March/016734.html # Bitcoin Wiki entry: https://en.bitcoin.it/wiki/Signet == Copyright == This document is licensed under the Creative Commons CC0 1.0 Universal license. ================================================ FILE: bip-0326.mediawiki ================================================
  BIP: 326
  Layer: Applications
  Title: Anti-fee-sniping in taproot transactions
  Authors: Chris Belcher 
  Status: Draft
  Type: Informational
  Assigned: 2021-06-10
  License: CC0-1.0
  Discussion: 2021-6-10: https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2021-June/019048.html
== Abstract == This document proposes a certain type of wallet behaviour which uses BIP341 taproot[1]. It provides a greater anonymity set for off-chain protocols which will make use of point-time-locked contracts (PTLCs) such as CoinSwap, Lightning and Discrete Log Contracts. == Motivation == With taproot recently added to bitcoin, and wallet software about to implement taproot wallets, we are in a unique position to improve the privacy of off-chain protocols if we act soon. Taproot allows for point-time-locked contracts (PTLCs) as a more private replacement for hash-time-locked contracts (HTLCs). If an off-chain contract (for example a Lightning channel) is closed using a PTLC instead of an HTLC, then the blockchain will just see a regular taproot script instead of a hash value and preimage. However, if a contract is closed using the timelock path, then the blockchain will either see a OP_CHECKSEQUENCEVERIFY opcode or a nSequence value in the transaction, neither of which are very common today, and this would mark the closing transaction as something special and unusual. This BIP proposes to improve the privacy and fungibility of off-chain protocols by having on-chain wallets like Bitcoin Core also set the nSequence field in their taproot transactions as in BIP68[5]. This would be in place of their regular nLockTime anti-fee-sniping protection. The end result is that, if an observer of the blockchain sees a taproot spend with an nSequence value, then that could be either: a regular spend from a wallet, or an off-chain settlement transaction spent with a timelock. The two cases would be indistinguishable, and this could greatly improve the privacy and fungibility of bitcoin. The community and wallet developers should act now to implement this so that the anonymity set of nSequence transactions starts to be built up as soon as taproot itself becomes adopted by wallets. == Background == === Fee sniping === Fee sniping is a hypothetical outcome of bad incentives to bitcoin mining in the low-inflation future. For a large miner the value of the transactions in the best block and the mempool can be exceeded by the cost of deliberately attempting to mine two blocks to orphan the best block. However with anti-fee-sniping protection using nLockTime or nSequence the bad miner will soon run out of transactions that can be put in the first block, which means they now need to go in the second. Anti-fee-sniping adds to the incentive to move the blockchain forward. The nLockTime field is being used this way today. It is implemented in Bitcoin Core[2] and Electrum[3], and adopted by approximately 20% of all recent transactions[4]. === Absolute vs relative locktime === nLockTime is an absolute lock time, it allows the transaction to only be mined after a certain block height or unix time. The widespread adoption of it might have provided a good anonymity set for off-chain protocols. Unfortunately those protocols also commonly use relative lock times, because it allows contracts (for example Lightning payment channels or CoinSwaps) to remain open indefinitely as the countdown clock only starts ticking when the closing transaction is confirmed. Absolute locktimes are also still used, so we should keep using nLockTime, but also often use nSequence. === Transaction pinning === Transaction pinning[8] is a method for making fee bumping prohibitively expensive by abusing node protections against attacks that can waste bandwidth, CPU, and memory. This can make fee management more difficult in multipart contract protocols (such as Lightning Network or CoinSwap). One possible way of solving the problem is to include a 1-block relative timelock `1 OP_CSV` to all spend paths, making it impossible to spend the unconfirmed UTXO. Such a 1-block locktime can also be created with an nSequence value of 1. Many on-chain transactions in bitcoin spend inputs that were created just one or two blocks ago, following this BIP such transactions with `nSequence=1` would also provide cover traffic for off-chain transactions which disable transaction pinning. == Specifications == When wallets create transactions spending UTXOs protected by BIP341 taproot, they should set either an nLockTime value or nSequence values to discourage fee sniping, by allowing the transaction to only be mined in the next block after the tip, not the current block. This BIP suggests 50% probability for using nLockTime and 50% for nSequence. If nSequence is set it should apply to at least one of the inputs of the transaction, if it has multiple inputs. It is suggested that on-chain wallets pick an input randomly. Wallets should also have a second random branch which sets the nLockTime or nSequence value even further back, so that transactions that are delayed after signing for whatever reason (e.g. high-latency mix networks) have better privacy. Existing behaviour is that with a probability of 10%, choose a random number between 0 and 99, and subtract it from the current block height. See the Bitcoin Core and Electrum source codes linked in the references for an example. nSequence can only encode up to 65535 for the block distance[5] so if the UTXOs being spent have more than 65535 confirmations, then the wallet should use nLockTime instead. === Pseudocode === def apply_anti_fee_sniping_fields(transaction, rbf_set): # bip68 requires v=2 transaction.version = 2 # Initialize all nsequence to indicate the requested RBF state # nsequence can not be 2**32 - 1 in order for nlocktime to take effect for input in transaction.inputs: if rbf_set: input.nsequence = 2**32 - 3 else: input.nsequence = 2**32 - 2 # always set nlocktime if any of the transaction inputs have more # confirmations than 65535 or are not taproot inputs, or have # unconfirmed inputs # otherwise choose either nlocktime or nsequence with 50% probability if not rbf_set || any(map(lambda input: input.confirmations() > 65535 || !input.is_taproot() || input.confirmations() == 0, transaction.inputs)) || randint(2) == 0: transaction.nlocktime = blockchain.height() if randint(10) == 0: transaction.nlocktime = max(0, transaction.nlocktime - randint(0, 99)) # nsequence must be set in order for nlocktime to take effect else: transaction.nlocktime = 0 input_index = randint(len(transaction.inputs)) transaction.inputs[input_index].nsequence = transaction.inputs\ [input_index].confirmations() if randint(10) == 0: transaction.inputs[input_index].nsequence = max(1, transaction.inputs[input_index].nsequence - randint(0, 99)) == Compatibility == This BIP doesn't need any consensus changes. It can be adopted unilaterally and gradually by wallets. Although for greater privacy it would be good for software to adopt it as soon as possible. Ideally during the process of developers implementing their taproot wallets, so that when taproot starts to be used it will already include the nSequence code. All wallet software already keeps track of how many confirmations its UTXOs have, so the information required to set the nSequence field is already available. == Acknowledgements == Originally suggested by David Harding[6] and mentioned to me by ZmnSCPxj. Thanks to craigraw for suggesting a new value for input nsequence in the absolute locktime case[7]. == Copyright == This BIP is licensed under the Creative Commons CC0 1.0 Universal licence. == References == [1] https://github.com/bitcoin/bips/blob/master/bip-0341.mediawiki [2] https://github.com/bitcoin/bitcoin/pull/2340 [3] https://github.com/spesmilo/electrum/blob/7e6d65ec11c0dccfc24478471c5951d3ae586937/electrum/wallet.py#L211-L224 [4] https://txstats.com/dashboard/db/blocks-statistics?panelId=4&fullscreen&orgId=1 [5] https://github.com/bitcoin/bips/blob/master/bip-0068.mediawiki [6] https://lists.linuxfoundation.org/pipermail/lightning-dev/2020-January/002412.html [7] https://github.com/sparrowwallet/sparrow/issues/161#issuecomment-925003231 [8] https://bitcoinops.org/en/topics/transaction-pinning/ ================================================ FILE: bip-0327/gen_vectors_helper.py ================================================ from reference import * def gen_key_agg_vectors(): print("key_agg_vectors.json: Intermediate tweaking result is point at infinity") sk = bytes.fromhex("7FB9E0E687ADA1EEBF7ECFE2F21E73EBDB51A7D450948DFE8D76D7F2D1007671") pk = individual_pk(sk) keygen_ctx = key_agg([pk]) aggpoint, _, _ = keygen_ctx aggsk = key_agg_coeff([pk], pk)*int_from_bytes(sk) % n t = n - aggsk assert point_add(point_mul(G, t), aggpoint) == None is_xonly = False tweak = bytes_from_int(t) assert_raises(ValueError, lambda: apply_tweak(keygen_ctx, tweak, is_xonly), lambda e: True) print(" pubkey:", pk.hex().upper()) print(" tweak: ", tweak.hex().upper()) def check_sign_verify_vectors(): with open(os.path.join(sys.path[0], 'vectors', 'sign_verify_vectors.json')) as f: test_data = json.load(f) X = fromhex_all(test_data["pubkeys"]) pnonce = fromhex_all(test_data["pnonces"]) aggnonces = fromhex_all(test_data["aggnonces"]) msgs = fromhex_all(test_data["msgs"]) valid_test_cases = test_data["valid_test_cases"] for (i, test_case) in enumerate(valid_test_cases): pubkeys = [X[i] for i in test_case["key_indices"]] pubnonces = [pnonce[i] for i in test_case["nonce_indices"]] aggnonce = aggnonces[test_case["aggnonce_index"]] assert nonce_agg(pubnonces) == aggnonce msg = msgs[test_case["msg_index"]] signer_index = test_case["signer_index"] expected = bytes.fromhex(test_case["expected"]) session_ctx = SessionContext(aggnonce, pubkeys, [], [], msg) (Q, _, _, _, R, _) = get_session_values(session_ctx) # Make sure the vectors include tests for both variants of Q and R if i == 0: assert has_even_y(Q) and not has_even_y(R) if i == 1: assert not has_even_y(Q) and has_even_y(R) if i == 2: assert has_even_y(Q) and has_even_y(R) def check_tweak_vectors(): with open(os.path.join(sys.path[0], 'vectors', 'tweak_vectors.json')) as f: test_data = json.load(f) X = fromhex_all(test_data["pubkeys"]) pnonce = fromhex_all(test_data["pnonces"]) tweak = fromhex_all(test_data["tweaks"]) valid_test_cases = test_data["valid_test_cases"] for (i, test_case) in enumerate(valid_test_cases): pubkeys = [X[i] for i in test_case["key_indices"]] tweaks = [tweak[i] for i in test_case["tweak_indices"]] is_xonly = test_case["is_xonly"] _, gacc, _ = key_agg_and_tweak(pubkeys, tweaks, is_xonly) # Make sure the vectors include tests for gacc = 1 and -1 if i == 0: assert gacc == n - 1 if i == 1: assert gacc == 1 def sig_agg_vectors(): print("sig_agg_vectors.json:") sk = fromhex_all([ "7FB9E0E687ADA1EEBF7ECFE2F21E73EBDB51A7D450948DFE8D76D7F2D1007671", "3874D22DE7A7290C49CE7F1DC17D1A8CD8918E1F799055139D57FC0988D04D10", "D0EA1B84481ED1BCFAA39D6775F97BDC9BF8D7C02FD0C009D6D85BAE5EC7B87A", "FC2BF9E056B273AF0A8AABB815E541A3552C142AC10D4FE584F01D2CAB84F577"]) pubkeys = list(map(lambda secret: individual_pk(secret), sk)) indices32 = [i.to_bytes(32, 'big') for i in range(6)] secnonces, pnonces = zip(*[nonce_gen_internal(r, None, pubkeys[0], None, None, None) for r in indices32]) tweaks = fromhex_all([ "B511DA492182A91B0FFB9A98020D55F260AE86D7ECBD0399C7383D59A5F2AF7C", "A815FE049EE3C5AAB66310477FBC8BCCCAC2F3395F59F921C364ACD78A2F48DC", "75448A87274B056468B977BE06EB1E9F657577B7320B0A3376EA51FD420D18A8"]) msg = bytes.fromhex("599C67EA410D005B9DA90817CF03ED3B1C868E4DA4EDF00A5880B0082C237869") psigs = [None] * 9 valid_test_cases = [ { "aggnonce": None, "nonce_indices": [0, 1], "key_indices": [0, 1], "tweak_indices": [], "is_xonly": [], "psig_indices": [0, 1], }, { "aggnonce": None, "nonce_indices": [0, 2], "key_indices": [0, 2], "tweak_indices": [], "is_xonly": [], "psig_indices": [2, 3], }, { "aggnonce": None, "nonce_indices": [0, 3], "key_indices": [0, 2], "tweak_indices": [0], "is_xonly": [False], "psig_indices": [4, 5], }, { "aggnonce": None, "nonce_indices": [0, 4], "key_indices": [0, 3], "tweak_indices": [0, 1, 2], "is_xonly": [True, False, True], "psig_indices": [6, 7], }, ] for (i, test_case) in enumerate(valid_test_cases): is_xonly = test_case["is_xonly"] nonce_indices = test_case["nonce_indices"] key_indices = test_case["key_indices"] psig_indices = test_case["psig_indices"] vec_pnonces = [pnonces[i] for i in nonce_indices] vec_pubkeys = [pubkeys[i] for i in key_indices] vec_tweaks = [tweaks[i] for i in test_case["tweak_indices"]] aggnonce = nonce_agg(vec_pnonces) test_case["aggnonce"] = aggnonce.hex().upper() session_ctx = SessionContext(aggnonce, vec_pubkeys, vec_tweaks, is_xonly, msg) for j in range(len(key_indices)): # WARNING: An actual implementation should _not_ copy the secnonce. # Reusing the secnonce, as we do here for testing purposes, can leak the # secret key. secnonce_tmp = bytearray(secnonces[nonce_indices[j]][:64] + pubkeys[key_indices[j]]) psigs[psig_indices[j]] = sign(secnonce_tmp, sk[key_indices[j]], session_ctx) sig = partial_sig_agg([psigs[i] for i in psig_indices], session_ctx) keygen_ctx = key_agg_and_tweak(vec_pubkeys, vec_tweaks, is_xonly) # To maximize coverage of the sig_agg algorithm, we want one public key # point with an even and one with an odd Y coordinate. if i == 0: assert(has_even_y(keygen_ctx[0])) if i == 1: assert(not has_even_y(keygen_ctx[0])) aggpk = get_xonly_pk(keygen_ctx) assert schnorr_verify(msg, aggpk, sig) test_case["expected"] = sig.hex().upper() error_test_case = { "aggnonce": None, "nonce_indices": [0, 4], "key_indices": [0, 3], "tweak_indices": [0, 1, 2], "is_xonly": [True, False, True], "psig_indices": [7, 8], "error": { "type": "invalid_contribution", "signer": 1, "contrib": "psig", }, "comment": "Partial signature is invalid because it exceeds group size" } psigs[8] = bytes.fromhex("FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141") vec_pnonces = [pnonces[i] for i in error_test_case["nonce_indices"]] aggnonce = nonce_agg(vec_pnonces) error_test_case["aggnonce"] = aggnonce.hex().upper() def tohex_all(l): return list(map(lambda e: e.hex().upper(), l)) print(json.dumps({ "pubkeys": tohex_all(pubkeys), "pnonces": tohex_all(pnonces), "tweaks": tohex_all(tweaks), "psigs": tohex_all(psigs), "msg": msg.hex().upper(), "valid_test_cases": valid_test_cases, "error_test_cases": [error_test_case] }, indent=4)) gen_key_agg_vectors() check_sign_verify_vectors() check_tweak_vectors() print() sig_agg_vectors() ================================================ FILE: bip-0327/reference.py ================================================ # BIP327 reference implementation # # WARNING: This implementation is for demonstration purposes only and _not_ to # be used in production environments. The code is vulnerable to timing attacks, # for example. from typing import List, Optional, Tuple, NewType, NamedTuple import hashlib import secrets import time # # The following helper functions were copied from the BIP-340 reference implementation: # https://github.com/bitcoin/bips/blob/master/bip-0340/reference.py # p = 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEFFFFFC2F n = 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141 # Points are tuples of X and Y coordinates and the point at infinity is # represented by the None keyword. G = (0x79BE667EF9DCBBAC55A06295CE870B07029BFCDB2DCE28D959F2815B16F81798, 0x483ADA7726A3C4655DA4FBFC0E1108A8FD17B448A68554199C47D08FFB10D4B8) Point = Tuple[int, int] # This implementation can be sped up by storing the midstate after hashing # tag_hash instead of rehashing it all the time. def tagged_hash(tag: str, msg: bytes) -> bytes: tag_hash = hashlib.sha256(tag.encode()).digest() return hashlib.sha256(tag_hash + tag_hash + msg).digest() def is_infinite(P: Optional[Point]) -> bool: return P is None def x(P: Point) -> int: assert not is_infinite(P) return P[0] def y(P: Point) -> int: assert not is_infinite(P) return P[1] def point_add(P1: Optional[Point], P2: Optional[Point]) -> Optional[Point]: if P1 is None: return P2 if P2 is None: return P1 if (x(P1) == x(P2)) and (y(P1) != y(P2)): return None if P1 == P2: lam = (3 * x(P1) * x(P1) * pow(2 * y(P1), p - 2, p)) % p else: lam = ((y(P2) - y(P1)) * pow(x(P2) - x(P1), p - 2, p)) % p x3 = (lam * lam - x(P1) - x(P2)) % p return (x3, (lam * (x(P1) - x3) - y(P1)) % p) def point_mul(P: Optional[Point], n: int) -> Optional[Point]: R = None for i in range(256): if (n >> i) & 1: R = point_add(R, P) P = point_add(P, P) return R def bytes_from_int(x: int) -> bytes: return x.to_bytes(32, byteorder="big") def lift_x(b: bytes) -> Optional[Point]: x = int_from_bytes(b) if x >= p: return None y_sq = (pow(x, 3, p) + 7) % p y = pow(y_sq, (p + 1) // 4, p) if pow(y, 2, p) != y_sq: return None return (x, y if y & 1 == 0 else p-y) def int_from_bytes(b: bytes) -> int: return int.from_bytes(b, byteorder="big") def has_even_y(P: Point) -> bool: assert not is_infinite(P) return y(P) % 2 == 0 def schnorr_verify(msg: bytes, pubkey: bytes, sig: bytes) -> bool: if len(msg) != 32: raise ValueError('The message must be a 32-byte array.') if len(pubkey) != 32: raise ValueError('The public key must be a 32-byte array.') if len(sig) != 64: raise ValueError('The signature must be a 64-byte array.') P = lift_x(pubkey) r = int_from_bytes(sig[0:32]) s = int_from_bytes(sig[32:64]) if (P is None) or (r >= p) or (s >= n): return False e = int_from_bytes(tagged_hash("BIP0340/challenge", sig[0:32] + pubkey + msg)) % n R = point_add(point_mul(G, s), point_mul(P, n - e)) if (R is None) or (not has_even_y(R)) or (x(R) != r): return False return True # # End of helper functions copied from BIP-340 reference implementation. # PlainPk = NewType('PlainPk', bytes) XonlyPk = NewType('XonlyPk', bytes) # There are two types of exceptions that can be raised by this implementation: # - ValueError for indicating that an input doesn't conform to some function # precondition (e.g. an input array is the wrong length, a serialized # representation doesn't have the correct format). # - InvalidContributionError for indicating that a signer (or the # aggregator) is misbehaving in the protocol. # # Assertions are used to (1) satisfy the type-checking system, and (2) check for # inconvenient events that can't happen except with negligible probability (e.g. # output of a hash function is 0) and can't be manually triggered by any # signer. # This exception is raised if a party (signer or nonce aggregator) sends invalid # values. Actual implementations should not crash when receiving invalid # contributions. Instead, they should hold the offending party accountable. class InvalidContributionError(Exception): def __init__(self, signer, contrib): self.signer = signer # contrib is one of "pubkey", "pubnonce", "aggnonce", or "psig". self.contrib = contrib infinity = None def xbytes(P: Point) -> bytes: return bytes_from_int(x(P)) def cbytes(P: Point) -> bytes: a = b'\x02' if has_even_y(P) else b'\x03' return a + xbytes(P) def cbytes_ext(P: Optional[Point]) -> bytes: if is_infinite(P): return (0).to_bytes(33, byteorder='big') assert P is not None return cbytes(P) def point_negate(P: Optional[Point]) -> Optional[Point]: if P is None: return P return (x(P), p - y(P)) def cpoint(x: bytes) -> Point: if len(x) != 33: raise ValueError('x is not a valid compressed point.') P = lift_x(x[1:33]) if P is None: raise ValueError('x is not a valid compressed point.') if x[0] == 2: return P elif x[0] == 3: P = point_negate(P) assert P is not None return P else: raise ValueError('x is not a valid compressed point.') def cpoint_ext(x: bytes) -> Optional[Point]: if x == (0).to_bytes(33, 'big'): return None else: return cpoint(x) # Return the plain public key corresponding to a given secret key def individual_pk(seckey: bytes) -> PlainPk: d0 = int_from_bytes(seckey) if not (1 <= d0 <= n - 1): raise ValueError('The secret key must be an integer in the range 1..n-1.') P = point_mul(G, d0) assert P is not None return PlainPk(cbytes(P)) def key_sort(pubkeys: List[PlainPk]) -> List[PlainPk]: pubkeys.sort() return pubkeys KeyAggContext = NamedTuple('KeyAggContext', [('Q', Point), ('gacc', int), ('tacc', int)]) def get_xonly_pk(keyagg_ctx: KeyAggContext) -> XonlyPk: Q, _, _ = keyagg_ctx return XonlyPk(xbytes(Q)) def key_agg(pubkeys: List[PlainPk]) -> KeyAggContext: pk2 = get_second_key(pubkeys) u = len(pubkeys) Q = infinity for i in range(u): try: P_i = cpoint(pubkeys[i]) except ValueError: raise InvalidContributionError(i, "pubkey") a_i = key_agg_coeff_internal(pubkeys, pubkeys[i], pk2) Q = point_add(Q, point_mul(P_i, a_i)) # Q is not the point at infinity except with negligible probability. assert(Q is not None) gacc = 1 tacc = 0 return KeyAggContext(Q, gacc, tacc) def hash_keys(pubkeys: List[PlainPk]) -> bytes: return tagged_hash('KeyAgg list', b''.join(pubkeys)) def get_second_key(pubkeys: List[PlainPk]) -> PlainPk: u = len(pubkeys) for j in range(1, u): if pubkeys[j] != pubkeys[0]: return pubkeys[j] return PlainPk(b'\x00'*33) def key_agg_coeff(pubkeys: List[PlainPk], pk_: PlainPk) -> int: pk2 = get_second_key(pubkeys) return key_agg_coeff_internal(pubkeys, pk_, pk2) def key_agg_coeff_internal(pubkeys: List[PlainPk], pk_: PlainPk, pk2: PlainPk) -> int: L = hash_keys(pubkeys) if pk_ == pk2: return 1 return int_from_bytes(tagged_hash('KeyAgg coefficient', L + pk_)) % n def apply_tweak(keyagg_ctx: KeyAggContext, tweak: bytes, is_xonly: bool) -> KeyAggContext: if len(tweak) != 32: raise ValueError('The tweak must be a 32-byte array.') Q, gacc, tacc = keyagg_ctx if is_xonly and not has_even_y(Q): g = n - 1 else: g = 1 t = int_from_bytes(tweak) if t >= n: raise ValueError('The tweak must be less than n.') Q_ = point_add(point_mul(Q, g), point_mul(G, t)) if Q_ is None: raise ValueError('The result of tweaking cannot be infinity.') gacc_ = g * gacc % n tacc_ = (t + g * tacc) % n return KeyAggContext(Q_, gacc_, tacc_) def bytes_xor(a: bytes, b: bytes) -> bytes: return bytes(x ^ y for x, y in zip(a, b)) def nonce_hash(rand: bytes, pk: PlainPk, aggpk: XonlyPk, i: int, msg_prefixed: bytes, extra_in: bytes) -> int: buf = b'' buf += rand buf += len(pk).to_bytes(1, 'big') buf += pk buf += len(aggpk).to_bytes(1, 'big') buf += aggpk buf += msg_prefixed buf += len(extra_in).to_bytes(4, 'big') buf += extra_in buf += i.to_bytes(1, 'big') return int_from_bytes(tagged_hash('MuSig/nonce', buf)) def nonce_gen_internal(rand_: bytes, sk: Optional[bytes], pk: PlainPk, aggpk: Optional[XonlyPk], msg: Optional[bytes], extra_in: Optional[bytes]) -> Tuple[bytearray, bytes]: if sk is not None: rand = bytes_xor(sk, tagged_hash('MuSig/aux', rand_)) else: rand = rand_ if aggpk is None: aggpk = XonlyPk(b'') if msg is None: msg_prefixed = b'\x00' else: msg_prefixed = b'\x01' msg_prefixed += len(msg).to_bytes(8, 'big') msg_prefixed += msg if extra_in is None: extra_in = b'' k_1 = nonce_hash(rand, pk, aggpk, 0, msg_prefixed, extra_in) % n k_2 = nonce_hash(rand, pk, aggpk, 1, msg_prefixed, extra_in) % n # k_1 == 0 or k_2 == 0 cannot occur except with negligible probability. assert k_1 != 0 assert k_2 != 0 R_s1 = point_mul(G, k_1) R_s2 = point_mul(G, k_2) assert R_s1 is not None assert R_s2 is not None pubnonce = cbytes(R_s1) + cbytes(R_s2) secnonce = bytearray(bytes_from_int(k_1) + bytes_from_int(k_2) + pk) return secnonce, pubnonce def nonce_gen(sk: Optional[bytes], pk: PlainPk, aggpk: Optional[XonlyPk], msg: Optional[bytes], extra_in: Optional[bytes]) -> Tuple[bytearray, bytes]: if sk is not None and len(sk) != 32: raise ValueError('The optional byte array sk must have length 32.') if aggpk is not None and len(aggpk) != 32: raise ValueError('The optional byte array aggpk must have length 32.') rand_ = secrets.token_bytes(32) return nonce_gen_internal(rand_, sk, pk, aggpk, msg, extra_in) def nonce_agg(pubnonces: List[bytes]) -> bytes: u = len(pubnonces) aggnonce = b'' for j in (1, 2): R_j = infinity for i in range(u): try: R_ij = cpoint(pubnonces[i][(j-1)*33:j*33]) except ValueError: raise InvalidContributionError(i, "pubnonce") R_j = point_add(R_j, R_ij) aggnonce += cbytes_ext(R_j) return aggnonce SessionContext = NamedTuple('SessionContext', [('aggnonce', bytes), ('pubkeys', List[PlainPk]), ('tweaks', List[bytes]), ('is_xonly', List[bool]), ('msg', bytes)]) def key_agg_and_tweak(pubkeys: List[PlainPk], tweaks: List[bytes], is_xonly: List[bool]) -> KeyAggContext: if len(tweaks) != len(is_xonly): raise ValueError('The `tweaks` and `is_xonly` arrays must have the same length.') keyagg_ctx = key_agg(pubkeys) v = len(tweaks) for i in range(v): keyagg_ctx = apply_tweak(keyagg_ctx, tweaks[i], is_xonly[i]) return keyagg_ctx def get_session_values(session_ctx: SessionContext) -> Tuple[Point, int, int, int, Point, int]: (aggnonce, pubkeys, tweaks, is_xonly, msg) = session_ctx Q, gacc, tacc = key_agg_and_tweak(pubkeys, tweaks, is_xonly) b = int_from_bytes(tagged_hash('MuSig/noncecoef', aggnonce + xbytes(Q) + msg)) % n try: R_1 = cpoint_ext(aggnonce[0:33]) R_2 = cpoint_ext(aggnonce[33:66]) except ValueError: # Nonce aggregator sent invalid nonces raise InvalidContributionError(None, "aggnonce") R_ = point_add(R_1, point_mul(R_2, b)) R = R_ if not is_infinite(R_) else G assert R is not None e = int_from_bytes(tagged_hash('BIP0340/challenge', xbytes(R) + xbytes(Q) + msg)) % n return (Q, gacc, tacc, b, R, e) def get_session_key_agg_coeff(session_ctx: SessionContext, P: Point) -> int: (_, pubkeys, _, _, _) = session_ctx pk = PlainPk(cbytes(P)) if pk not in pubkeys: raise ValueError('The signer\'s pubkey must be included in the list of pubkeys.') return key_agg_coeff(pubkeys, pk) def sign(secnonce: bytearray, sk: bytes, session_ctx: SessionContext) -> bytes: (Q, gacc, _, b, R, e) = get_session_values(session_ctx) k_1_ = int_from_bytes(secnonce[0:32]) k_2_ = int_from_bytes(secnonce[32:64]) # Overwrite the secnonce argument with zeros such that subsequent calls of # sign with the same secnonce raise a ValueError. secnonce[:64] = bytearray(b'\x00'*64) if not 0 < k_1_ < n: raise ValueError('first secnonce value is out of range.') if not 0 < k_2_ < n: raise ValueError('second secnonce value is out of range.') k_1 = k_1_ if has_even_y(R) else n - k_1_ k_2 = k_2_ if has_even_y(R) else n - k_2_ d_ = int_from_bytes(sk) if not 0 < d_ < n: raise ValueError('secret key value is out of range.') P = point_mul(G, d_) assert P is not None pk = cbytes(P) if not pk == secnonce[64:97]: raise ValueError('Public key does not match nonce_gen argument') a = get_session_key_agg_coeff(session_ctx, P) g = 1 if has_even_y(Q) else n - 1 d = g * gacc * d_ % n s = (k_1 + b * k_2 + e * a * d) % n psig = bytes_from_int(s) R_s1 = point_mul(G, k_1_) R_s2 = point_mul(G, k_2_) assert R_s1 is not None assert R_s2 is not None pubnonce = cbytes(R_s1) + cbytes(R_s2) # Optional correctness check. The result of signing should pass signature verification. assert partial_sig_verify_internal(psig, pubnonce, pk, session_ctx) return psig def det_nonce_hash(sk_: bytes, aggothernonce: bytes, aggpk: bytes, msg: bytes, i: int) -> int: buf = b'' buf += sk_ buf += aggothernonce buf += aggpk buf += len(msg).to_bytes(8, 'big') buf += msg buf += i.to_bytes(1, 'big') return int_from_bytes(tagged_hash('MuSig/deterministic/nonce', buf)) def deterministic_sign(sk: bytes, aggothernonce: bytes, pubkeys: List[PlainPk], tweaks: List[bytes], is_xonly: List[bool], msg: bytes, rand: Optional[bytes]) -> Tuple[bytes, bytes]: if rand is not None: sk_ = bytes_xor(sk, tagged_hash('MuSig/aux', rand)) else: sk_ = sk aggpk = get_xonly_pk(key_agg_and_tweak(pubkeys, tweaks, is_xonly)) k_1 = det_nonce_hash(sk_, aggothernonce, aggpk, msg, 0) % n k_2 = det_nonce_hash(sk_, aggothernonce, aggpk, msg, 1) % n # k_1 == 0 or k_2 == 0 cannot occur except with negligible probability. assert k_1 != 0 assert k_2 != 0 R_s1 = point_mul(G, k_1) R_s2 = point_mul(G, k_2) assert R_s1 is not None assert R_s2 is not None pubnonce = cbytes(R_s1) + cbytes(R_s2) secnonce = bytearray(bytes_from_int(k_1) + bytes_from_int(k_2) + individual_pk(sk)) try: aggnonce = nonce_agg([pubnonce, aggothernonce]) except Exception: raise InvalidContributionError(None, "aggothernonce") session_ctx = SessionContext(aggnonce, pubkeys, tweaks, is_xonly, msg) psig = sign(secnonce, sk, session_ctx) return (pubnonce, psig) def partial_sig_verify(psig: bytes, pubnonces: List[bytes], pubkeys: List[PlainPk], tweaks: List[bytes], is_xonly: List[bool], msg: bytes, i: int) -> bool: if len(pubnonces) != len(pubkeys): raise ValueError('The `pubnonces` and `pubkeys` arrays must have the same length.') if len(tweaks) != len(is_xonly): raise ValueError('The `tweaks` and `is_xonly` arrays must have the same length.') aggnonce = nonce_agg(pubnonces) session_ctx = SessionContext(aggnonce, pubkeys, tweaks, is_xonly, msg) return partial_sig_verify_internal(psig, pubnonces[i], pubkeys[i], session_ctx) def partial_sig_verify_internal(psig: bytes, pubnonce: bytes, pk: bytes, session_ctx: SessionContext) -> bool: (Q, gacc, _, b, R, e) = get_session_values(session_ctx) s = int_from_bytes(psig) if s >= n: return False R_s1 = cpoint(pubnonce[0:33]) R_s2 = cpoint(pubnonce[33:66]) Re_s_ = point_add(R_s1, point_mul(R_s2, b)) Re_s = Re_s_ if has_even_y(R) else point_negate(Re_s_) P = cpoint(pk) a = get_session_key_agg_coeff(session_ctx, P) g = 1 if has_even_y(Q) else n - 1 g_ = g * gacc % n return point_mul(G, s) == point_add(Re_s, point_mul(P, e * a * g_ % n)) def partial_sig_agg(psigs: List[bytes], session_ctx: SessionContext) -> bytes: (Q, _, tacc, _, R, e) = get_session_values(session_ctx) s = 0 u = len(psigs) for i in range(u): s_i = int_from_bytes(psigs[i]) if s_i >= n: raise InvalidContributionError(i, "psig") s = (s + s_i) % n g = 1 if has_even_y(Q) else n - 1 s = (s + e * g * tacc) % n return xbytes(R) + bytes_from_int(s) # # The following code is only used for testing. # import json import os import sys def fromhex_all(l): return [bytes.fromhex(l_i) for l_i in l] # Check if calling `try_fn` raises an exception. If yes, examine it with `except_fn`. def assert_raises(exception, try_fn, except_fn): raised = False try: try_fn() except exception as e: raised = True assert(except_fn(e)) except BaseException: raise AssertionError("Wrong exception raised in a test.") if not raised: raise AssertionError("Exception was _not_ raised in a test where it was required.") def get_error_details(test_case): error = test_case["error"] if error["type"] == "invalid_contribution": exception = InvalidContributionError if "contrib" in error: except_fn = lambda e: e.signer == error["signer"] and e.contrib == error["contrib"] else: except_fn = lambda e: e.signer == error["signer"] elif error["type"] == "value": exception = ValueError except_fn = lambda e: str(e) == error["message"] else: raise RuntimeError(f"Invalid error type: {error['type']}") return exception, except_fn def test_key_sort_vectors() -> None: with open(os.path.join(sys.path[0], 'vectors', 'key_sort_vectors.json')) as f: test_data = json.load(f) X = fromhex_all(test_data["pubkeys"]) X_sorted = fromhex_all(test_data["sorted_pubkeys"]) assert key_sort(X) == X_sorted def test_key_agg_vectors() -> None: with open(os.path.join(sys.path[0], 'vectors', 'key_agg_vectors.json')) as f: test_data = json.load(f) X = fromhex_all(test_data["pubkeys"]) T = fromhex_all(test_data["tweaks"]) valid_test_cases = test_data["valid_test_cases"] error_test_cases = test_data["error_test_cases"] for test_case in valid_test_cases: pubkeys = [X[i] for i in test_case["key_indices"]] expected = bytes.fromhex(test_case["expected"]) assert get_xonly_pk(key_agg(pubkeys)) == expected for test_case in error_test_cases: exception, except_fn = get_error_details(test_case) pubkeys = [X[i] for i in test_case["key_indices"]] tweaks = [T[i] for i in test_case["tweak_indices"]] is_xonly = test_case["is_xonly"] assert_raises(exception, lambda: key_agg_and_tweak(pubkeys, tweaks, is_xonly), except_fn) def test_nonce_gen_vectors() -> None: with open(os.path.join(sys.path[0], 'vectors', 'nonce_gen_vectors.json')) as f: test_data = json.load(f) for test_case in test_data["test_cases"]: def get_value(key) -> bytes: return bytes.fromhex(test_case[key]) def get_value_maybe(key) -> Optional[bytes]: if test_case[key] is not None: return get_value(key) else: return None rand_ = get_value("rand_") sk = get_value_maybe("sk") pk = PlainPk(get_value("pk")) aggpk = get_value_maybe("aggpk") if aggpk is not None: aggpk = XonlyPk(aggpk) msg = get_value_maybe("msg") extra_in = get_value_maybe("extra_in") expected_secnonce = get_value("expected_secnonce") expected_pubnonce = get_value("expected_pubnonce") assert nonce_gen_internal(rand_, sk, pk, aggpk, msg, extra_in) == (expected_secnonce, expected_pubnonce) def test_nonce_agg_vectors() -> None: with open(os.path.join(sys.path[0], 'vectors', 'nonce_agg_vectors.json')) as f: test_data = json.load(f) pnonce = fromhex_all(test_data["pnonces"]) valid_test_cases = test_data["valid_test_cases"] error_test_cases = test_data["error_test_cases"] for test_case in valid_test_cases: pubnonces = [pnonce[i] for i in test_case["pnonce_indices"]] expected = bytes.fromhex(test_case["expected"]) assert nonce_agg(pubnonces) == expected for test_case in error_test_cases: exception, except_fn = get_error_details(test_case) pubnonces = [pnonce[i] for i in test_case["pnonce_indices"]] assert_raises(exception, lambda: nonce_agg(pubnonces), except_fn) def test_sign_verify_vectors() -> None: with open(os.path.join(sys.path[0], 'vectors', 'sign_verify_vectors.json')) as f: test_data = json.load(f) sk = bytes.fromhex(test_data["sk"]) X = fromhex_all(test_data["pubkeys"]) # The public key corresponding to sk is at index 0 assert X[0] == individual_pk(sk) secnonces = fromhex_all(test_data["secnonces"]) pnonce = fromhex_all(test_data["pnonces"]) # The public nonce corresponding to secnonces[0] is at index 0 k_1 = int_from_bytes(secnonces[0][0:32]) k_2 = int_from_bytes(secnonces[0][32:64]) R_s1 = point_mul(G, k_1) R_s2 = point_mul(G, k_2) assert R_s1 is not None and R_s2 is not None assert pnonce[0] == cbytes(R_s1) + cbytes(R_s2) aggnonces = fromhex_all(test_data["aggnonces"]) # The aggregate of the first three elements of pnonce is at index 0 assert (aggnonces[0] == nonce_agg([pnonce[0], pnonce[1], pnonce[2]])) # The aggregate of the first and fourth elements of pnonce is at index 1, # which is the infinity point encoded as a zeroed 33-byte array assert (aggnonces[1] == nonce_agg([pnonce[0], pnonce[3]])) msgs = fromhex_all(test_data["msgs"]) valid_test_cases = test_data["valid_test_cases"] sign_error_test_cases = test_data["sign_error_test_cases"] verify_fail_test_cases = test_data["verify_fail_test_cases"] verify_error_test_cases = test_data["verify_error_test_cases"] for test_case in valid_test_cases: pubkeys = [X[i] for i in test_case["key_indices"]] pubnonces = [pnonce[i] for i in test_case["nonce_indices"]] aggnonce = aggnonces[test_case["aggnonce_index"]] # Make sure that pubnonces and aggnonce in the test vector are # consistent assert nonce_agg(pubnonces) == aggnonce msg = msgs[test_case["msg_index"]] signer_index = test_case["signer_index"] expected = bytes.fromhex(test_case["expected"]) session_ctx = SessionContext(aggnonce, pubkeys, [], [], msg) # WARNING: An actual implementation should _not_ copy the secnonce. # Reusing the secnonce, as we do here for testing purposes, can leak the # secret key. secnonce_tmp = bytearray(secnonces[0]) assert sign(secnonce_tmp, sk, session_ctx) == expected assert partial_sig_verify(expected, pubnonces, pubkeys, [], [], msg, signer_index) for test_case in sign_error_test_cases: exception, except_fn = get_error_details(test_case) pubkeys = [X[i] for i in test_case["key_indices"]] aggnonce = aggnonces[test_case["aggnonce_index"]] msg = msgs[test_case["msg_index"]] secnonce = bytearray(secnonces[test_case["secnonce_index"]]) session_ctx = SessionContext(aggnonce, pubkeys, [], [], msg) assert_raises(exception, lambda: sign(secnonce, sk, session_ctx), except_fn) for test_case in verify_fail_test_cases: sig = bytes.fromhex(test_case["sig"]) pubkeys = [X[i] for i in test_case["key_indices"]] pubnonces = [pnonce[i] for i in test_case["nonce_indices"]] msg = msgs[test_case["msg_index"]] signer_index = test_case["signer_index"] assert not partial_sig_verify(sig, pubnonces, pubkeys, [], [], msg, signer_index) for test_case in verify_error_test_cases: exception, except_fn = get_error_details(test_case) sig = bytes.fromhex(test_case["sig"]) pubkeys = [X[i] for i in test_case["key_indices"]] pubnonces = [pnonce[i] for i in test_case["nonce_indices"]] msg = msgs[test_case["msg_index"]] signer_index = test_case["signer_index"] assert_raises(exception, lambda: partial_sig_verify(sig, pubnonces, pubkeys, [], [], msg, signer_index), except_fn) def test_tweak_vectors() -> None: with open(os.path.join(sys.path[0], 'vectors', 'tweak_vectors.json')) as f: test_data = json.load(f) sk = bytes.fromhex(test_data["sk"]) X = fromhex_all(test_data["pubkeys"]) # The public key corresponding to sk is at index 0 assert X[0] == individual_pk(sk) secnonce = bytearray(bytes.fromhex(test_data["secnonce"])) pnonce = fromhex_all(test_data["pnonces"]) # The public nonce corresponding to secnonce is at index 0 k_1 = int_from_bytes(secnonce[0:32]) k_2 = int_from_bytes(secnonce[32:64]) R_s1 = point_mul(G, k_1) R_s2 = point_mul(G, k_2) assert R_s1 is not None and R_s2 is not None assert pnonce[0] == cbytes(R_s1) + cbytes(R_s2) aggnonce = bytes.fromhex(test_data["aggnonce"]) # The aggnonce is the aggregate of the first three elements of pnonce assert(aggnonce == nonce_agg([pnonce[0], pnonce[1], pnonce[2]])) tweak = fromhex_all(test_data["tweaks"]) msg = bytes.fromhex(test_data["msg"]) valid_test_cases = test_data["valid_test_cases"] error_test_cases = test_data["error_test_cases"] for test_case in valid_test_cases: pubkeys = [X[i] for i in test_case["key_indices"]] pubnonces = [pnonce[i] for i in test_case["nonce_indices"]] tweaks = [tweak[i] for i in test_case["tweak_indices"]] is_xonly = test_case["is_xonly"] signer_index = test_case["signer_index"] expected = bytes.fromhex(test_case["expected"]) session_ctx = SessionContext(aggnonce, pubkeys, tweaks, is_xonly, msg) secnonce_tmp = bytearray(secnonce) # WARNING: An actual implementation should _not_ copy the secnonce. # Reusing the secnonce, as we do here for testing purposes, can leak the # secret key. assert sign(secnonce_tmp, sk, session_ctx) == expected assert partial_sig_verify(expected, pubnonces, pubkeys, tweaks, is_xonly, msg, signer_index) for test_case in error_test_cases: exception, except_fn = get_error_details(test_case) pubkeys = [X[i] for i in test_case["key_indices"]] pubnonces = [pnonce[i] for i in test_case["nonce_indices"]] tweaks = [tweak[i] for i in test_case["tweak_indices"]] is_xonly = test_case["is_xonly"] signer_index = test_case["signer_index"] session_ctx = SessionContext(aggnonce, pubkeys, tweaks, is_xonly, msg) assert_raises(exception, lambda: sign(secnonce, sk, session_ctx), except_fn) def test_det_sign_vectors() -> None: with open(os.path.join(sys.path[0], 'vectors', 'det_sign_vectors.json')) as f: test_data = json.load(f) sk = bytes.fromhex(test_data["sk"]) X = fromhex_all(test_data["pubkeys"]) # The public key corresponding to sk is at index 0 assert X[0] == individual_pk(sk) msgs = fromhex_all(test_data["msgs"]) valid_test_cases = test_data["valid_test_cases"] error_test_cases = test_data["error_test_cases"] for test_case in valid_test_cases: pubkeys = [X[i] for i in test_case["key_indices"]] aggothernonce = bytes.fromhex(test_case["aggothernonce"]) tweaks = fromhex_all(test_case["tweaks"]) is_xonly = test_case["is_xonly"] msg = msgs[test_case["msg_index"]] signer_index = test_case["signer_index"] rand = bytes.fromhex(test_case["rand"]) if test_case["rand"] is not None else None expected = fromhex_all(test_case["expected"]) pubnonce, psig = deterministic_sign(sk, aggothernonce, pubkeys, tweaks, is_xonly, msg, rand) assert pubnonce == expected[0] assert psig == expected[1] pubnonces = [aggothernonce, pubnonce] aggnonce = nonce_agg(pubnonces) session_ctx = SessionContext(aggnonce, pubkeys, tweaks, is_xonly, msg) assert partial_sig_verify_internal(psig, pubnonce, pubkeys[signer_index], session_ctx) for test_case in error_test_cases: exception, except_fn = get_error_details(test_case) pubkeys = [X[i] for i in test_case["key_indices"]] aggothernonce = bytes.fromhex(test_case["aggothernonce"]) tweaks = fromhex_all(test_case["tweaks"]) is_xonly = test_case["is_xonly"] msg = msgs[test_case["msg_index"]] signer_index = test_case["signer_index"] rand = bytes.fromhex(test_case["rand"]) if test_case["rand"] is not None else None try_fn = lambda: deterministic_sign(sk, aggothernonce, pubkeys, tweaks, is_xonly, msg, rand) assert_raises(exception, try_fn, except_fn) def test_sig_agg_vectors() -> None: with open(os.path.join(sys.path[0], 'vectors', 'sig_agg_vectors.json')) as f: test_data = json.load(f) X = fromhex_all(test_data["pubkeys"]) # These nonces are only required if the tested API takes the individual # nonces and not the aggregate nonce. pnonce = fromhex_all(test_data["pnonces"]) tweak = fromhex_all(test_data["tweaks"]) psig = fromhex_all(test_data["psigs"]) msg = bytes.fromhex(test_data["msg"]) valid_test_cases = test_data["valid_test_cases"] error_test_cases = test_data["error_test_cases"] for test_case in valid_test_cases: pubnonces = [pnonce[i] for i in test_case["nonce_indices"]] aggnonce = bytes.fromhex(test_case["aggnonce"]) assert aggnonce == nonce_agg(pubnonces) pubkeys = [X[i] for i in test_case["key_indices"]] tweaks = [tweak[i] for i in test_case["tweak_indices"]] is_xonly = test_case["is_xonly"] psigs = [psig[i] for i in test_case["psig_indices"]] expected = bytes.fromhex(test_case["expected"]) session_ctx = SessionContext(aggnonce, pubkeys, tweaks, is_xonly, msg) sig = partial_sig_agg(psigs, session_ctx) assert sig == expected aggpk = get_xonly_pk(key_agg_and_tweak(pubkeys, tweaks, is_xonly)) assert schnorr_verify(msg, aggpk, sig) for test_case in error_test_cases: exception, except_fn = get_error_details(test_case) pubnonces = [pnonce[i] for i in test_case["nonce_indices"]] aggnonce = nonce_agg(pubnonces) pubkeys = [X[i] for i in test_case["key_indices"]] tweaks = [tweak[i] for i in test_case["tweak_indices"]] is_xonly = test_case["is_xonly"] psigs = [psig[i] for i in test_case["psig_indices"]] session_ctx = SessionContext(aggnonce, pubkeys, tweaks, is_xonly, msg) assert_raises(exception, lambda: partial_sig_agg(psigs, session_ctx), except_fn) def test_sign_and_verify_random(iters: int) -> None: for i in range(iters): sk_1 = secrets.token_bytes(32) sk_2 = secrets.token_bytes(32) pk_1 = individual_pk(sk_1) pk_2 = individual_pk(sk_2) pubkeys = [pk_1, pk_2] # In this example, the message and aggregate pubkey are known # before nonce generation, so they can be passed into the nonce # generation function as a defense-in-depth measure to protect # against nonce reuse. # # If these values are not known when nonce_gen is called, empty # byte arrays can be passed in for the corresponding arguments # instead. msg = secrets.token_bytes(32) v = secrets.randbelow(4) tweaks = [secrets.token_bytes(32) for _ in range(v)] is_xonly = [secrets.choice([False, True]) for _ in range(v)] aggpk = get_xonly_pk(key_agg_and_tweak(pubkeys, tweaks, is_xonly)) # Use a non-repeating counter for extra_in secnonce_1, pubnonce_1 = nonce_gen(sk_1, pk_1, aggpk, msg, i.to_bytes(4, 'big')) # On even iterations use regular signing algorithm for signer 2, # otherwise use deterministic signing algorithm if i % 2 == 0: # Use a clock for extra_in t = time.clock_gettime_ns(time.CLOCK_MONOTONIC) secnonce_2, pubnonce_2 = nonce_gen(sk_2, pk_2, aggpk, msg, t.to_bytes(8, 'big')) else: aggothernonce = nonce_agg([pubnonce_1]) rand = secrets.token_bytes(32) pubnonce_2, psig_2 = deterministic_sign(sk_2, aggothernonce, pubkeys, tweaks, is_xonly, msg, rand) pubnonces = [pubnonce_1, pubnonce_2] aggnonce = nonce_agg(pubnonces) session_ctx = SessionContext(aggnonce, pubkeys, tweaks, is_xonly, msg) psig_1 = sign(secnonce_1, sk_1, session_ctx) assert partial_sig_verify(psig_1, pubnonces, pubkeys, tweaks, is_xonly, msg, 0) # An exception is thrown if secnonce_1 is accidentally reused assert_raises(ValueError, lambda: sign(secnonce_1, sk_1, session_ctx), lambda e: True) # Wrong signer index assert not partial_sig_verify(psig_1, pubnonces, pubkeys, tweaks, is_xonly, msg, 1) # Wrong message assert not partial_sig_verify(psig_1, pubnonces, pubkeys, tweaks, is_xonly, secrets.token_bytes(32), 0) if i % 2 == 0: psig_2 = sign(secnonce_2, sk_2, session_ctx) assert partial_sig_verify(psig_2, pubnonces, pubkeys, tweaks, is_xonly, msg, 1) sig = partial_sig_agg([psig_1, psig_2], session_ctx) assert schnorr_verify(msg, aggpk, sig) if __name__ == '__main__': test_key_sort_vectors() test_key_agg_vectors() test_nonce_gen_vectors() test_nonce_agg_vectors() test_sign_verify_vectors() test_tweak_vectors() test_det_sign_vectors() test_sig_agg_vectors() test_sign_and_verify_random(6) ================================================ FILE: bip-0327/tests.sh ================================================ #!/bin/sh set -e cd "$(dirname "$0")" mypy --no-error-summary reference.py python3 reference.py python3 gen_vectors_helper.py > /dev/null ================================================ FILE: bip-0327/vectors/det_sign_vectors.json ================================================ { "sk": "7FB9E0E687ADA1EEBF7ECFE2F21E73EBDB51A7D450948DFE8D76D7F2D1007671", "pubkeys": [ "03935F972DA013F80AE011890FA89B67A27B7BE6CCB24D3274D18B2D4067F261A9", "02F9308A019258C31049344F85F89D5229B531C845836F99B08601F113BCE036F9", "02DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA659", "020000000000000000000000000000000000000000000000000000000000000007" ], "msgs": [ "F95466D086770E689964664219266FE5ED215C92AE20BAB5C9D79ADDDDF3C0CF", "2626262626262626262626262626262626262626262626262626262626262626262626262626" ], "valid_test_cases": [ { "rand": "0000000000000000000000000000000000000000000000000000000000000000", "aggothernonce": "0337C87821AFD50A8644D820A8F3E02E499C931865C2360FB43D0A0D20DAFE07EA0287BF891D2A6DEAEBADC909352AA9405D1428C15F4B75F04DAE642A95C2548480", "key_indices": [0, 1, 2], "tweaks": [], "is_xonly": [], "msg_index": 0, "signer_index": 0, "expected": [ "03D96275257C2FCCBB6EEB77BDDF51D3C88C26EE1626C6CDA8999B9D34F4BA13A60309BE2BF883C6ABE907FA822D9CA166D51A3DCC28910C57528F6983FC378B7843", "41EA65093F71D084785B20DC26A887CD941C9597860A21660CBDB9CC2113CAD3" ] }, { "rand": null, "aggothernonce": "0337C87821AFD50A8644D820A8F3E02E499C931865C2360FB43D0A0D20DAFE07EA0287BF891D2A6DEAEBADC909352AA9405D1428C15F4B75F04DAE642A95C2548480", "key_indices": [1, 0, 2], "tweaks": [], "is_xonly": [], "msg_index": 0, "signer_index": 1, "expected": [ "028FBCCF5BB73A7B61B270BAD15C0F9475D577DD85C2157C9D38BEF1EC922B48770253BE3638C87369BC287E446B7F2C8CA5BEB9FFBD1EA082C62913982A65FC214D", "AEAA31262637BFA88D5606679018A0FEEEC341F3107D1199857F6C81DE61B8DD" ] }, { "rand": "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF", "aggothernonce": "0279BE667EF9DCBBAC55A06295CE870B07029BFCDB2DCE28D959F2815B16F817980279BE667EF9DCBBAC55A06295CE870B07029BFCDB2DCE28D959F2815B16F81798", "key_indices": [1, 2, 0], "tweaks": [], "is_xonly": [], "msg_index": 1, "signer_index": 2, "expected": [ "024FA8D774F0C8743FAA77AFB4D08EE5A013C2E8EEAD8A6F08A77DDD2D28266DB803050905E8C994477F3F2981861A2E3791EF558626E645FBF5AA131C5D6447C2C2", "FEE28A56B8556B7632E42A84122C51A4861B1F2DEC7E81B632195E56A52E3E13" ], "comment": "Message longer than 32 bytes" }, { "rand": "0000000000000000000000000000000000000000000000000000000000000000", "aggothernonce": "032DE2662628C90B03F5E720284EB52FF7D71F4284F627B68A853D78C78E1FFE9303E4C5524E83FFE1493B9077CF1CA6BEB2090C93D930321071AD40B2F44E599046", "key_indices": [0, 1, 2], "tweaks": ["E8F791FF9225A2AF0102AFFF4A9A723D9612A682A25EBE79802B263CDFCD83BB"], "is_xonly": [true], "msg_index": 0, "signer_index": 0, "expected": [ "031E07C0D11A0134E55DB1FC16095ADCBD564236194374AA882BFB3C78273BF673039D0336E8CA6288C00BFC1F8B594563529C98661172B9BC1BE85C23A4CE1F616B", "7B1246C5889E59CB0375FA395CC86AC42D5D7D59FD8EAB4FDF1DCAB2B2F006EA" ], "comment": "Tweaked public key" } ], "error_test_cases": [ { "rand": "0000000000000000000000000000000000000000000000000000000000000000", "aggothernonce": "0337C87821AFD50A8644D820A8F3E02E499C931865C2360FB43D0A0D20DAFE07EA0287BF891D2A6DEAEBADC909352AA9405D1428C15F4B75F04DAE642A95C2548480", "key_indices": [1, 0, 3], "tweaks": [], "is_xonly": [], "msg_index": 0, "signer_index": 1, "error": { "type": "invalid_contribution", "signer": 2, "contrib": "pubkey" }, "comment": "Signer 2 provided an invalid public key" }, { "rand": "0000000000000000000000000000000000000000000000000000000000000000", "aggothernonce": "0337C87821AFD50A8644D820A8F3E02E499C931865C2360FB43D0A0D20DAFE07EA0287BF891D2A6DEAEBADC909352AA9405D1428C15F4B75F04DAE642A95C2548480", "key_indices": [1, 2], "tweaks": [], "is_xonly": [], "msg_index": 0, "signer_index": 1, "error": { "type": "value", "message": "The signer's pubkey must be included in the list of pubkeys." }, "comment": "The signers pubkey is not in the list of pubkeys" }, { "rand": "0000000000000000000000000000000000000000000000000000000000000000", "aggothernonce": "0437C87821AFD50A8644D820A8F3E02E499C931865C2360FB43D0A0D20DAFE07EA0287BF891D2A6DEAEBADC909352AA9405D1428C15F4B75F04DAE642A95C2548480", "key_indices": [1, 2, 0], "tweaks": [], "is_xonly": [], "msg_index": 0, "signer_index": 2, "error": { "type": "invalid_contribution", "signer": null, "contrib": "aggothernonce" }, "comment": "aggothernonce is invalid due wrong tag, 0x04, in the first half" }, { "rand": "0000000000000000000000000000000000000000000000000000000000000000", "aggothernonce": "0000000000000000000000000000000000000000000000000000000000000000000287BF891D2A6DEAEBADC909352AA9405D1428C15F4B75F04DAE642A95C2548480", "key_indices": [1, 2, 0], "tweaks": [], "is_xonly": [], "msg_index": 0, "signer_index": 2, "error": { "type": "invalid_contribution", "signer": null, "contrib": "aggothernonce" }, "comment": "aggothernonce is invalid because first half corresponds to point at infinity" }, { "rand": "0000000000000000000000000000000000000000000000000000000000000000", "aggothernonce": "0337C87821AFD50A8644D820A8F3E02E499C931865C2360FB43D0A0D20DAFE07EA0287BF891D2A6DEAEBADC909352AA9405D1428C15F4B75F04DAE642A95C2548480", "key_indices": [1, 2, 0], "tweaks": ["FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141"], "is_xonly": [false], "msg_index": 0, "signer_index": 2, "error": { "type": "value", "message": "The tweak must be less than n." }, "comment": "Tweak is invalid because it exceeds group size" } ] } ================================================ FILE: bip-0327/vectors/key_agg_vectors.json ================================================ { "pubkeys": [ "02F9308A019258C31049344F85F89D5229B531C845836F99B08601F113BCE036F9", "03DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA659", "023590A94E768F8E1815C2F24B4D80A8E3149316C3518CE7B7AD338368D038CA66", "020000000000000000000000000000000000000000000000000000000000000005", "02FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEFFFFFC30", "04F9308A019258C31049344F85F89D5229B531C845836F99B08601F113BCE036F9", "03935F972DA013F80AE011890FA89B67A27B7BE6CCB24D3274D18B2D4067F261A9" ], "tweaks": [ "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141", "252E4BD67410A76CDF933D30EAA1608214037F1B105A013ECCD3C5C184A6110B" ], "valid_test_cases": [ { "key_indices": [0, 1, 2], "expected": "90539EEDE565F5D054F32CC0C220126889ED1E5D193BAF15AEF344FE59D4610C" }, { "key_indices": [2, 1, 0], "expected": "6204DE8B083426DC6EAF9502D27024D53FC826BF7D2012148A0575435DF54B2B" }, { "key_indices": [0, 0, 0], "expected": "B436E3BAD62B8CD409969A224731C193D051162D8C5AE8B109306127DA3AA935" }, { "key_indices": [0, 0, 1, 1], "expected": "69BC22BFA5D106306E48A20679DE1D7389386124D07571D0D872686028C26A3E" } ], "error_test_cases": [ { "key_indices": [0, 3], "tweak_indices": [], "is_xonly": [], "error": { "type": "invalid_contribution", "signer": 1, "contrib": "pubkey" }, "comment": "Invalid public key" }, { "key_indices": [0, 4], "tweak_indices": [], "is_xonly": [], "error": { "type": "invalid_contribution", "signer": 1, "contrib": "pubkey" }, "comment": "Public key exceeds field size" }, { "key_indices": [5, 0], "tweak_indices": [], "is_xonly": [], "error": { "type": "invalid_contribution", "signer": 0, "contrib": "pubkey" }, "comment": "First byte of public key is not 2 or 3" }, { "key_indices": [0, 1], "tweak_indices": [0], "is_xonly": [true], "error": { "type": "value", "message": "The tweak must be less than n." }, "comment": "Tweak is out of range" }, { "key_indices": [6], "tweak_indices": [1], "is_xonly": [false], "error": { "type": "value", "message": "The result of tweaking cannot be infinity." }, "comment": "Intermediate tweaking result is point at infinity" } ] } ================================================ FILE: bip-0327/vectors/key_sort_vectors.json ================================================ { "pubkeys": [ "02DD308AFEC5777E13121FA72B9CC1B7CC0139715309B086C960E18FD969774EB8", "02F9308A019258C31049344F85F89D5229B531C845836F99B08601F113BCE036F9", "03DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA659", "023590A94E768F8E1815C2F24B4D80A8E3149316C3518CE7B7AD338368D038CA66", "02DD308AFEC5777E13121FA72B9CC1B7CC0139715309B086C960E18FD969774EFF", "02DD308AFEC5777E13121FA72B9CC1B7CC0139715309B086C960E18FD969774EB8" ], "sorted_pubkeys": [ "023590A94E768F8E1815C2F24B4D80A8E3149316C3518CE7B7AD338368D038CA66", "02DD308AFEC5777E13121FA72B9CC1B7CC0139715309B086C960E18FD969774EB8", "02DD308AFEC5777E13121FA72B9CC1B7CC0139715309B086C960E18FD969774EB8", "02DD308AFEC5777E13121FA72B9CC1B7CC0139715309B086C960E18FD969774EFF", "02F9308A019258C31049344F85F89D5229B531C845836F99B08601F113BCE036F9", "03DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA659" ] } ================================================ FILE: bip-0327/vectors/nonce_agg_vectors.json ================================================ { "pnonces": [ "020151C80F435648DF67A22B749CD798CE54E0321D034B92B709B567D60A42E66603BA47FBC1834437B3212E89A84D8425E7BF12E0245D98262268EBDCB385D50641", "03FF406FFD8ADB9CD29877E4985014F66A59F6CD01C0E88CAA8E5F3166B1F676A60248C264CDD57D3C24D79990B0F865674EB62A0F9018277A95011B41BFC193B833", "020151C80F435648DF67A22B749CD798CE54E0321D034B92B709B567D60A42E6660279BE667EF9DCBBAC55A06295CE870B07029BFCDB2DCE28D959F2815B16F81798", "03FF406FFD8ADB9CD29877E4985014F66A59F6CD01C0E88CAA8E5F3166B1F676A60379BE667EF9DCBBAC55A06295CE870B07029BFCDB2DCE28D959F2815B16F81798", "04FF406FFD8ADB9CD29877E4985014F66A59F6CD01C0E88CAA8E5F3166B1F676A60248C264CDD57D3C24D79990B0F865674EB62A0F9018277A95011B41BFC193B833", "03FF406FFD8ADB9CD29877E4985014F66A59F6CD01C0E88CAA8E5F3166B1F676A60248C264CDD57D3C24D79990B0F865674EB62A0F9018277A95011B41BFC193B831", "03FF406FFD8ADB9CD29877E4985014F66A59F6CD01C0E88CAA8E5F3166B1F676A602FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEFFFFFC30" ], "valid_test_cases": [ { "pnonce_indices": [0, 1], "expected": "035FE1873B4F2967F52FEA4A06AD5A8ECCBE9D0FD73068012C894E2E87CCB5804B024725377345BDE0E9C33AF3C43C0A29A9249F2F2956FA8CFEB55C8573D0262DC8" }, { "pnonce_indices": [2, 3], "expected": "035FE1873B4F2967F52FEA4A06AD5A8ECCBE9D0FD73068012C894E2E87CCB5804B000000000000000000000000000000000000000000000000000000000000000000", "comment": "Sum of second points encoded in the nonces is point at infinity which is serialized as 33 zero bytes" } ], "error_test_cases": [ { "pnonce_indices": [0, 4], "error": { "type": "invalid_contribution", "signer": 1, "contrib": "pubnonce" }, "comment": "Public nonce from signer 1 is invalid due wrong tag, 0x04, in the first half" }, { "pnonce_indices": [5, 1], "error": { "type": "invalid_contribution", "signer": 0, "contrib": "pubnonce" }, "comment": "Public nonce from signer 0 is invalid because the second half does not correspond to an X coordinate" }, { "pnonce_indices": [6, 1], "error": { "type": "invalid_contribution", "signer": 0, "contrib": "pubnonce" }, "comment": "Public nonce from signer 0 is invalid because second half exceeds field size" } ] } ================================================ FILE: bip-0327/vectors/nonce_gen_vectors.json ================================================ { "test_cases": [ { "rand_": "0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F", "sk": "0202020202020202020202020202020202020202020202020202020202020202", "pk": "024D4B6CD1361032CA9BD2AEB9D900AA4D45D9EAD80AC9423374C451A7254D0766", "aggpk": "0707070707070707070707070707070707070707070707070707070707070707", "msg": "0101010101010101010101010101010101010101010101010101010101010101", "extra_in": "0808080808080808080808080808080808080808080808080808080808080808", "expected_secnonce": "B114E502BEAA4E301DD08A50264172C84E41650E6CB726B410C0694D59EFFB6495B5CAF28D045B973D63E3C99A44B807BDE375FD6CB39E46DC4A511708D0E9D2024D4B6CD1361032CA9BD2AEB9D900AA4D45D9EAD80AC9423374C451A7254D0766", "expected_pubnonce": "02F7BE7089E8376EB355272368766B17E88E7DB72047D05E56AA881EA52B3B35DF02C29C8046FDD0DED4C7E55869137200FBDBFE2EB654267B6D7013602CAED3115A" }, { "rand_": "0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F", "sk": "0202020202020202020202020202020202020202020202020202020202020202", "pk": "024D4B6CD1361032CA9BD2AEB9D900AA4D45D9EAD80AC9423374C451A7254D0766", "aggpk": "0707070707070707070707070707070707070707070707070707070707070707", "msg": "", "extra_in": "0808080808080808080808080808080808080808080808080808080808080808", "expected_secnonce": "E862B068500320088138468D47E0E6F147E01B6024244AE45EAC40ACE5929B9F0789E051170B9E705D0B9EB49049A323BBBBB206D8E05C19F46C6228742AA7A9024D4B6CD1361032CA9BD2AEB9D900AA4D45D9EAD80AC9423374C451A7254D0766", "expected_pubnonce": "023034FA5E2679F01EE66E12225882A7A48CC66719B1B9D3B6C4DBD743EFEDA2C503F3FD6F01EB3A8E9CB315D73F1F3D287CAFBB44AB321153C6287F407600205109" }, { "rand_": "0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F", "sk": "0202020202020202020202020202020202020202020202020202020202020202", "pk": "024D4B6CD1361032CA9BD2AEB9D900AA4D45D9EAD80AC9423374C451A7254D0766", "aggpk": "0707070707070707070707070707070707070707070707070707070707070707", "msg": "2626262626262626262626262626262626262626262626262626262626262626262626262626", "extra_in": "0808080808080808080808080808080808080808080808080808080808080808", "expected_secnonce": "3221975ACBDEA6820EABF02A02B7F27D3A8EF68EE42787B88CBEFD9AA06AF3632EE85B1A61D8EF31126D4663A00DD96E9D1D4959E72D70FE5EBB6E7696EBA66F024D4B6CD1361032CA9BD2AEB9D900AA4D45D9EAD80AC9423374C451A7254D0766", "expected_pubnonce": "02E5BBC21C69270F59BD634FCBFA281BE9D76601295345112C58954625BF23793A021307511C79F95D38ACACFF1B4DA98228B77E65AA216AD075E9673286EFB4EAF3" }, { "rand_": "0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F0F", "sk": null, "pk": "02F9308A019258C31049344F85F89D5229B531C845836F99B08601F113BCE036F9", "aggpk": null, "msg": null, "extra_in": null, "expected_secnonce": "89BDD787D0284E5E4D5FC572E49E316BAB7E21E3B1830DE37DFE80156FA41A6D0B17AE8D024C53679699A6FD7944D9C4A366B514BAF43088E0708B1023DD289702F9308A019258C31049344F85F89D5229B531C845836F99B08601F113BCE036F9", "expected_pubnonce": "02C96E7CB1E8AA5DAC64D872947914198F607D90ECDE5200DE52978AD5DED63C000299EC5117C2D29EDEE8A2092587C3909BE694D5CFF0667D6C02EA4059F7CD9786" } ] } ================================================ FILE: bip-0327/vectors/sig_agg_vectors.json ================================================ { "pubkeys": [ "03935F972DA013F80AE011890FA89B67A27B7BE6CCB24D3274D18B2D4067F261A9", "02D2DC6F5DF7C56ACF38C7FA0AE7A759AE30E19B37359DFDE015872324C7EF6E05", "03C7FB101D97FF930ACD0C6760852EF64E69083DE0B06AC6335724754BB4B0522C", "02352433B21E7E05D3B452B81CAE566E06D2E003ECE16D1074AABA4289E0E3D581" ], "pnonces": [ "036E5EE6E28824029FEA3E8A9DDD2C8483F5AF98F7177C3AF3CB6F47CAF8D94AE902DBA67E4A1F3680826172DA15AFB1A8CA85C7C5CC88900905C8DC8C328511B53E", "03E4F798DA48A76EEC1C9CC5AB7A880FFBA201A5F064E627EC9CB0031D1D58FC5103E06180315C5A522B7EC7C08B69DCD721C313C940819296D0A7AB8E8795AC1F00", "02C0068FD25523A31578B8077F24F78F5BD5F2422AFF47C1FADA0F36B3CEB6C7D202098A55D1736AA5FCC21CF0729CCE852575C06C081125144763C2C4C4A05C09B6", "031F5C87DCFBFCF330DEE4311D85E8F1DEA01D87A6F1C14CDFC7E4F1D8C441CFA40277BF176E9F747C34F81B0D9F072B1B404A86F402C2D86CF9EA9E9C69876EA3B9", "023F7042046E0397822C4144A17F8B63D78748696A46C3B9F0A901D296EC3406C302022B0B464292CF9751D699F10980AC764E6F671EFCA15069BBE62B0D1C62522A", "02D97DDA5988461DF58C5897444F116A7C74E5711BF77A9446E27806563F3B6C47020CBAD9C363A7737F99FA06B6BE093CEAFF5397316C5AC46915C43767AE867C00" ], "tweaks": [ "B511DA492182A91B0FFB9A98020D55F260AE86D7ECBD0399C7383D59A5F2AF7C", "A815FE049EE3C5AAB66310477FBC8BCCCAC2F3395F59F921C364ACD78A2F48DC", "75448A87274B056468B977BE06EB1E9F657577B7320B0A3376EA51FD420D18A8" ], "psigs": [ "B15D2CD3C3D22B04DAE438CE653F6B4ECF042F42CFDED7C41B64AAF9B4AF53FB", "6193D6AC61B354E9105BBDC8937A3454A6D705B6D57322A5A472A02CE99FCB64", "9A87D3B79EC67228CB97878B76049B15DBD05B8158D17B5B9114D3C226887505", "66F82EA90923689B855D36C6B7E032FB9970301481B99E01CDB4D6AC7C347A15", "4F5AEE41510848A6447DCD1BBC78457EF69024944C87F40250D3EF2C25D33EFE", "DDEF427BBB847CC027BEFF4EDB01038148917832253EBC355FC33F4A8E2FCCE4", "97B890A26C981DA8102D3BC294159D171D72810FDF7C6A691DEF02F0F7AF3FDC", "53FA9E08BA5243CBCB0D797C5EE83BC6728E539EB76C2D0BF0F971EE4E909971", "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141" ], "msg": "599C67EA410D005B9DA90817CF03ED3B1C868E4DA4EDF00A5880B0082C237869", "valid_test_cases": [ { "aggnonce": "0341432722C5CD0268D829C702CF0D1CBCE57033EED201FD335191385227C3210C03D377F2D258B64AADC0E16F26462323D701D286046A2EA93365656AFD9875982B", "nonce_indices": [ 0, 1 ], "key_indices": [ 0, 1 ], "tweak_indices": [], "is_xonly": [], "psig_indices": [ 0, 1 ], "expected": "041DA22223CE65C92C9A0D6C2CAC828AAF1EEE56304FEC371DDF91EBB2B9EF0912F1038025857FEDEB3FF696F8B99FA4BB2C5812F6095A2E0004EC99CE18DE1E" }, { "aggnonce": "0224AFD36C902084058B51B5D36676BBA4DC97C775873768E58822F87FE437D792028CB15929099EEE2F5DAE404CD39357591BA32E9AF4E162B8D3E7CB5EFE31CB20", "nonce_indices": [ 0, 2 ], "key_indices": [ 0, 2 ], "tweak_indices": [], "is_xonly": [], "psig_indices": [ 2, 3 ], "expected": "1069B67EC3D2F3C7C08291ACCB17A9C9B8F2819A52EB5DF8726E17E7D6B52E9F01800260A7E9DAC450F4BE522DE4CE12BA91AEAF2B4279219EF74BE1D286ADD9" }, { "aggnonce": "0208C5C438C710F4F96A61E9FF3C37758814B8C3AE12BFEA0ED2C87FF6954FF186020B1816EA104B4FCA2D304D733E0E19CEAD51303FF6420BFD222335CAA402916D", "nonce_indices": [ 0, 3 ], "key_indices": [ 0, 2 ], "tweak_indices": [ 0 ], "is_xonly": [ false ], "psig_indices": [ 4, 5 ], "expected": "5C558E1DCADE86DA0B2F02626A512E30A22CF5255CAEA7EE32C38E9A71A0E9148BA6C0E6EC7683B64220F0298696F1B878CD47B107B81F7188812D593971E0CC" }, { "aggnonce": "02B5AD07AFCD99B6D92CB433FBD2A28FDEB98EAE2EB09B6014EF0F8197CD58403302E8616910F9293CF692C49F351DB86B25E352901F0E237BAFDA11F1C1CEF29FFD", "nonce_indices": [ 0, 4 ], "key_indices": [ 0, 3 ], "tweak_indices": [ 0, 1, 2 ], "is_xonly": [ true, false, true ], "psig_indices": [ 6, 7 ], "expected": "839B08820B681DBA8DAF4CC7B104E8F2638F9388F8D7A555DC17B6E6971D7426CE07BF6AB01F1DB50E4E33719295F4094572B79868E440FB3DEFD3FAC1DB589E" } ], "error_test_cases": [ { "aggnonce": "02B5AD07AFCD99B6D92CB433FBD2A28FDEB98EAE2EB09B6014EF0F8197CD58403302E8616910F9293CF692C49F351DB86B25E352901F0E237BAFDA11F1C1CEF29FFD", "nonce_indices": [ 0, 4 ], "key_indices": [ 0, 3 ], "tweak_indices": [ 0, 1, 2 ], "is_xonly": [ true, false, true ], "psig_indices": [ 7, 8 ], "error": { "type": "invalid_contribution", "signer": 1, "contrib": "psig" }, "comment": "Partial signature is invalid because it exceeds group size" } ] } ================================================ FILE: bip-0327/vectors/sign_verify_vectors.json ================================================ { "sk": "7FB9E0E687ADA1EEBF7ECFE2F21E73EBDB51A7D450948DFE8D76D7F2D1007671", "pubkeys": [ "03935F972DA013F80AE011890FA89B67A27B7BE6CCB24D3274D18B2D4067F261A9", "02F9308A019258C31049344F85F89D5229B531C845836F99B08601F113BCE036F9", "02DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA661", "020000000000000000000000000000000000000000000000000000000000000007" ], "secnonces": [ "508B81A611F100A6B2B6B29656590898AF488BCF2E1F55CF22E5CFB84421FE61FA27FD49B1D50085B481285E1CA205D55C82CC1B31FF5CD54A489829355901F703935F972DA013F80AE011890FA89B67A27B7BE6CCB24D3274D18B2D4067F261A9", "0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000003935F972DA013F80AE011890FA89B67A27B7BE6CCB24D3274D18B2D4067F261A9" ], "pnonces": [ "0337C87821AFD50A8644D820A8F3E02E499C931865C2360FB43D0A0D20DAFE07EA0287BF891D2A6DEAEBADC909352AA9405D1428C15F4B75F04DAE642A95C2548480", "0279BE667EF9DCBBAC55A06295CE870B07029BFCDB2DCE28D959F2815B16F817980279BE667EF9DCBBAC55A06295CE870B07029BFCDB2DCE28D959F2815B16F81798", "032DE2662628C90B03F5E720284EB52FF7D71F4284F627B68A853D78C78E1FFE9303E4C5524E83FFE1493B9077CF1CA6BEB2090C93D930321071AD40B2F44E599046", "0237C87821AFD50A8644D820A8F3E02E499C931865C2360FB43D0A0D20DAFE07EA0387BF891D2A6DEAEBADC909352AA9405D1428C15F4B75F04DAE642A95C2548480", "0200000000000000000000000000000000000000000000000000000000000000090287BF891D2A6DEAEBADC909352AA9405D1428C15F4B75F04DAE642A95C2548480" ], "aggnonces": [ "028465FCF0BBDBCF443AABCCE533D42B4B5A10966AC09A49655E8C42DAAB8FCD61037496A3CC86926D452CAFCFD55D25972CA1675D549310DE296BFF42F72EEEA8C9", "000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000", "048465FCF0BBDBCF443AABCCE533D42B4B5A10966AC09A49655E8C42DAAB8FCD61037496A3CC86926D452CAFCFD55D25972CA1675D549310DE296BFF42F72EEEA8C9", "028465FCF0BBDBCF443AABCCE533D42B4B5A10966AC09A49655E8C42DAAB8FCD61020000000000000000000000000000000000000000000000000000000000000009", "028465FCF0BBDBCF443AABCCE533D42B4B5A10966AC09A49655E8C42DAAB8FCD6102FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEFFFFFC30" ], "msgs": [ "F95466D086770E689964664219266FE5ED215C92AE20BAB5C9D79ADDDDF3C0CF", "", "2626262626262626262626262626262626262626262626262626262626262626262626262626" ], "valid_test_cases": [ { "key_indices": [0, 1, 2], "nonce_indices": [0, 1, 2], "aggnonce_index": 0, "msg_index": 0, "signer_index": 0, "expected": "012ABBCB52B3016AC03AD82395A1A415C48B93DEF78718E62A7A90052FE224FB" }, { "key_indices": [1, 0, 2], "nonce_indices": [1, 0, 2], "aggnonce_index": 0, "msg_index": 0, "signer_index": 1, "expected": "9FF2F7AAA856150CC8819254218D3ADEEB0535269051897724F9DB3789513A52" }, { "key_indices": [1, 2, 0], "nonce_indices": [1, 2, 0], "aggnonce_index": 0, "msg_index": 0, "signer_index": 2, "expected": "FA23C359F6FAC4E7796BB93BC9F0532A95468C539BA20FF86D7C76ED92227900" }, { "key_indices": [0, 1], "nonce_indices": [0, 3], "aggnonce_index": 1, "msg_index": 0, "signer_index": 0, "expected": "AE386064B26105404798F75DE2EB9AF5EDA5387B064B83D049CB7C5E08879531", "comment": "Both halves of aggregate nonce correspond to point at infinity" }, { "key_indices": [0, 1, 2], "nonce_indices": [0, 1, 2], "aggnonce_index": 0, "msg_index": 1, "signer_index": 0, "expected": "D7D63FFD644CCDA4E62BC2BC0B1D02DD32A1DC3030E155195810231D1037D82D", "comment": "Empty message" }, { "key_indices": [0, 1, 2], "nonce_indices": [0, 1, 2], "aggnonce_index": 0, "msg_index": 2, "signer_index": 0, "expected": "E184351828DA5094A97C79CABDAAA0BFB87608C32E8829A4DF5340A6F243B78C", "comment": "38-byte message" } ], "sign_error_test_cases": [ { "key_indices": [1, 2], "aggnonce_index": 0, "msg_index": 0, "secnonce_index": 0, "error": { "type": "value", "message": "The signer's pubkey must be included in the list of pubkeys." }, "comment": "The signers pubkey is not in the list of pubkeys. This test case is optional: it can be skipped by implementations that do not check that the signer's pubkey is included in the list of pubkeys." }, { "key_indices": [1, 0, 3], "aggnonce_index": 0, "msg_index": 0, "secnonce_index": 0, "error": { "type": "invalid_contribution", "signer": 2, "contrib": "pubkey" }, "comment": "Signer 2 provided an invalid public key" }, { "key_indices": [1, 2, 0], "aggnonce_index": 2, "msg_index": 0, "secnonce_index": 0, "error": { "type": "invalid_contribution", "signer": null, "contrib": "aggnonce" }, "comment": "Aggregate nonce is invalid due wrong tag, 0x04, in the first half" }, { "key_indices": [1, 2, 0], "aggnonce_index": 3, "msg_index": 0, "secnonce_index": 0, "error": { "type": "invalid_contribution", "signer": null, "contrib": "aggnonce" }, "comment": "Aggregate nonce is invalid because the second half does not correspond to an X coordinate" }, { "key_indices": [1, 2, 0], "aggnonce_index": 4, "msg_index": 0, "secnonce_index": 0, "error": { "type": "invalid_contribution", "signer": null, "contrib": "aggnonce" }, "comment": "Aggregate nonce is invalid because second half exceeds field size" }, { "key_indices": [0, 1, 2], "aggnonce_index": 0, "msg_index": 0, "signer_index": 0, "secnonce_index": 1, "error": { "type": "value", "message": "first secnonce value is out of range." }, "comment": "Secnonce is invalid which may indicate nonce reuse" } ], "verify_fail_test_cases": [ { "sig": "FED54434AD4CFE953FC527DC6A5E5BE8F6234907B7C187559557CE87A0541C46", "key_indices": [0, 1, 2], "nonce_indices": [0, 1, 2], "msg_index": 0, "signer_index": 0, "comment": "Wrong signature (which is equal to the negation of valid signature)" }, { "sig": "012ABBCB52B3016AC03AD82395A1A415C48B93DEF78718E62A7A90052FE224FB", "key_indices": [0, 1, 2], "nonce_indices": [0, 1, 2], "msg_index": 0, "signer_index": 1, "comment": "Wrong signer" }, { "sig": "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141", "key_indices": [0, 1, 2], "nonce_indices": [0, 1, 2], "msg_index": 0, "signer_index": 0, "comment": "Signature exceeds group size" } ], "verify_error_test_cases": [ { "sig": "012ABBCB52B3016AC03AD82395A1A415C48B93DEF78718E62A7A90052FE224FB", "key_indices": [0, 1, 2], "nonce_indices": [4, 1, 2], "msg_index": 0, "signer_index": 0, "error": { "type": "invalid_contribution", "signer": 0, "contrib": "pubnonce" }, "comment": "Invalid pubnonce" }, { "sig": "012ABBCB52B3016AC03AD82395A1A415C48B93DEF78718E62A7A90052FE224FB", "key_indices": [3, 1, 2], "nonce_indices": [0, 1, 2], "msg_index": 0, "signer_index": 0, "error": { "type": "invalid_contribution", "signer": 0, "contrib": "pubkey" }, "comment": "Invalid pubkey" } ] } ================================================ FILE: bip-0327/vectors/tweak_vectors.json ================================================ { "sk": "7FB9E0E687ADA1EEBF7ECFE2F21E73EBDB51A7D450948DFE8D76D7F2D1007671", "pubkeys": [ "03935F972DA013F80AE011890FA89B67A27B7BE6CCB24D3274D18B2D4067F261A9", "02F9308A019258C31049344F85F89D5229B531C845836F99B08601F113BCE036F9", "02DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA659" ], "secnonce": "508B81A611F100A6B2B6B29656590898AF488BCF2E1F55CF22E5CFB84421FE61FA27FD49B1D50085B481285E1CA205D55C82CC1B31FF5CD54A489829355901F703935F972DA013F80AE011890FA89B67A27B7BE6CCB24D3274D18B2D4067F261A9", "pnonces": [ "0337C87821AFD50A8644D820A8F3E02E499C931865C2360FB43D0A0D20DAFE07EA0287BF891D2A6DEAEBADC909352AA9405D1428C15F4B75F04DAE642A95C2548480", "0279BE667EF9DCBBAC55A06295CE870B07029BFCDB2DCE28D959F2815B16F817980279BE667EF9DCBBAC55A06295CE870B07029BFCDB2DCE28D959F2815B16F81798", "032DE2662628C90B03F5E720284EB52FF7D71F4284F627B68A853D78C78E1FFE9303E4C5524E83FFE1493B9077CF1CA6BEB2090C93D930321071AD40B2F44E599046" ], "aggnonce": "028465FCF0BBDBCF443AABCCE533D42B4B5A10966AC09A49655E8C42DAAB8FCD61037496A3CC86926D452CAFCFD55D25972CA1675D549310DE296BFF42F72EEEA8C9", "tweaks": [ "E8F791FF9225A2AF0102AFFF4A9A723D9612A682A25EBE79802B263CDFCD83BB", "AE2EA797CC0FE72AC5B97B97F3C6957D7E4199A167A58EB08BCAFFDA70AC0455", "F52ECBC565B3D8BEA2DFD5B75A4F457E54369809322E4120831626F290FA87E0", "1969AD73CC177FA0B4FCED6DF1F7BF9907E665FDE9BA196A74FED0A3CF5AEF9D", "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141" ], "msg": "F95466D086770E689964664219266FE5ED215C92AE20BAB5C9D79ADDDDF3C0CF", "valid_test_cases": [ { "key_indices": [1, 2, 0], "nonce_indices": [1, 2, 0], "tweak_indices": [0], "is_xonly": [true], "signer_index": 2, "expected": "E28A5C66E61E178C2BA19DB77B6CF9F7E2F0F56C17918CD13135E60CC848FE91", "comment": "A single x-only tweak" }, { "key_indices": [1, 2, 0], "nonce_indices": [1, 2, 0], "tweak_indices": [0], "is_xonly": [false], "signer_index": 2, "expected": "38B0767798252F21BF5702C48028B095428320F73A4B14DB1E25DE58543D2D2D", "comment": "A single plain tweak" }, { "key_indices": [1, 2, 0], "nonce_indices": [1, 2, 0], "tweak_indices": [0, 1], "is_xonly": [false, true], "signer_index": 2, "expected": "408A0A21C4A0F5DACAF9646AD6EB6FECD7F7A11F03ED1F48DFFF2185BC2C2408", "comment": "A plain tweak followed by an x-only tweak" }, { "key_indices": [1, 2, 0], "nonce_indices": [1, 2, 0], "tweak_indices": [0, 1, 2, 3], "is_xonly": [false, false, true, true], "signer_index": 2, "expected": "45ABD206E61E3DF2EC9E264A6FEC8292141A633C28586388235541F9ADE75435", "comment": "Four tweaks: plain, plain, x-only, x-only." }, { "key_indices": [1, 2, 0], "nonce_indices": [1, 2, 0], "tweak_indices": [0, 1, 2, 3], "is_xonly": [true, false, true, false], "signer_index": 2, "expected": "B255FDCAC27B40C7CE7848E2D3B7BF5EA0ED756DA81565AC804CCCA3E1D5D239", "comment": "Four tweaks: x-only, plain, x-only, plain. If an implementation prohibits applying plain tweaks after x-only tweaks, it can skip this test vector or return an error." } ], "error_test_cases": [ { "key_indices": [1, 2, 0], "nonce_indices": [1, 2, 0], "tweak_indices": [4], "is_xonly": [false], "signer_index": 2, "error": { "type": "value", "message": "The tweak must be less than n." }, "comment": "Tweak is invalid because it exceeds group size" } ] } ================================================ FILE: bip-0327.mediawiki ================================================
  BIP: 327
  Title: MuSig2 for BIP340-compatible Multi-Signatures
  Authors: Jonas Nick 
           Tim Ruffing 
           Elliott Jin 
  Status: Deployed
  Type: Informational
  Assigned: 2022-03-22
  License: BSD-3-Clause
  Discussion: 2022-04-05: https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2022-April/020198.html [bitcoin-dev] MuSig2 BIP
              2022-10-11: https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2022-October/021000.html [bitcoin-dev] MuSig2 BIP
  Version: 1.0.3
== Introduction == === Abstract === This document proposes a standard for the [https://eprint.iacr.org/2020/1261.pdf MuSig2] multi-signature scheme. The standard is compatible with [https://github.com/bitcoin/bips/blob/master/bip-0340.mediawiki BIP340] public keys and signatures. It supports ''tweaking'', which allows deriving [https://github.com/bitcoin/bips/blob/master/bip-0032.mediawiki BIP32] child keys from aggregate public keys and creating [https://github.com/bitcoin/bips/blob/master/bip-0341.mediawiki BIP341] Taproot outputs with key and script paths. === Copyright === This document is licensed under the 3-clause BSD license. === Motivation === MuSig2 is a multi-signature scheme that allows multiple signers to create a single aggregate public key and cooperatively create ordinary Schnorr signatures valid under the aggregate public key. Signing requires interaction between ''all'' signers involved in key aggregation. (MuSig2 is a ''n-of-n'' multi-signature scheme and not a ''t-of-n'' threshold-signature scheme.) The primary motivation is to create a standard that allows users of different software projects to jointly control Taproot outputs ([https://github.com/bitcoin/bips/blob/master/bip-0341.mediawiki BIP341]). Such an output contains a public key which, in this case, would be the aggregate of all users' individual public keys. It can be spent using MuSig2 to produce a signature for the key-based spending path. The on-chain footprint of a MuSig2 Taproot output is essentially a single BIP340 public key, and a transaction spending the output only requires a single signature cooperatively produced by all signers. This is '''more compact''' and has '''lower verification cost''' than each signer providing an individual public key and signature, as would be required by an ''n-of-n'' policy implemented using OP_CHECKSIGADD as introduced in ([https://github.com/bitcoin/bips/blob/master/bip-0342.mediawiki BIP342]). As a side effect, the number ''n'' of signers is not limited by any consensus rules when using MuSig2. Moreover, MuSig2 offers a '''higher level of privacy''' than OP_CHECKSIGADD: MuSig2 Taproot outputs are indistinguishable for a blockchain observer from regular, single-signer Taproot outputs even though they are actually controlled by multiple signers. By tweaking an aggregate public key, the shared Taproot output can have script spending paths that are hidden unless used. There are multi-signature schemes other than MuSig2 that are fully compatible with Schnorr signatures. The MuSig2 variant proposed below stands out by combining all the following features: * '''Simple Key Setup''': Key aggregation is non-interactive and fully compatible with BIP340 public keys. * '''Two Communication Rounds''': MuSig2 is faster in practice than previous three-round multi-signature schemes such as [https://eprint.iacr.org/2018/068.pdf MuSig1], particularly when signers are connected through high-latency anonymous links. Moreover, the need for fewer communication rounds simplifies the algorithms and reduces the probability that implementations and users make security-relevant mistakes. * '''Provable security''': MuSig2 has been [https://eprint.iacr.org/2020/1261.pdf proven existentially unforgeable] under the algebraic one-more discrete logarithm (AOMDL) assumption (instead of the discrete logarithm assumption required for single-signer Schnorr signatures). AOMDL is a falsifiable and weaker variant of the well-studied OMDL problem. * '''Low complexity''': MuSig2 has a substantially lower computational and implementation complexity than alternative schemes like [https://eprint.iacr.org/2020/1057 MuSig-DN]. However, this comes at the cost of having no ability to generate nonces deterministically and the requirement to securely handle signing state. === Design === * '''Compatibility with BIP340''': In this proposal, the aggregate public key is a BIP340 X-only public key, and the signature output at the end of the signing protocol is a BIP340 signature that passes BIP340 verification for the aggregate public key and a message. The individual public keys that are input to the key aggregation algorithm are ''plain'' public keys in compressed format. * '''Tweaking for BIP32 derivations and Taproot''': This proposal supports tweaking aggregate public keys and signing for tweaked aggregate public keys. We distinguish two modes of tweaking: ''Plain'' tweaking can be used to derive child aggregate public keys per [https://github.com/bitcoin/bips/blob/master/bip-0032.mediawiki BIP32]. ''X-only'' tweaking, on the other hand, allows creating a [https://github.com/bitcoin/bips/blob/master/bip-0341.mediawiki BIP341] tweak to add script paths to a Taproot output. See [[#tweaking-the-aggregate-public-key|below]] for details. * '''Non-interactive signing with preprocessing''': The first communication round, exchanging the nonces, can happen before the message or the exact set of signers is determined. Once the parameters of the signing session are finalized, the signers can send partial signatures without additional interaction. * '''Key aggregation optionally independent of order''': The output of the key aggregation algorithm depends on the order in which the individual public keys are provided as input. Key aggregation does not sort the individual public keys by default because applications often already have a canonical order of signers. Nonetheless, applications can mandate sorting before aggregation,Applications that sort individual public keys before aggregation should ensure that the implementation of sorting is reasonably efficient, and in particular does not degenerate to quadratic runtime on pathological inputs. and this proposal specifies a canonical order to sort the individual public keys before key aggregation. Sorting will ensure the same output, independent of the initial order. * '''Third-party nonce and partial signature aggregation''': Instead of every signer sending their nonce and partial signature to every other signer, it is possible to use an untrusted third-party ''aggregator'' in order to reduce the communication complexity from quadratic to linear in the number of signers. In each of the two rounds, the aggregator collects all signers' contributions (nonces or partial signatures), aggregates them, and broadcasts the aggregate back to the signers. A malicious aggregator can force the signing session to fail to produce a valid Schnorr signature but cannot negatively affect the unforgeability of the scheme. * '''Partial signature verification''': If any signer sends a partial signature contribution that was not created by honestly following the signing protocol, the signing session will fail to produce a valid Schnorr signature. This proposal specifies a partial signature verification algorithm to identify disruptive signers. It is incompatible with third-party nonce aggregation because the individual nonce is required for partial verification. * '''MuSig2* optimization''': This proposal uses an optimized scheme MuSig2*, which allows saving a point multiplication in key aggregation as compared to MuSig2. MuSig2* is proven secure in the appendix of the [https://eprint.iacr.org/2020/1261 MuSig2 paper]. The optimization consists of assigning the constant key aggregation coefficient ''1'' to the second distinct key in the list of individual public keys to be aggregated (as well as to any key identical to this key). * '''Size of the nonce and security''': In this proposal, each signer's nonce consists of two elliptic curve points. The [https://eprint.iacr.org/2020/1261 MuSig2 paper] gives distinct security proofs depending on the number of points that constitute a nonce. See section [[#choosing-the-size-of-the-nonce|Choosing the Size of the Nonce]] for a discussion. == Overview == Implementers must make sure to understand this section thoroughly to avoid subtle mistakes that may lead to catastrophic failure. === Optionality of Features === The goal of this proposal is to support a wide range of possible application scenarios. Given a specific application scenario, some features may be unnecessary or not desirable, and implementers can choose not to support them. Such optional features include: * Applying plain tweaks after x-only tweaks. * Applying tweaks at all. * Dealing with messages that are not exactly 32 bytes. * Identifying a disruptive signer after aborting (aborting itself remains mandatory). * Dealing with duplicate individual public keys in key aggregation. If applicable, the corresponding algorithms should simply fail when encountering inputs unsupported by a particular implementation. (For example, the signing algorithm may fail when given a message which is not 32 bytes.) Similarly, the test vectors that exercise the unimplemented features should be re-interpreted to expect an error, or be skipped if appropriate. === General Signing Flow === The signers start by exchanging their individual public keys and computing an aggregate public key using the ''KeyAgg'' algorithm. Whenever they want to sign a message, the basic order of operations to create a multi-signature is as follows: '''First broadcast round:''' The signers start the signing session by running ''NonceGen'' to compute ''secnonce'' and ''pubnonce''.We treat the ''secnonce'' and ''pubnonce'' as grammatically singular even though they include serializations of two scalars and two elliptic curve points, respectively. This treatment may be confusing for readers familiar with the MuSig2 paper. However, serialization is a technical detail that is irrelevant for users of MuSig2 interfaces. Then, the signers broadcast their ''pubnonce'' to each other and run ''NonceAgg'' to compute an aggregate nonce. '''Second broadcast round:''' At this point, every signer has the required data to sign, which, in the algorithms specified below, is stored in a data structure called [[#session-context|Session Context]]. Every signer computes a partial signature by running ''Sign'' with the secret signing key, the ''secnonce'' and the session context. Then, the signers broadcast their partial signatures to each other and run ''PartialSigAgg'' to obtain the final signature. If all signers behaved honestly, the result passes [https://github.com/bitcoin/bips/blob/master/bip-0340.mediawiki BIP340] verification. Both broadcast rounds can be optimized by using an aggregator who collects all signers' nonces or partial signatures, aggregates them using ''NonceAgg'' or ''PartialSigAgg'', respectively, and broadcasts the aggregate result back to the signers. A malicious aggregator can force the signing session to fail to produce a valid Schnorr signature but cannot negatively affect the unforgeability of the scheme, i.e., even a malicious aggregator colluding with all but one signer cannot forge a signature. '''IMPORTANT''': The ''Sign'' algorithm must '''not''' be executed twice with the same ''secnonce''. Otherwise, it is possible to extract the secret signing key from the two partial signatures output by the two executions of ''Sign''. To avoid accidental reuse of ''secnonce'', an implementation may securely erase the ''secnonce'' argument by overwriting it with 64 zero bytes after it has been read by ''Sign''. A ''secnonce'' consisting of only zero bytes is invalid for ''Sign'' and will cause it to fail. To simplify the specification of the algorithms, some intermediary values are unnecessarily recomputed from scratch, e.g., when executing ''GetSessionValues'' multiple times. Actual implementations can cache these values. As a result, the [[#session-context|Session Context]] may look very different in implementations or may not exist at all. However, computation of ''GetSessionValues'' and storage of the result must be protected against modification from an untrusted third party. This party would have complete control over the aggregate public key and message to be signed. === Public Key Aggregation === We distinguish between two public key types, namely ''plain public keys'', the key type traditionally used in Bitcoin, and ''X-only public keys''. Plain public keys are byte strings of length 33 (often called ''compressed'' format). In contrast, X-only public keys are 32-byte strings defined in [https://github.com/bitcoin/bips/blob/master/bip-0340.mediawiki BIP340]. The individual public keys of signers as input to the key aggregation algorithm ''KeyAgg'' (and to ''GetSessionValues'' and ''PartialSigVerify'') are plain public keys. The output of ''KeyAgg'' is a [[#keyagg-context|KeyAgg Context]] which stores information required for tweaking the aggregate public key (see [[#tweaking-the-aggregate-public-key|below]]), and it can be used to produce an X-only aggregate public key, or a plain aggregate public key. In order to obtain an X-only public key compatible with BIP340 verification, implementations call the ''GetXonlyPubkey'' function with the KeyAgg Context. To get the plain aggregate public key, which is required for some applications of [[#tweaking-the-aggregate-public-key|tweaking]], implementations call ''GetPlainPubkey'' instead. The aggregate public key produced by ''KeyAgg'' (regardless of the type) depends on the order of the individual public keys. If the application does not have a canonical order of the signers, the individual public keys can be sorted with the ''KeySort'' algorithm to ensure that the aggregate public key is independent of the order of signers. The same individual public key is allowed to occur more than once in the input of ''KeyAgg'' and ''KeySort''. This is by design: All algorithms in this proposal handle multiple signers who (claim to) have identical individual public keys properly, and applications are not required to check for duplicate individual public keys. In fact, applications are recommended to omit checks for duplicate individual public keys in order to simplify error handling. Moreover, it is often impossible to tell at key aggregation which signer is to blame for the duplicate, i.e., which signer came up with an individual public key honestly and which disruptive signer copied it. In contrast, MuSig2 is designed to identify disruptive signers at signing time (see [[#identifying-disruptive-signers|Identifying Disruptive Signers]]). While the algorithms in this proposal are able to handle duplicate individual public keys, there are scenarios where applications may choose to abort when encountering duplicates. For example, we can imagine a scenario where a single entity creates a MuSig2 setup with multiple signing devices. In that case, duplicates may not result from a malicious signing device copying an individual public key of another signing device but from accidental initialization of two devices with the same seed. Since MuSig2 key aggregation would accept the duplicate keys and not error out, which would in turn reduce the security compared to the intended key setup, applications may reject duplicate individual public keys before passing them to MuSig2 key aggregation and ask the user to investigate. === Nonce Generation === '''IMPORTANT''': ''NonceGen'' must have access to a high-quality random generator to draw an unbiased, uniformly random value ''rand' ''. In contrast to BIP340 signing, the values ''k1'' and ''k2'' '''must not be derived deterministically''' from the session parameters because otherwise active adversaries can [https://medium.com/blockstream/musig-dn-schnorr-multisignatures-with-verifiably-deterministic-nonces-27424b5df9d6#e3b6 trick the victim into reusing a nonce]. The optional arguments to ''NonceGen'' enable a defense-in-depth mechanism that may prevent secret key exposure if ''rand' '' is accidentally not drawn uniformly at random. If the value ''rand' '' was identical in two ''NonceGen'' invocations, but any other argument was different, the ''secnonce'' would still be guaranteed to be different as well (with overwhelming probability), and thus accidentally using the same ''secnonce'' for ''Sign'' in both sessions would be avoided. Therefore, it is recommended to provide the optional arguments ''sk'', ''aggpk'', and ''m'' if these session parameters are already determined during nonce generation. The auxiliary input ''extra_in'' can contain additional contextual data that has a chance of changing between ''NonceGen'' runs, e.g., a supposedly unique session id (taken from the application), a session counter wide enough not to repeat in practice, any nonces by other signers (if already known), or the serialization of a data structure containing multiple of the above. However, the protection provided by the optional arguments should only be viewed as a last resort. In most conceivable scenarios, the assumption that the arguments are different between two executions of ''NonceGen'' is relatively strong, particularly when facing an active adversary. In some applications, it is beneficial to generate and send a ''pubnonce'' before the other signers, their individual public keys, or the message to sign is known. In this case, only the available arguments are provided to the ''NonceGen'' algorithm. After this preprocessing phase, the ''Sign'' algorithm can be run immediately when the message and set of signers is determined. This way, the final signature is created quicker and with fewer round trips. However, applications that use this method presumably store the nonces for a longer time and must therefore be even more careful not to reuse them. Moreover, this method is not compatible with the defense-in-depth mechanism described in the previous paragraph. Instead of every signer broadcasting their ''pubnonce'' to every other signer, the signers can send their ''pubnonce'' to a single aggregator node that runs ''NonceAgg'' and sends the ''aggnonce'' back to the signers. This technique reduces the overall communication. A malicious aggregator can force the signing session to fail to produce a valid Schnorr signature but cannot negatively affect the unforgeability of the scheme. In general, MuSig2 signers are stateful in the sense that they first generate ''secnonce'' and then need to store it until they receive the other signers' ''pubnonces'' or the ''aggnonce''. However, it is possible for one of the signers to be stateless. This signer waits until it receives the ''pubnonce'' of all the other signers and until session parameters such as a message to sign, individual public keys, and tweaks are determined. Then, the signer can run ''NonceGen'', ''NonceAgg'' and ''Sign'' in sequence and send out its ''pubnonce'' along with its partial signature. Stateless signers may want to consider signing deterministically (see [[#modifications-to-nonce-generation|Modifications to Nonce Generation]]) to remove the reliance on the random number generator in the ''NonceGen'' algorithm. === Identifying Disruptive Signers === The signing protocol makes it possible to identify malicious signers who send invalid contributions to a signing session in order to make the signing session abort and prevent the honest signers from obtaining a valid signature. This property is called "identifiable aborts" and ensures that honest parties can assign blame to malicious signers who cause an abort in the signing protocol. Aborts are identifiable for an honest party if the following conditions hold in a signing session: * The contributions received from all signers have not been tampered with (e.g., because they were sent over authenticated connections). * Nonce aggregation is performed honestly (e.g., because the honest signer performs nonce aggregation on its own or because the aggregator is trusted). * The partial signatures received from all signers are verified using the algorithm ''PartialSigVerify''. If these conditions hold and an honest party (signer or aggregator) runs an algorithm that fails due to invalid protocol contributions from malicious signers, then the algorithm run by the honest party will output the index of exactly one malicious signer. Additionally, if the honest parties agree on the contributions sent by all signers in the signing session, all the honest parties who run the aborting algorithm will identify the same malicious signer. ==== Further Remarks ==== Some of the algorithms specified below may also assign blame to a malicious aggregator. While this is possible for some particular misbehavior of the aggregator, it is not guaranteed that a malicious aggregator can be identified. More specifically, a malicious aggregator (whose existence violates the second condition above) can always make signing abort and wrongly hold honest signers accountable for the abort (e.g., by claiming to have received an invalid contribution from a particular honest signer). The only purpose of the algorithm ''PartialSigVerify'' is to ensure identifiable aborts, and it is not necessary to use it when identifiable aborts are not desired. In particular, partial signatures are ''not'' signatures. An adversary can forge a partial signature, i.e., create a partial signature without knowing the secret key for the claimed individual public key.Assume an adversary wants to forge a partial signature for individual public key ''P''. It joins the signing session pretending to be two different signers, one with individual public key ''P'' and one with another individual public key. The adversary can then set the second signer's nonce such that it will be able to produce a partial signature for ''P'' but not for the other claimed signer. An explanation of the individual steps required to create a partial signature forgery can be found in [https://gist.github.com/AdamISZ/ca974ed67889cedc738c4a1f65ff620b a write up by Adam Gibson]. However, if ''PartialSigVerify'' succeeds for all partial signatures then ''PartialSigAgg'' will return a valid Schnorr signature.Given a list of individual public keys, it is an open question whether a BIP-340 signature valid under the corresponding aggregate public key is a proof of knowledge of all secret keys of the individual public keys. === Tweaking the Aggregate Public Key === The aggregate public key can be ''tweaked'', which modifies the key as defined in the [[#tweaking-definition|Tweaking Definition]] subsection. In order to apply a tweak, the KeyAgg Context output by ''KeyAgg'' is provided to the ''ApplyTweak'' algorithm with the ''is_xonly_t'' argument set to false for plain tweaking and true for X-only tweaking. The resulting KeyAgg Context can be used to apply another tweak with ''ApplyTweak'' or obtain the aggregate public key with ''GetXonlyPubkey'' or ''GetPlainPubkey''. The purpose of supporting tweaking is to ensure compatibility with existing uses of tweaking, i.e., that the result of signing is a valid signature for the tweaked public key. The MuSig2 algorithms take arbitrary tweaks as input but accepting arbitrary tweaks may negatively affect the security of the scheme.It is an open question whether allowing arbitrary tweaks from an adversary affects the unforgeability of MuSig2. Instead, signers should obtain the tweaks according to other specifications. This typically involves deriving the tweaks from a hash of the aggregate public key and some other information. Depending on the specific scheme that is used for tweaking, either the plain or the X-only aggregate public key is required. For example, to do [https://github.com/bitcoin/bips/blob/master/bip-0032.mediawiki BIP32] derivation, you call ''GetPlainPubkey'' to be able to compute the tweak, whereas [https://github.com/bitcoin/bips/blob/master/bip-0341.mediawiki BIP341] TapTweaks require X-only public keys that are obtained with ''GetXonlyPubkey''. The tweak mode provided to ''ApplyTweak'' depends on the application: Plain tweaking can be used to derive child public keys from an aggregate public key using [https://github.com/bitcoin/bips/blob/master/bip-0032.mediawiki BIP32]. On the other hand, X-only tweaking is required for Taproot tweaking per [https://github.com/bitcoin/bips/blob/master/bip-0341.mediawiki BIP341]. A Taproot-tweaked public key commits to a ''script path'', allowing users to create transaction outputs that are spendable either with a MuSig2 multi-signature or by providing inputs that satisfy the script path. Script path spends require a control block that contains a parity bit for the tweaked X-only public key. The bit can be obtained with ''GetPlainPubkey(keyagg_ctx)[0] & 1''. == Algorithms == The following specification of the algorithms has been written with a focus on clarity. As a result, the specified algorithms are not always optimal in terms of computation and space. In particular, some values are recomputed but can be cached in actual implementations (see [[#general-signing-flow|General Signing Flow]]). === Notation === The following conventions are used, with constants as defined for [https://www.secg.org/sec2-v2.pdf secp256k1]. We note that adapting this proposal to other elliptic curves is not straightforward and can result in an insecure scheme. * Lowercase variables represent integers or byte arrays. ** The constant ''p'' refers to the field size, ''0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEFFFFFC2F''. ** The constant ''n'' refers to the curve order, ''0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141''. * Uppercase variables refer to points on the curve with equation ''y2 = x3 + 7'' over the integers modulo ''p''. ** ''is_infinite(P)'' returns whether ''P'' is the point at infinity. ** ''x(P)'' and ''y(P)'' are integers in the range ''0..p-1'' and refer to the X and Y coordinates of a point ''P'' (assuming it is not infinity). ** The constant ''G'' refers to the base point, for which ''x(G) = 0x79BE667EF9DCBBAC55A06295CE870B07029BFCDB2DCE28D959F2815B16F81798'' and ''y(G) = 0x483ADA7726A3C4655DA4FBFC0E1108A8FD17B448A68554199C47D08FFB10D4B8''. ** Addition of points refers to the usual [https://en.wikipedia.org/wiki/Elliptic_curve#The_group_law elliptic curve group operation]. ** [https://en.wikipedia.org/wiki/Elliptic_curve_point_multiplication Multiplication (⋅) of an integer and a point] refers to the repeated application of the group operation. * Functions and operations: ** ''||'' refers to byte array concatenation. ** The function ''x[i:j]'', where ''x'' is a byte array and ''i, j ≥ 0'', returns a ''(j - i)''-byte array with a copy of the ''i''-th byte (inclusive) to the ''j''-th byte (exclusive) of ''x''. ** The function ''bytes(n, x)'', where ''x'' is an integer, returns the n-byte encoding of ''x'', most significant byte first. ** The constant ''empty_bytestring'' refers to the empty byte array. It holds that ''len(empty_bytestring) = 0''. ** The function ''xbytes(P)'', where ''P'' is a point for which ''not is_infinite(P)'', returns ''bytes(32, x(P))''. ** The function ''len(x)'' where ''x'' is a byte array returns the length of the array. ** The function ''has_even_y(P)'', where ''P'' is a point for which ''not is_infinite(P)'', returns ''y(P) mod 2 == 0''. ** The function ''with_even_y(P)'', where ''P'' is a point, returns ''P'' if ''is_infinite(P)'' or ''has_even_y(P)''. Otherwise, ''with_even_y(P)'' returns ''-P''. ** The function ''cbytes(P)'', where ''P'' is a point for which ''not is_infinite(P)'', returns ''a || xbytes(P)'' where ''a'' is a byte that is ''2'' if ''has_even_y(P)'' and ''3'' otherwise. ** The function ''cbytes_ext(P)'', where ''P'' is a point, returns ''bytes(33, 0)'' if ''is_infinite(P)''. Otherwise, it returns ''cbytes(P)''. ** The function ''int(x)'', where ''x'' is a 32-byte array, returns the 256-bit unsigned integer whose most significant byte first encoding is ''x''. ** The function ''lift_x(x)'', where ''x'' is an integer in range ''0..2256-1'', returns the point ''P'' for which ''x(P) = x'' Given a candidate X coordinate ''x'' in the range ''0..p-1'', there exist either exactly two or exactly zero valid Y coordinates. If no valid Y coordinate exists, then ''x'' is not a valid X coordinate either, i.e., no point ''P'' exists for which ''x(P) = x''. The valid Y coordinates for a given candidate ''x'' are the square roots of ''c = x3 + 7 mod p'' and they can be computed as ''y = ±c(p+1)/4 mod p'' (see [https://en.wikipedia.org/wiki/Quadratic_residue#Prime_or_prime_power_modulus Quadratic residue]) if they exist, which can be checked by squaring and comparing with ''c''. and ''has_even_y(P)'', or fails if ''x'' is greater than ''p-1'' or no such point exists. The function ''lift_x(x)'' is equivalent to the following pseudocode: *** Fail if ''x > p-1''. *** Let ''c = x3 + 7 mod p''. *** Let ''y' = c(p+1)/4 mod p''. *** Fail if ''c ≠ y'2 mod p''. *** Let ''y = y' '' if ''y' mod 2 = 0'', otherwise let ''y = p - y' ''. *** Return the unique point ''P'' such that ''x(P) = x'' and ''y(P) = y''. ** The function ''cpoint(x)'', where ''x'' is a 33-byte array (compressed serialization), sets ''P = lift_x(int(x[1:33]))'' and fails if that fails. If ''x[0] = 2'' it returns ''P'' and if ''x[0] = 3'' it returns ''-P''. Otherwise, it fails. ** The function ''cpoint_ext(x)'', where ''x'' is a 33-byte array (compressed serialization), returns the point at infinity if ''x = bytes(33, 0)''. Otherwise, it returns ''cpoint(x)'' and fails if that fails. ** The function ''hashtag(x)'' where ''tag'' is a UTF-8 encoded tag name and ''x'' is a byte array returns the 32-byte hash ''SHA256(SHA256(tag) || SHA256(tag) || x)''. * Other: ** Tuples are written by listing the elements within parentheses and separated by commas. For example, ''(2, 3, 1)'' is a tuple. === Key Generation and Aggregation === ==== Key Generation of an Individual Signer ====
Algorithm ''IndividualPubkey(sk)'':The ''IndividualPubkey'' algorithm matches the key generation procedure traditionally used for ECDSA in Bitcoin * Inputs: ** The secret key ''sk'': a 32-byte array, freshly generated uniformly at random * Let ''d' = int(sk)''. * Fail if ''d' = 0'' or ''d' ≥ n''. * Return ''cbytes(d'⋅G)''.
==== KeyAgg Context ==== The KeyAgg Context is a data structure consisting of the following elements: * The point ''Q'' representing the potentially tweaked aggregate public key: an elliptic curve point * The accumulated tweak ''tacc'': an integer with ''0 ≤ tacc < n'' * The value ''gacc'' : 1 or -1 mod n We write "Let ''(Q, gacc, tacc) = keyagg_ctx''" to assign names to the elements of a KeyAgg Context.
Algorithm ''GetXonlyPubkey(keyagg_ctx)'': * Let ''(Q, _, _) = keyagg_ctx'' * Return ''xbytes(Q)''
Algorithm ''GetPlainPubkey(keyagg_ctx)'': * Let ''(Q, _, _) = keyagg_ctx'' * Return ''cbytes(Q)''
==== Key Sorting ====
Algorithm ''KeySort(pk1..u)'': * Inputs: ** The number ''u'' of individual public keys with ''0 < u < 2^32'' ** The individual public keys ''pk1..u'': ''u'' 33-byte arrays * Return ''pk1..u'' sorted in lexicographical order.
==== Key Aggregation ====
Algorithm ''KeyAgg(pk1..u)'': * Inputs: ** The number ''u'' of individual public keys with ''0 < u < 2^32'' ** The individual public keys ''pk1..u'': ''u'' 33-byte arrays * Let ''pk2 = GetSecondKey(pk1..u)'' * For ''i = 1 .. u'': ** Let ''Pi = cpoint(pki)''; fail if that fails and blame signer ''i'' for invalid individual public key. ** Let ''ai = KeyAggCoeffInternal(pk1..u, pki, pk2)''. * Let ''Q = a1⋅P1 + a2⋅P2 + ... + au⋅Pu'' * Fail if ''is_infinite(Q)''. * Let ''gacc = 1'' * Let ''tacc = 0'' * Return ''keyagg_ctx = (Q, gacc, tacc)''.
Internal Algorithm ''HashKeys(pk1..u)'': * Return ''hashKeyAgg list(pk1 || pk2 || ... || pku)''
Internal Algorithm ''GetSecondKey(pk1..u)'': * For ''j = 1 .. u'': ** If ''pkj ≠ pk1'': *** Return ''pkj'' * Return ''bytes(33, 0)''
Internal Algorithm ''KeyAggCoeff(pk1..u, pk')'': * Let ''pk2 = GetSecondKey(pk1..u)'': * Return ''KeyAggCoeffInternal(pk1..u, pk', pk2)''
Internal Algorithm ''KeyAggCoeffInternal(pk1..u, pk', pk2)'': * Let ''L = HashKeys(pk1..u)'' * If ''pk' = pk2'': ** Return 1 * Return ''int(hashKeyAgg coefficient(L || pk')) mod n''The key aggregation coefficient is computed by hashing the individual public key instead of its index, which requires one more invocation of the SHA-256 compression function. However, it results in significantly simpler implementations because signers do not need to translate between public key indices before and after sorting.
==== Applying Tweaks ====
Algorithm ''ApplyTweak(keyagg_ctx, tweak, is_xonly_t)'': * Inputs: ** The ''keyagg_ctx'': a [[#keyagg-context|KeyAgg Context]] data structure ** The ''tweak'': a 32-byte array ** The tweak mode ''is_xonly_t'': a boolean * Let ''(Q, gacc, tacc) = keyagg_ctx'' * If ''is_xonly_t'' and ''not has_even_y(Q)'': ** Let ''g = -1 mod n'' * Else: ** Let ''g = 1'' * Let ''t = int(tweak)''; fail if ''t ≥ n'' * Let ''Q' = g⋅Q + t⋅G'' ** Fail if ''is_infinite(Q')'' * Let ''gacc' = g⋅gacc mod n'' * Let ''tacc' = t + g⋅tacc mod n'' * Return ''keyagg_ctx' = (Q', gacc', tacc')''
=== Nonce Generation ===
Algorithm ''NonceGen(sk, pk, aggpk, m, extra_in)'': * Inputs: ** The secret signing key ''sk'': a 32-byte array (optional argument) ** The individual public key ''pk'': a 33-byte array (see [[#signing-with-tweaked-individual-keys|Signing with Tweaked Individual Keys]] for the reason that this argument is mandatory) ** The x-only aggregate public key ''aggpk'': a 32-byte array (optional argument) ** The message ''m'': a byte array (optional argument)In theory, the allowed message size is restricted because SHA256 accepts byte strings only up to size of 2^61-1 bytes (and because of the 8-byte length encoding). ** The auxiliary input ''extra_in'': a byte array with ''0 ≤ len(extra_in) ≤ 232-1'' (optional argument) * Let ''rand' '' be a 32-byte array freshly drawn uniformly at random * If the optional argument ''sk'' is present: ** Let ''rand'' be the byte-wise xor of ''sk'' and ''hashMuSig/aux(rand')''The random data is hashed (with a unique tag) as a precaution against situations where the randomness may be correlated with the secret signing key itself. It is xored with the secret key (rather than combined with it in a hash) to reduce the number of operations exposed to the actual secret key. * Else: ** Let ''rand = rand' '' * If the optional argument ''aggpk'' is not present: ** Let ''aggpk = empty_bytestring'' * If the optional argument ''m'' is not present: ** Let ''m_prefixed = bytes(1, 0)'' * Else: ** Let ''m_prefixed = bytes(1, 1) || bytes(8, len(m)) || m'' * If the optional argument ''extra_in'' is not present: ** Let ''extra_in = empty_bytestring'' * Let ''ki = int(hashMuSig/nonce(rand || bytes(1, len(pk)) || pk || bytes(1, len(aggpk)) || aggpk || m_prefixed || bytes(4, len(extra_in)) || extra_in || bytes(1, i - 1))) mod n'' for ''i = 1,2'' * Fail if ''k1 = 0'' or ''k2 = 0'' * Let ''R⁎,1 = k1⋅G, R⁎,2 = k2⋅G'' * Let ''pubnonce = cbytes(R⁎,1) || cbytes(R⁎,2)'' * Let ''secnonce = bytes(32, k1) || bytes(32, k2) || pk''The algorithms as specified here assume that the ''secnonce'' is stored as a 97-byte array using the serialization ''secnonce = bytes(32, k1) || bytes(32, k2) || pk''. The same format is used in the reference implementation and in the test vectors. However, since the ''secnonce'' is (obviously) not meant to be sent over the wire, compatibility between implementations is not a concern, and this method of storing the ''secnonce'' is merely a suggestion.
The ''secnonce'' is effectively a local data structure of the signer which comprises the value triple ''(k1, k2, pk)'', and implementations may choose any suitable method to carry it from ''NonceGen'' (first communication round) to ''Sign'' (second communication round). In particular, implementations may choose to hide the ''secnonce'' in internal state without exposing it in an API explicitly, e.g., in an effort to prevent callers from reusing a ''secnonce'' accidentally.
* Return ''(secnonce, pubnonce)''
=== Nonce Aggregation ===
Algorithm ''NonceAgg(pubnonce1..u)'': * Inputs: ** The number ''u'' of ''pubnonces'' with ''0 < u < 2^32'' ** The public nonces ''pubnonce1..u'': ''u'' 66-byte arrays * For ''j = 1 .. 2'': ** For ''i = 1 .. u'': *** Let ''Ri,j = cpoint(pubnoncei[(j-1)*33:j*33])''; fail if that fails and blame signer ''i'' for invalid ''pubnonce''. ** Let ''Rj = R1,j + R2,j + ... + Ru,j'' * Return ''aggnonce = cbytes_ext(R1) || cbytes_ext(R2)''
=== Session Context === The Session Context is a data structure consisting of the following elements: * The aggregate public nonce ''aggnonce'': a 66-byte array * The number ''u'' of individual public keys with ''0 < u < 2^32'' * The individual public keys ''pk1..u'': ''u'' 33-byte arrays * The number ''v'' of tweaks with ''0 ≤ v < 2^32'' * The tweaks ''tweak1..v'': ''v'' 32-byte arrays * The tweak modes ''is_xonly_t1..v'' : ''v'' booleans * The message ''m'': a byte array We write "Let ''(aggnonce, u, pk1..u, v, tweak1..v, is_xonly_t1..v, m) = session_ctx''" to assign names to the elements of a Session Context.
Algorithm ''GetSessionValues(session_ctx)'': * Let ''(aggnonce, u, pk1..u, v, tweak1..v, is_xonly_t1..v, m) = session_ctx'' * Let ''keyagg_ctx0 = KeyAgg(pk1..u)''; fail if that fails * For ''i = 1 .. v'': ** Let ''keyagg_ctxi = ApplyTweak(keyagg_ctxi-1, tweaki, is_xonly_ti)''; fail if that fails * Let ''(Q, gacc, tacc) = keyagg_ctxv'' * Let ''b = int(hashMuSig/noncecoef(aggnonce || xbytes(Q) || m)) mod n'' * Let ''R1 = cpoint_ext(aggnonce[0:33]), R2 = cpoint_ext(aggnonce[33:66])''; fail if that fails and blame nonce aggregator for invalid ''aggnonce''. * Let ''R' = R1 + b⋅R2'' * If ''is_infinite(R'): ** Let final nonce ''R = G'' (see [[#dealing-with-infinity-in-nonce-aggregation|Dealing with Infinity in Nonce Aggregation]]) * Else: ** Let final nonce ''R = R' '' * Let ''e = int(hashBIP0340/challenge(xbytes(R) || xbytes(Q) || m)) mod n'' * Return ''(Q, gacc, tacc, b, R, e)''
Algorithm ''GetSessionKeyAggCoeff(session_ctx, P)'': * Let ''(_, u, pk1..u, _, _, _, _) = session_ctx'' * Let ''pk = cbytes(P)'' * Fail if ''pk'' not in ''pk1..u'' * Return ''KeyAggCoeff(pk1..u, pk)''
=== Signing ===
Algorithm ''Sign(secnonce, sk, session_ctx)'': * Inputs: ** The secret nonce ''secnonce'' that has never been used as input to ''Sign'' before: a 97-byte array ** The secret key ''sk'': a 32-byte array ** The ''session_ctx'': a [[#session-context|Session Context]] data structure * Let ''(Q, gacc, _, b, R, e) = GetSessionValues(session_ctx)''; fail if that fails * Let ''k1' = int(secnonce[0:32]), k2' = int(secnonce[32:64])'' * Fail if ''ki' = 0'' or ''ki' ≥ n'' for ''i = 1..2'' * Let ''k1 = k1', k2 = k2' '' if ''has_even_y(R)'', otherwise let ''k1 = n - k1', k2 = n - k2' '' * Let ''d' = int(sk)'' * Fail if ''d' = 0'' or ''d' ≥ n'' * Let ''P = d'⋅G'' * Let ''pk = cbytes(P)'' * Fail if ''pk ≠ secnonce[64:97]'' * Let ''a = GetSessionKeyAggCoeff(session_ctx, P)''; fail if that failsFailing ''Sign'' when ''GetSessionKeyAggCoeff(session_ctx, P)'' fails is not necessary for unforgeability. It merely indicates to the caller that the scheme is not being used correctly. * Let ''g = 1'' if ''has_even_y(Q)'', otherwise let ''g = -1 mod n'' *
Let ''d = g⋅gacc⋅d' mod n'' (See [[#negation-of-the-secret-key-when-signing|Negation Of The Secret Key When Signing]]) * Let ''s = (k1 + b⋅k2 + e⋅a⋅d) mod n'' * Let ''psig = bytes(32, s)'' * Let ''pubnonce = cbytes(k1'⋅G) || cbytes(k2'⋅G)'' * If ''PartialSigVerifyInternal(psig, pubnonce, pk, session_ctx)'' (see below) returns failure, failVerifying the signature before leaving the signer prevents random or adversarially provoked computation errors. This prevents publishing invalid signatures which may leak information about the secret key. It is recommended but can be omitted if the computation cost is prohibitive. * Return partial signature ''psig''
=== Partial Signature Verification ===
Algorithm ''PartialSigVerify(psig, pubnonce1..u, pk1..u, tweak1..v, is_xonly_t1..v, m, i)'': * Inputs: ** The partial signature ''psig'': a 32-byte array ** The number ''u'' of public nonces and individual public keys with ''0 < u < 2^32'' ** The public nonces ''pubnonce1..u'': ''u'' 66-byte arrays ** The individual public keys ''pk1..u'': ''u'' 33-byte arrays ** The number ''v'' of tweaks with ''0 ≤ v < 2^32'' ** The tweaks ''tweak1..v'': ''v'' 32-byte arrays ** The tweak modes ''is_xonly_t1..v'' : ''v'' booleans ** The message ''m'': a byte array ** The index of the signer ''i'' in the of public nonces and individual public keys with ''0 < i ≤ u'' * Let ''aggnonce = NonceAgg(pubnonce1..u)''; fail if that fails * Let ''session_ctx = (aggnonce, u, pk1..u, v, tweak1..v, is_xonly_t1..v, m)'' * Run ''PartialSigVerifyInternal(psig, pubnoncei, pki, session_ctx)'' * Return success iff no failure occurred before reaching this point.
Internal Algorithm ''PartialSigVerifyInternal(psig, pubnonce, pk, session_ctx)'': * Let ''(Q, gacc, _, b, R, e) = GetSessionValues(session_ctx)''; fail if that fails * Let ''s = int(psig)''; fail if ''s ≥ n'' * Let ''R⁎,1 = cpoint(pubnonce[0:33]), R⁎,2 = cpoint(pubnonce[33:66])'' * Let ''Re' = R⁎,1 + b⋅R⁎,2'' * Let effective nonce ''Re = Re' '' if ''has_even_y(R)'', otherwise let ''Re = -Re' '' * Let ''P = cpoint(pk)''; fail if that fails * Let ''a = GetSessionKeyAggCoeff(session_ctx, P)''''GetSessionKeyAggCoeff(session_ctx, P)'' cannot fail when called from ''PartialSigVerifyInternal''. * Let ''g = 1'' if ''has_even_y(Q)'', otherwise let ''g = -1 mod n'' *
Let ''g' = g⋅gacc mod n'' (See [[#negation-of-the-individual-public-key-when-partially-verifying|Negation Of The Individual Public Key When Partially Verifying]]) * Fail if ''s⋅G ≠ Re + e⋅a⋅g'⋅P'' * Return success iff no failure occurred before reaching this point.
=== Partial Signature Aggregation ===
Algorithm ''PartialSigAgg(psig1..u, session_ctx)'': * Inputs: ** The number ''u'' of signatures with ''0 < u < 2^32'' ** The partial signatures ''psig1..u'': ''u'' 32-byte arrays ** The ''session_ctx'': a [[#session-context|Session Context]] data structure * Let ''(Q, _, tacc, _, _, R, e) = GetSessionValues(session_ctx)''; fail if that fails * For ''i = 1 .. u'': ** Let ''si = int(psigi)''; fail if ''si ≥ n'' and blame signer ''i'' for invalid partial signature. * Let ''g = 1'' if ''has_even_y(Q)'', otherwise let ''g = -1 mod n'' * Let ''s = s1 + ... + su + e⋅g⋅tacc mod n'' * Return ''sig = ''xbytes(R) || bytes(32, s)''
=== Test Vectors and Reference Code === We provide a naive, highly inefficient, and non-constant time [[bip-0327/reference.py|pure Python 3 reference implementation of the key aggregation, partial signing, and partial signature verification algorithms]]. Standalone JSON test vectors are also available in the [[bip-0327|same directory]], to facilitate porting the test vectors into other implementations. The reference implementation is for demonstration purposes only and not to be used in production environments. == Remarks on Security and Correctness == === Signing with Tweaked Individual Keys === The scheme in this proposal has been designed to be secure even if signers tweak their individual secret keys with tweaks known to the adversary (e.g., as in BIP32 unhardened derivation) before providing the corresponding individual public keys as input to key aggregation. In particular, the scheme as specified above requires each signer to provide a final individual public key ''pk'' already to ''NonceGen'', which writes it into the ''secnonce'' array so that it can be checked against ''IndividualPubkey(sk)'' in the ''Sign'' algorithm. The purpose of this check in ''Sign'' is to ensure that ''pk'', and thus the secret key ''sk'' that will be provided to ''Sign'', is determined before the signer sends out the ''pubnonce''. If the check in ''Sign'' was omitted, and a signer supported signing with at least two different secret keys ''sk1'' and ''sk2'' which have been obtained via tweaking another secret key with tweaks known to the adversary, then the adversary could, after having seen the ''pubnonce'', influence whether ''sk1'' or ''sk2'' is provided to ''Sign''. This degree of freedom may allow the adversary to perform a generalized birthday attack and thereby forge a signature (see [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2022-October/021000.html bitcoin-dev mailing list post] and [https://github.com/jonasnick/musig2-tweaking writeup] for details). Checking ''pk'' against ''IndividualPubkey(sk)'' is a simple way to ensure that the secret key provided to ''Sign'' is fully determined already when ''NonceGen'' is invoked. This removes the adversary's ability to influence the secret key after having seen the ''pubnonce'' and thus rules out the attack.Ensuring that the secret key provided to ''Sign'' is fully determined already when ''NonceGen'' is invoked is a simple policy to rule out the attack, but more flexible polices are conceivable. In fact, if the signer uses nothing but the message to be signed and the list of the individual public keys of all signers to decide which secret key to use, then it is not a problem that the adversary can influence this decision after having seen the ''pubnonce''.
More formally, consider modified algorithms ''NonceGen' '' and ''Sign' '', where ''NonceGen' '' does not take the individual public key of the signer as input and does not store it in pubnonce, and Sign' does not check read the individual public key from pubnonce and does not check it against the secret key taken as input. Then it suffices that for each invocation of ''NonceGen' '' with output ''(secnonce, pubnonce)'', a function ''fsk'' is determined before sending out ''pubnonce'', where ''fsk'' maps a pair consisting of a list of individual public keys and a message to a secret key, such that the secret key ''sk'' and the session context ''session_ctx = (_, _, pk1..u, _, _, _, m)'' provided to the corresponding invocation of ''Sign'(secnonce, sk, session_ctx)'', adhere to the condition ''fsk(pk1..u, m) = sk''.
However, this requirement is complex and hard to enforce in implementations. The algorithms ''NonceGen'' and ''Sign'' specified in this BIP are effectively restricted to constant functions ''fsk(_, _) = sk''. In other words, their usage ensure that the secret key ''sk'' of the signers is determined entirely when invoking ''NonceGen'', which is enforced easily by letting ''NonceGen'' take the corresponding individual public key ''pk'' as input and checking ''pk'' against ''IndividualPubKey(sk)'' in ''Sign''.
Note that the scheme as given in the [https://eprint.iacr.org/2020/1261 MuSig2 paper] does not perform the check in ''Sign''. However, the security model in the paper does not cover tweaking at all and assumes a single fixed secret key. === Modifications to Nonce Generation === Implementers must avoid modifying the ''NonceGen'' algorithm without being fully aware of the implications. We provide two modifications to ''NonceGen'' that are secure when applied correctly and may be useful in special circumstances, summarized in the following table. {| class="wikitable" style="margin:auto" ! !! needs secure randomness !! needs secure counter !! needs to keep state securely !! needs aggregate nonce of all other signers (only possible for one signer) |- ! NonceGen || ✓ ||   || ✓ ||   |- ! CounterNonceGen ||   || ✓ || ✓ ||   |- ! DeterministicSign ||   ||   ||   || ✓ |} First, on systems where obtaining uniformly random values is much harder than maintaining a global atomic counter, it can be beneficial to modify ''NonceGen''. The resulting algorithm ''CounterNonceGen'' does not draw ''rand' '' uniformly at random but instead sets ''rand' '' to the value of an atomic counter that is incremented whenever it is read. With this modification, the secret signing key ''sk'' of the signer generating the nonce is '''not''' an optional argument and must be provided to ''NonceGen''. The security of the resulting scheme then depends on the requirement that reading the counter must never yield the same counter value in two ''NonceGen'' invocations with the same ''sk''. Second, if there is a unique signer who is supposed to send the ''pubnonce'' last, it is possible to modify nonce generation for this single signer to not require high-quality randomness. Such a nonce generation algorithm ''DeterministicSign'' is specified below. Note that the only optional argument is ''rand'', which can be omitted if randomness is entirely unavailable. ''DeterministicSign'' requires the argument ''aggothernonce'' which should be set to the output of ''NonceAgg'' run on the ''pubnonce'' value of '''all''' other signers (but can be provided by an untrusted party). Hence, using ''DeterministicSign'' is only possible for the last signer to generate a nonce and makes the signer stateless, similar to the stateless signer described in the [[#nonce-generation|Nonce Generation]] section. ==== Deterministic and Stateless Signing for a Single Signer ====
Algorithm ''DeterministicSign(sk, aggothernonce, pk1..u, tweak1..v, is_xonly_t1..v, m, rand)'': * Inputs: ** The secret signing key ''sk'': a 32-byte array ** The aggregate public nonce ''aggothernonce'' (see [[#modifications-to-nonce-generation|above]]): a 66-byte array ** The number ''u'' of individual public keys with ''0 < u < 2^32'' ** The individual public keys ''pk1..u'': ''u'' 33-byte arrays ** The number ''v'' of tweaks with ''0 ≤ v < 2^32'' ** The tweaks ''tweak1..v'': ''v'' 32-byte arrays ** The tweak methods ''is_xonly_t1..v'': ''v'' booleans ** The message ''m'': a byte array ** The auxiliary randomness ''rand'': a 32-byte array (optional argument) * If the optional argument ''rand'' is present: ** Let ''sk' '' be the byte-wise xor of ''sk'' and ''hashMuSig/aux(rand)'' * Else: ** Let ''sk' = sk'' * Let ''keyagg_ctx0 = KeyAgg(pk1..u)''; fail if that fails * For ''i = 1 .. v'': ** Let ''keyagg_ctxi = ApplyTweak(keyagg_ctxi-1, tweaki, is_xonly_ti)''; fail if that fails * Let ''aggpk = GetXonlyPubkey(keyagg_ctxv)'' * Let ''ki = int(hashMuSig/deterministic/nonce(sk' || aggothernonce || aggpk || bytes(8, len(m)) || m || bytes(1, i - 1))) mod n'' for ''i = 1,2'' * Fail if ''k1 = 0'' or ''k2 = 0'' * Let ''R⁎,1 = k1⋅G, R⁎,2 = k2⋅G'' * Let ''pubnonce = cbytes(R⁎,1) || cbytes(R⁎,2)'' * Let ''d = int(sk)'' * Fail if ''d = 0'' or ''d ≥ n'' * Let ''pk = cbytes(d⋅G)'' * Let ''secnonce = bytes(32, k1) || bytes(32, k2) || pk'' * Let ''aggnonce = NonceAgg((pubnonce, aggothernonce))''; fail if that fails and blame nonce aggregator for invalid ''aggothernonce''. * Let ''session_ctx = (aggnonce, u, pk1..u, v, tweak1..v, is_xonly_t1..v, m)'' * Return ''(pubnonce, Sign(secnonce, sk, session_ctx))''
=== Tweaking Definition === Two modes of tweaking the aggregate public key are supported. They correspond to the following algorithms:
Algorithm ''ApplyPlainTweak(P, t)'': * Inputs: ** ''P'': a point ** The tweak ''t'': an integer with ''0 ≤ t < n '' * Return ''P + t⋅G''
Algorithm ''ApplyXonlyTweak(P, t)'': * Return ''with_even_y(P) + t⋅G''
=== Negation Of The Secret Key When Signing === In order to produce a partial signature for an X-only aggregate public key that is an aggregate of ''u'' individual public keys and tweaked ''v'' times (X-only or plain), the ''[[#Sign negation|Sign]]'' algorithm may need to negate the secret key during the signing process. The following elliptic curve points arise as intermediate steps when creating a signature: • ''Pi'' as computed in ''KeyAgg'' is the point corresponding to the ''i''-th signer's individual public key. Defining ''di' '' to be the ''i''-th signer's secret key as an integer, i.e., the ''d' '' value as computed in the ''Sign'' algorithm of the ''i''-th signer, we have ''Pi = di'⋅G ''. • ''Q0'' is the aggregate of the individual public keys. It is identical to value ''Q'' computed in ''KeyAgg'' and therefore defined as ''Q0 = a1⋅P1 + a2⋅P2 + ... + au⋅Pu''. • ''Qi'' is the tweaked aggregate public key after the ''i''-th execution of ''ApplyTweak'' for ''1 ≤ i ≤ v''. It holds that ''Qi = f(i-1) + ti⋅G'' for ''i = 1, ..., v'' where ''f(i-1) := with_even_y(Qi-1)'' if ''is_xonly_ti'' and ''f(i-1) := Qi-1'' otherwise. • ''with_even_y(Qv)'' is the final result of the key aggregation and tweaking operations. It corresponds to the output of ''GetXonlyPubkey'' applied on the final KeyAgg Context. The signer's goal is to produce a partial signature corresponding to the final result of key aggregation and tweaking, i.e., the X-only public key ''with_even_y(Qv)''. For ''1 ≤ i ≤ v'', we denote the value ''g'' computed in the ''i''-th execution of ''ApplyTweak'' by ''gi-1''. Therefore, ''gi-1'' is ''-1 mod n'' if and only if ''is_xonly_ti'' is true and ''Qi-1'' has an odd Y coordinate. In other words, ''gi-1'' indicates whether ''Qi-1'' needed to be negated to apply an X-only tweak: ''f(i-1) = gi-1⋅Qi-1'' for ''1 ≤ i ≤ v''. Furthermore, the ''Sign'' and ''PartialSigVerify'' algorithms set value ''g'' depending on whether ''Qv'' needed to be negated to produce the (X-only) final output. For consistency, this value ''g'' is referred to as ''gv'' in this section. ''with_even_y(Qv) = gv⋅Qv''. So, the (X-only) final public key is ''with_even_y(Qv) = gv⋅Qv = gv⋅(f(v-1) + tv⋅G) = gv⋅(gv-1⋅(f(v-2) + tv-1⋅G) + tv⋅G) = gv⋅gv-1⋅f(v-2) + gv⋅(tv + gv-1⋅tv-1)⋅G = gv⋅gv-1⋅f(v-2) + (sumi=v-1..v ti⋅prodj=i..v gj)⋅G = gv⋅gv-1⋅...⋅g1⋅f(0) + (sumi=1..v ti⋅prodj=i..v gj)⋅G = gv⋅...⋅g0⋅Q0 + gv⋅taccv⋅G'' where ''tacci'' is computed by ''KeyAgg'' and ''ApplyTweak'' as follows: ''tacc0 = 0 tacci = ti + gi-1⋅tacci-1 for i=1..v mod n'' for which it holds that ''gv⋅taccv = sumi=1..v ti⋅prodj=i..v gj''. ''KeyAgg'' and ''ApplyTweak'' compute ''gacc0 = 1 gacci = gi-1⋅gacci-1 for i=1..v mod n'' So we can rewrite above equation for the final public key as ''with_even_y(Qv) = gv⋅gaccv⋅Q0 + gv⋅taccv⋅G''. Then we have ''with_even_y(Qv) - gv⋅taccv⋅G = gv⋅gaccv⋅Q0 = gv⋅gaccv⋅(a1⋅P1 + ... + au⋅Pu) = gv⋅gaccv⋅(a1⋅d1'⋅G + ... + au⋅du'⋅G) = sumi=1..u(gv⋅gaccv⋅ai⋅di')*G''. Intuitively, ''gacci'' tracks accumulated sign flipping and ''tacci'' tracks the accumulated tweak value after applying the first ''i'' individual tweaks. Additionally, ''gv'' indicates whether ''Qv'' needed to be negated to produce the final X-only result. Thus, signer ''i'' multiplies its secret key ''di' '' with ''gv⋅gaccv'' in the ''[[#Sign negation|Sign]]'' algorithm. ==== Negation Of The Individual Public Key When Partially Verifying ==== As explained in [[#negation-of-the-secret-key-when-signing|Negation Of The Secret Key When Signing]] the signer uses a possibly negated secret key ''d = gv⋅gaccv⋅d' mod n'' when producing a partial signature to ensure that the aggregate signature will correspond to an aggregate public key with even Y coordinate. The ''[[#SigVerify negation|PartialSigVerifyInternal]]'' algorithm is supposed to check ''s⋅G = Re + e⋅a⋅d⋅G''. The verifier doesn't have access to ''d⋅G'' but can construct it using the individual public key ''pk'' as follows: ''d⋅G = gv⋅gaccv⋅d'⋅G = gv⋅gaccv⋅cpoint(pk)'' Note that the aggregate public key and list of tweaks are inputs to partial signature verification, so the verifier can also construct ''gv'' and ''gaccv''. === Dealing with Infinity in Nonce Aggregation === If the nonce aggregator provides ''aggnonce = bytes(33,0) || bytes(33,0)'', either the nonce aggregator is dishonest or there is at least one dishonest signer (except with negligible probability). If signing aborted in this case, it would be impossible to determine who is dishonest. Therefore, signing continues so that the culprit is revealed when collecting and verifying partial signatures. However, the final nonce ''R'' of a BIP340 Schnorr signature cannot be the point at infinity. If we would nonetheless allow the final nonce to be the point at infinity, then the scheme would lose the following property: if ''PartialSigVerify'' succeeds for all partial signatures, then ''PartialSigAgg'' will return a valid Schnorr signature. Since this is a valuable feature, we modify MuSig2* (which is defined in the appendix of the [https://eprint.iacr.org/2020/1261 MuSig2 paper]) to avoid producing an invalid Schnorr signature while still allowing detection of the dishonest signer: In ''GetSessionValues'', if the final nonce ''R'' would be the point at infinity, set it to the generator instead (an arbitrary choice). This modification to ''GetSessionValues'' does not affect the unforgeability of the scheme. Given a successful adversary against the unforgeability game (EUF-CMA) for the modified scheme, a reduction can win the unforgeability game for the original scheme by simulating the modification towards the adversary: When the adversary provides ''aggnonce' = bytes(33, 0) || bytes(33, 0)'', the reduction sets ''aggnonce = cbytes_ext(G) || bytes(33, 0)''. For any other ''aggnonce' '', the reduction sets ''aggnonce = aggnonce' ''. (The case that the adversary provides an ''aggnonce' ≠ bytes(33, 0) || bytes(33, 0) '' but nevertheless ''R' '' in ''GetSessionValues'' is the point at infinity happens only with negligible probability.) === Choosing the Size of the Nonce === The [https://eprint.iacr.org/2020/1261 MuSig2 paper] contains two security proofs that apply to different variants of the scheme. The first proof relies on the random oracle model (ROM) and applies to a scheme variant where each signer's nonce consists of four elliptic curve points. The second proof requires a stronger model, namely the combination of the ROM and the algebraic group model (AGM), and applies to an optimized scheme variant where the signers' nonces consist of only two points. This proposal uses the latter, optimized scheme variant. Relying on the stronger model is a legitimate choice for the following reasons: First, an approach widely taken is interpreting a Forking Lemma proof in the ROM merely as design justification and ignoring the loss of security due to the Forking Lemma. If one believes in this approach, then the ROM may not be the optimal model in the first place because some parts of the concrete security bound are arbitrarily ignored. One may just as well move to the ROM+AGM model, which produces bounds close to the best-known attacks, e.g., for Schnorr signatures. Second, as of this writing, there is no instance of a serious cryptographic scheme with a security proof in the AGM that is not secure in practice. There are, however, insecure toy schemes with AGM security proofs, but those explicitly violate the requirements of the AGM. [https://eprint.iacr.org/2022/226.pdf Broken AGM proofs of toy schemes] provide group elements to the adversary without declaring them as group element inputs. In contrast, in MuSig2, all group elements that arise in the scheme are known to the adversary and declared as group element inputs. A scheme very similar to MuSig2 and with two-point nonces was independently proven secure in the ROM and AGM by [https://eprint.iacr.org/2020/1245 Alper and Burdges]. == Backwards Compatibility == This document proposes a standard for the MuSig2 multi-signature scheme that is compatible with [https://github.com/bitcoin/bips/blob/master/bip-0340.mediawiki BIP340]. MuSig2 is ''not'' compatible with ECDSA signatures traditionally used in Bitcoin. == Changelog == To help implementers understand updates to this document, we attach a version number that resembles ''semantic versioning'' (MAJOR.MINOR.PATCH). The MAJOR version is incremented if changes to the BIP are introduced that are incompatible with prior versions. An exception to this rule is MAJOR version zero (0.y.z) which is for development and does not need to be incremented if backwards incompatible changes are introduced. The MINOR version is incremented whenever the inputs or the output of an algorithm changes in a backward-compatible way or new backward-compatible functionality is added. The PATCH version is incremented for other changes that are noteworthy (bug fixes, test vectors, important clarifications, etc.). * '''1.0.3''' (2026-01-05): ** Fix minor bugs in the specification of ''DeterministicSign''. * '''1.0.2''' (2024-07-22): ** Fix minor bug in the specification of ''DeterministicSign'' and add small improvement to a ''PartialSigAgg'' test vector. * '''1.0.1''' (2024-05-14): ** Fix minor issue in ''PartialSigVerify'' vectors. * '''1.0.0''' (2023-03-26): ** Number 327 was assigned to this BIP. * '''1.0.0-rc.4''' (2023-03-02): ** Add expected value of ''pubnonce'' to ''NonceGen'' test vectors. * '''1.0.0-rc.3''' (2023-02-28): ** Improve ''NonceGen'' test vectors by not using an all-zero hex string as ''rand_'' values. This change addresses potential issues in some implementations that interpret this as a special value indicating uninitialized memory or a broken random number generator and therefore return an error. ** Fix invalid length of a ''pubnonce'' in the ''PartialSigVerify'' test vectors. ** Improve ''KeySort'' test vector. ** Add explicit ''IndividualPubkey'' algorithm. ** Rename KeyGen Context to KeyAgg Context. * '''1.0.0-rc.2''' (2022-10-28): ** Fix vulnerability that can occur in certain unusual scenarios (see [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2022-October/021000.html bitcoin-dev mailing list]: Add mandatory ''pk'' argument to ''NonceGen'', append ''pk'' to ''secnonce'' and check in ''Sign'' that the ''pk'' in ''secnonce'' matches. Update test vectors. ** Make sure that signer's key is in list of individual public keys by adding failure case to ''GetSessionKeyAggCoeff'' and add test vectors. * '''1.0.0-rc.1''' (2022-10-03): Submit draft BIP to the BIPs repository * '''0.8.6''' (2022-09-15): Clarify that implementations do not need to support every feature and add a test vector for signing with a tweaked key * '''0.8.5''' (2022-09-05): Rename some functions to improve clarity. * '''0.8.4''' (2022-09-02): Make naming of nonce variants ''R'' in specifications of the algorithms and reference code easier to read and more consistent. * '''0.8.3''' (2022-09-01): Overwrite ''secnonce'' in ''sign'' reference implementation to help prevent accidental reuse and add test vector for invalid ''secnonce''. * '''0.8.2''' (2022-08-30): Fix ''KeySort'' input length and add test vectors * '''0.8.1''' (2022-08-26): Add ''DeterministicSign'' algorithm * '''0.8.0''' (2022-08-26): Switch from X-only to plain public key for individual public keys. This requires updating a large portion of the test vectors. * '''0.7.2''' (2022-08-17): Add ''NonceGen'' and ''Sign/PartialSigVerify'' test vectors for messages longer than 32 bytes. * '''0.7.1''' (2022-08-10): Extract test vectors into separate JSON file. * '''0.7.0''' (2022-07-31): Change ''NonceGen'' such that output when message is not present is different from when message is present but has length 0. * '''0.6.0''' (2022-07-31): Allow variable length messages, change serialization of the message in the ''NonceGen'' hash function, and add test vectors * '''0.5.2''' (2022-06-26): Fix ''aggpk'' in ''NonceGen'' test vectors. * '''0.5.1''' (2022-06-22): Rename "ordinary" tweaking to "plain" tweaking. * '''0.5.0''' (2022-06-21): Separate ApplyTweak from KeyAgg and introduce KeyGen Context. * '''0.4.0''' (2022-06-20): Allow the output of NonceAgg to be infinity and add test vectors * '''0.3.2''' (2022-06-02): Add a lot of test vectors and improve handling of invalid contributions in reference code. * '''0.3.1''' (2022-05-24): Add ''NonceGen'' test vectors * '''0.3.0''' (2022-05-24): Hash ''i - 1'' instead of ''i'' in ''NonceGen'' * '''0.2.0''' (2022-05-19): Change order of arguments in ''NonceGen'' hash function * '''0.1.0''' (2022-05-19): Publication of draft BIP on the bitcoin-dev mailing list == Footnotes == == Acknowledgements == We thank Brandon Black, Riccardo Casatta, Sivaram Dhakshinamoorthy, Lloyd Fournier, Russell O'Connor, and Pieter Wuille for their contributions to this document. ================================================ FILE: bip-0328/_base58.py ================================================ """ Base 58 conversion utilities **************************** """ # # base58.py # Original source: git://github.com/joric/brutus.git # which was forked from git://github.com/samrushing/caesure.git # # Distributed under the MIT/X11 software license, see the accompanying # file COPYING or http://www.opensource.org/licenses/mit-license.php. # from binascii import hexlify, unhexlify from typing import List from _common import hash256 b58_digits: str = '123456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz' def encode(b: bytes) -> str: """ Encode bytes to a base58-encoded string :param b: Bytes to encode :return: Base58 encoded string of ``b`` """ # Convert big-endian bytes to integer n: int = int('0x0' + hexlify(b).decode('utf8'), 16) # Divide that integer into base58 temp: List[str] = [] while n > 0: n, r = divmod(n, 58) temp.append(b58_digits[r]) res: str = ''.join(temp[::-1]) # Encode leading zeros as base58 zeros czero: int = 0 pad: int = 0 for c in b: if c == czero: pad += 1 else: break return b58_digits[0] * pad + res def decode(s: str) -> bytes: """ Decode a base58-encoding string, returning bytes :param s: Base58 string to decode :return: Bytes encoded by ``s`` """ if not s: return b'' # Convert the string to an integer n: int = 0 for c in s: n *= 58 if c not in b58_digits: raise Exception('Character %r is not a valid base58 character' % c) digit = b58_digits.index(c) n += digit # Convert the integer to bytes h: str = '%x' % n if len(h) % 2: h = '0' + h res = unhexlify(h.encode('utf8')) # Add padding back. pad = 0 for c in s[:-1]: if c == b58_digits[0]: pad += 1 else: break return b'\x00' * pad + res def decode_check(s: str) -> bytes: """ Decode a Base58Check encoded string, returning bytes :param s: Base58 string to decode :return: Bytes encoded by ``s`` """ data = decode(s) payload = data[:-4] checksum = data[-4:] calc_checksum = hash256(payload) if checksum != calc_checksum[:4]: raise ValueError("Invalid checksum") return payload def encode_check(b: bytes) -> str: checksum = hash256(b)[0:4] data = b + checksum return encode(data) def get_xpub_fingerprint(s: str) -> bytes: """ Get the parent fingerprint from an extended public key :param s: The extended pubkey :return: The parent fingerprint bytes """ data = decode(s) fingerprint = data[5:9] return fingerprint def get_xpub_fingerprint_hex(xpub: str) -> str: """ Get the parent fingerprint as a hex string from an extended public key :param xpub: The extended pubkey :return: The parent fingerprint as a hex string """ data = decode(xpub) fingerprint = data[5:9] return hexlify(fingerprint).decode() def to_address(b: bytes, version: bytes) -> str: """ Base58 Check Encode the data with the version number. Used to encode legacy style addresses. :param b: The data to encode :param version: The version number to encode with :return: The Base58 Check Encoded string """ data = version + b checksum = hash256(data)[0:4] data += checksum return encode(data) def xpub_to_pub_hex(xpub: str) -> str: """ Get the public key as a string from the extended public key. :param xpub: The extended pubkey :return: The pubkey hex string """ data = decode(xpub) pubkey = data[-37:-4] return hexlify(pubkey).decode() def xpub_to_xonly_pub_hex(xpub: str) -> str: """ Get the public key as a string from the extended public key. :param xpub: The extended pubkey :return: The pubkey hex string """ data = decode(xpub) pubkey = data[-36:-4] return hexlify(pubkey).decode() def xpub_main_2_test(xpub: str) -> str: """ Convert an extended pubkey from mainnet version to testnet version. :param xpub: The extended pubkey :return: The extended pubkey re-encoded using testnet version bytes """ data = decode(xpub) test_data = b'\x04\x35\x87\xCF' + data[4:-4] checksum = hash256(test_data)[0:4] return encode(test_data + checksum) ================================================ FILE: bip-0328/_common.py ================================================ """ Common Classes and Utilities **************************** """ import hashlib def sha256(s: bytes) -> bytes: """ Perform a single SHA256 hash. :param s: Bytes to hash :return: The hash """ return hashlib.new('sha256', s).digest() def ripemd160(s: bytes) -> bytes: """ Perform a single RIPEMD160 hash. :param s: Bytes to hash :return: The hash """ return hashlib.new('ripemd160', s).digest() def hash256(s: bytes) -> bytes: """ Perform a double SHA256 hash. A SHA256 is performed on the input, and then a second SHA256 is performed on the result of the first SHA256 :param s: Bytes to hash :return: The hash """ return sha256(sha256(s)) def hash160(s: bytes) -> bytes: """ perform a single SHA256 hash followed by a single RIPEMD160 hash on the result of the SHA256 hash. :param s: Bytes to hash :return: The hash """ return ripemd160(sha256(s)) ================================================ FILE: bip-0328/_xpub.py ================================================ #!/usr/bin/env python3 # Copyright (c) 2020 The HWI developers # Distributed under the MIT software license, see the accompanying # file COPYING or http://www.opensource.org/licenses/mit-license.php. """ Key Classes and Utilities ************************* Classes and utilities for working with extended public keys, key origins, and other key related things. """ import _base58 as base58 from _common import ( hash256, hash160, ) import binascii import hmac import hashlib import struct from typing import ( Dict, Optional, Sequence, Tuple, ) HARDENED_FLAG = 1 << 31 p = 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEFFFFFC2F n = 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141 G = (0x79BE667EF9DCBBAC55A06295CE870B07029BFCDB2DCE28D959F2815B16F81798, 0x483ADA7726A3C4655DA4FBFC0E1108A8FD17B448A68554199C47D08FFB10D4B8) Point = Optional[Tuple[int, int]] def H_(x: int) -> int: """ Shortcut function that "hardens" a number in a BIP44 path. """ return x | HARDENED_FLAG def is_hardened(i: int) -> bool: """ Returns whether an index is hardened """ return i & HARDENED_FLAG != 0 def point_add(p1: Point, p2: Point) -> Point: if (p1 is None): return p2 if (p2 is None): return p1 if (p1[0] == p2[0] and p1[1] != p2[1]): return None if (p1 == p2): lam = (3 * p1[0] * p1[0] * pow(2 * p1[1], p - 2, p)) % p else: lam = ((p2[1] - p1[1]) * pow(p2[0] - p1[0], p - 2, p)) % p x3 = (lam * lam - p1[0] - p2[0]) % p return (x3, (lam * (p1[0] - x3) - p1[1]) % p) def point_mul(p: Point, n: int) -> Point: r = None for i in range(256): if ((n >> i) & 1): r = point_add(r, p) p = point_add(p, p) return r def deserialize_point(b: bytes) -> Point: x = int.from_bytes(b[1:], byteorder="big") y = pow((x * x * x + 7) % p, (p + 1) // 4, p) if (y & 1 != b[0] & 1): y = p - y return (x, y) def bytes_to_point(point_bytes: bytes) -> Point: header = point_bytes[0] if header == 4: x = point_bytes[1:33] y = point_bytes[33:65] return (int(binascii.hexlify(x), 16), int(binascii.hexlify(y), 16)) return deserialize_point(point_bytes) def point_to_bytes(p: Point) -> bytes: if p is None: raise ValueError("Cannot convert None to bytes") return (b'\x03' if p[1] & 1 else b'\x02') + p[0].to_bytes(32, byteorder="big") # An extended public key (xpub) or private key (xprv). Just a data container for now. # Only handles deserialization of extended keys into component data to be handled by something else class ExtendedKey(object): """ A BIP 32 extended public key. """ MAINNET_PUBLIC = b'\x04\x88\xB2\x1E' MAINNET_PRIVATE = b'\x04\x88\xAD\xE4' TESTNET_PUBLIC = b'\x04\x35\x87\xCF' TESTNET_PRIVATE = b'\x04\x35\x83\x94' def __init__(self, version: bytes, depth: int, parent_fingerprint: bytes, child_num: int, chaincode: bytes, privkey: Optional[bytes], pubkey: bytes) -> None: """ :param version: The version bytes for this xpub :param depth: The depth of this xpub as defined in BIP 32 :param parent_fingerprint: The 4 byte fingerprint of the parent xpub as defined in BIP 32 :param child_num: The number of this xpub as defined in BIP 32 :param chaincode: The chaincode of this xpub as defined in BIP 32 :param privkey: The private key for this xpub if available :param pubkey: The public key for this xpub """ self.version: bytes = version self.is_testnet: bool = version == ExtendedKey.TESTNET_PUBLIC or version == ExtendedKey.TESTNET_PRIVATE self.is_private: bool = version == ExtendedKey.MAINNET_PRIVATE or version == ExtendedKey.TESTNET_PRIVATE self.depth: int = depth self.parent_fingerprint: bytes = parent_fingerprint self.child_num: int = child_num self.chaincode: bytes = chaincode self.pubkey: bytes = pubkey self.privkey: Optional[bytes] = privkey @classmethod def deserialize(cls, xpub: str) -> 'ExtendedKey': """ Create an :class:`~ExtendedKey` from a Base58 check encoded xpub :param xpub: The Base58 check encoded xpub """ data = base58.decode(xpub)[:-4] # Decoded xpub without checksum return cls.from_bytes(data) @classmethod def from_bytes(cls, data: bytes) -> 'ExtendedKey': """ Create an :class:`~ExtendedKey` from a serialized xpub :param xpub: The serialized xpub """ version = data[0:4] if version not in [ExtendedKey.MAINNET_PRIVATE, ExtendedKey.MAINNET_PUBLIC, ExtendedKey.TESTNET_PRIVATE, ExtendedKey.TESTNET_PUBLIC]: raise Exception(f"Extended key magic of {version.hex()} is invalid") is_private = version == ExtendedKey.MAINNET_PRIVATE or version == ExtendedKey.TESTNET_PRIVATE depth = data[4] parent_fingerprint = data[5:9] child_num = struct.unpack('>I', data[9:13])[0] chaincode = data[13:45] if is_private: privkey = data[46:] pubkey = point_to_bytes(point_mul(G, int.from_bytes(privkey, byteorder="big"))) return cls(version, depth, parent_fingerprint, child_num, chaincode, privkey, pubkey) else: pubkey = data[45:78] return cls(version, depth, parent_fingerprint, child_num, chaincode, None, pubkey) def serialize(self) -> bytes: """ Serialize the ExtendedKey with the serialization format described in BIP 32. Does not create an xpub string, but the bytes serialized here can be Base58 check encoded into one. :return: BIP 32 serialized extended key """ r = self.version + struct.pack('B', self.depth) + self.parent_fingerprint + struct.pack('>I', self.child_num) + self.chaincode if self.is_private: if self.privkey is None: raise ValueError("Somehow we are private but don't have a privkey") r += b"\x00" + self.privkey else: r += self.pubkey return r def to_string(self) -> str: """ Serialize the ExtendedKey as a Base58 check encoded xpub string :return: Base58 check encoded xpub """ data = self.serialize() checksum = hash256(data)[0:4] return base58.encode(data + checksum) def get_printable_dict(self) -> Dict[str, object]: """ Get the attributes of this ExtendedKey as a dictionary that can be printed :return: Dictionary containing ExtendedKey information that can be printed """ d: Dict[str, object] = {} d['testnet'] = self.is_testnet d['private'] = self.is_private d['depth'] = self.depth d['parent_fingerprint'] = binascii.hexlify(self.parent_fingerprint).decode() d['child_num'] = self.child_num d['chaincode'] = binascii.hexlify(self.chaincode).decode() if self.is_private and isinstance(self.privkey, bytes): d['privkey'] = binascii.hexlify(self.privkey).decode() d['pubkey'] = binascii.hexlify(self.pubkey).decode() return d def derive_pub(self, i: int) -> 'ExtendedKey': """ Derive the public key at the given child index. :param i: The child index of the pubkey to derive """ if is_hardened(i): raise ValueError("Index cannot be larger than 2^31") # Data to HMAC. Same as CKDpriv() for public child key. data = self.pubkey + struct.pack(">L", i) # Get HMAC of data Ihmac = hmac.new(self.chaincode, data, hashlib.sha512).digest() Il = Ihmac[:32] Ir = Ihmac[32:] # Construct curve point Il*G+K Il_int = int(binascii.hexlify(Il), 16) child_pubkey = point_add(point_mul(G, Il_int), bytes_to_point(self.pubkey)) # Construct and return a new BIP32Key pubkey = point_to_bytes(child_pubkey) chaincode = Ir fingerprint = hash160(self.pubkey)[0:4] return ExtendedKey(ExtendedKey.TESTNET_PUBLIC if self.is_testnet else ExtendedKey.MAINNET_PUBLIC, self.depth + 1, fingerprint, i, chaincode, None, pubkey) def derive_pub_path(self, path: Sequence[int]) -> 'ExtendedKey': """ Derive the public key at the given path :param path: Sequence of integers for the path of the pubkey to derive """ key = self for i in path: key = key.derive_pub(i) return key ================================================ FILE: bip-0328/reference.py ================================================ #! /usr/bin/env python3 import json import os import sys from _base58 import xpub_to_pub_hex from _bip327 import cbytes, key_agg from _xpub import ExtendedKey CHAINCODE = bytes.fromhex("868087ca02a6f974c4598924c36b57762d32cb45717167e300622c7167e38965") def aggregate_to_xpub(aggregate: bytes) -> ExtendedKey: return ExtendedKey(ExtendedKey.MAINNET_PUBLIC, 0, b"\x00\x00\x00\x00", 0, CHAINCODE, None, aggregate) def test_aggregate_to_xpub(): with open(os.path.join(sys.path[0], "vectors.json"), "r") as f: test_data = json.load(f) for test_case in test_data: keys = [bytes.fromhex(k) for k in test_case["keys"]] agg_ctx = key_agg(keys) pub = cbytes(agg_ctx.Q) assert pub.hex() == test_case["aggregate_pubkey"] xpub = aggregate_to_xpub(pub) assert xpub.to_string() == test_case["xpub"] if __name__ == "__main__": test_aggregate_to_xpub() ================================================ FILE: bip-0328/vectors.json ================================================ [ { "aggregate_pubkey": "0354240c76b8f2999143301a99c7f721ee57eee0bce401df3afeaa9ae218c70f23", "keys": [ "03935F972DA013F80AE011890FA89B67A27B7BE6CCB24D3274D18B2D4067F261A9", "02F9308A019258C31049344F85F89D5229B531C845836F99B08601F113BCE036F9" ], "xpub": "xpub661MyMwAqRbcFt6tk3uaczE1y6EvM1TqXvawXcYmFEWijEM4PDBnuCXwwXEKGEouzXE6QLLRxjatMcLLzJ5LV5Nib1BN7vJg6yp45yHHRbm" }, { "aggregate_pubkey": "0290539eede565f5d054f32cc0c220126889ed1e5d193baf15aef344fe59d4610c", "keys": [ "02F9308A019258C31049344F85F89D5229B531C845836F99B08601F113BCE036F9", "03DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA659", "023590A94E768F8E1815C2F24B4D80A8E3149316C3518CE7B7AD338368D038CA66" ], "xpub": "xpub661MyMwAqRbcFt6tk3uaczE1y6EvM1TqXvawXcYmFEWijEM4PDBnuCXwwVk5TFJk8Tw5WAdV3DhrGfbFA216sE9BsQQiSFTdudkETnKdg8k" }, { "aggregate_pubkey": "022479f134cdb266141dab1a023cbba30a870f8995b95a91fc8464e56a7d41f8ea", "keys": [ "02DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA659", "023590A94E768F8E1815C2F24B4D80A8E3149316C3518CE7B7AD338368D038CA66", "02F9308A019258C31049344F85F89D5229B531C845836F99B08601F113BCE036F9", "03935F972DA013F80AE011890FA89B67A27B7BE6CCB24D3274D18B2D4067F261A9" ], "xpub": "xpub661MyMwAqRbcFt6tk3uaczE1y6EvM1TqXvawXcYmFEWijEM4PDBnuCXwwUvaZYpysLX4wN59tjwU5pBuDjNrPEJbfxjLwn7ruzbXTcUTHkZ" } ] ================================================ FILE: bip-0328.mediawiki ================================================
  BIP: 328
  Layer: Applications
  Title: Derivation Scheme for MuSig2 Aggregate Keys
  Authors: Ava Chow 
  Status: Complete
  Type: Informational
  Assigned: 2024-06-04
  License: CC0-1.0
==Abstract== This document specifies how BIP 32 extended public keys can be constructed from a BIP 327 MuSig2 aggregate public key and how such keys should be used for key derivation. ==Copyright== This BIP is licensed under the Creative Commons CC0 1.0 Universal license. ==Motivation== Multiple signers can create a single aggregate public key with MuSig2 that is indistinguishable from a random public key. The cosigners need a method for generating additional aggregate pubkeys to follow the best practice of using a new address for every payment. The obvious method is for the cosigners to generate multiple public keys and produce a new aggregate pubkey every time one is needed. This is similar to how multisig using Bitcoin script works where all of the cosigners share their extended public keys and do derivation to produce the multisig script. The same could be done with MuSig2 and instead of producing a multisig script, the result would be a MuSig2 aggregate pubkey. However, it is much simpler to be able to derive from a single extended public key instead of having to derive from many extended public keys and aggregate them. As MuSig2 produces a normal looking public key, the aggregate public can be used in this way. This reduces the storage and computation requirements for generating new aggregate pubkeys. ==Specification== A synthetic xpub can be created from a BIP 327 MuSig2 plain aggregate public key by setting the depth to 0, the child number to 0, and attaching a chaincode with the byte string 868087ca02a6f974c4598924c36b57762d32cb45717167e300622c7167e38965'''Where does this constant chaincode come from?''' It is the SHA256 of the text MuSig2MuSig2MuSig2. This fixed chaincode should be used by all such synthetic xpubs following this specification. Unhardened child public keys can be derived from the synthetic xpub as with any other xpub. Since the aggregate public key is all that is necessary to produce the synthetic xpub, any aggregate public key that will be used in this way shares the same privacy concerns as typical xpubs. Furthermore, as there is no aggregate private key, only unhardened derivation from the aggregate public key is possible. When signing, all signers must compute the tweaks used in the BIP 32 derivation for the child key being signed for. The IL value computed in ''CKDpub'' is the tweak used at each derivation step. These are provided in the session context, each with a tweak mode of plain (''is_xonly_t = false''). When the ''Sign'' algorithm is used, the tweaks will be applied to the partial signatures. ==Test Vectors== * Aggregate pubkey 0354240c76b8f2999143301a99c7f721ee57eee0bce401df3afeaa9ae218c70f23 ** Synthetic xpub xpub661MyMwAqRbcFt6tk3uaczE1y6EvM1TqXvawXcYmFEWijEM4PDBnuCXwwXEKGEouzXE6QLLRxjatMcLLzJ5LV5Nib1BN7vJg6yp45yHHRbm ** Keys: *** 03935F972DA013F80AE011890FA89B67A27B7BE6CCB24D3274D18B2D4067F261A9 *** 02F9308A019258C31049344F85F89D5229B531C845836F99B08601F113BCE036F9 * Aggregate pubkey 0290539eede565f5d054f32cc0c220126889ed1e5d193baf15aef344fe59d4610c ** Synthetic xpub xpub661MyMwAqRbcFt6tk3uaczE1y6EvM1TqXvawXcYmFEWijEM4PDBnuCXwwVk5TFJk8Tw5WAdV3DhrGfbFA216sE9BsQQiSFTdudkETnKdg8k ** Keys: *** 02F9308A019258C31049344F85F89D5229B531C845836F99B08601F113BCE036F9 *** 03DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA659 *** 023590A94E768F8E1815C2F24B4D80A8E3149316C3518CE7B7AD338368D038CA66 * Aggregate pubkey 022479f134cdb266141dab1a023cbba30a870f8995b95a91fc8464e56a7d41f8ea ** Synthetic xpub xpub661MyMwAqRbcFt6tk3uaczE1y6EvM1TqXvawXcYmFEWijEM4PDBnuCXwwUvaZYpysLX4wN59tjwU5pBuDjNrPEJbfxjLwn7ruzbXTcUTHkZ ** Keys: *** 02DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA659 *** 023590A94E768F8E1815C2F24B4D80A8E3149316C3518CE7B7AD338368D038CA66 *** 02F9308A019258C31049344F85F89D5229B531C845836F99B08601F113BCE036F9 *** 03935F972DA013F80AE011890FA89B67A27B7BE6CCB24D3274D18B2D4067F261A9 ==Backwards Compatibility== Once a synthetic xpub is created, it is fully backwards compatible with BIP 32 - only unhardened derivation can be done, and the signers will be able to produce a signature for any derived children. ==Rationale== ==Reference Implementation== A Python reference implementation is available in this BIP's [[bip-0328|Auxiliary Files]]. ==Acknowledgements== Thanks to Pieter Wuille, Andrew Poelstra, Sanket Kanjalkar, Salvatore Ingala, and all others who participated in discussions on this topic. ================================================ FILE: bip-0329.mediawiki ================================================
  BIP: 329
  Layer: Applications
  Title: Wallet Labels Export Format
  Authors: Craig Raw 
  Status: Draft
  Type: Informational
  Assigned: 2022-08-23
  License: BSD-2-Clause
==Abstract== This document specifies a format for the export of labels that may be attached to various common types of records in a wallet. ==Copyright== This BIP is licensed under the BSD 2-clause license. ==Motivation== The export and import of funds across different Bitcoin wallet applications is well defined through standards such as BIP39, BIP32, BIP44 etc. These standards are well supported and allow users to move easily between different wallets. There is, however, no defined standard to transfer any labels the user may have applied to the transactions, addresses, public keys, inputs, outputs or xpubs in their wallet. The UTXO model that Bitcoin uses makes these labels particularly valuable as they may indicate the source of funds, whether received externally or as a result of change from a prior transaction. In both cases, care must be taken when spending to avoid undesirable leaks of private information. Labels provide valuable guidance in this regard, and have even become mandatory when spending in several Bitcoin wallets. Allowing users to import and export their labels in a standardized way ensures that they do not experience lock-in to a particular wallet application. In addition, many wallets allow unspent outputs to be frozen or made unspendable within the wallet. Since this wallet-related metadata is similar to labels and not captured elsewhere, it is also included in this format. ==Rationale== While there is currently no widely accepted format for exporting and importing labels, there are existing formats in use. SLIP-0015[https://github.com/satoshilabs/slips/blob/master/slip-0015.md SLIP-0015] defines a format for exporting address and output labels, but requires encryption using a private key associated with the wallet seed, and thus cannot be used independently by coordinator wallets which cannot access private keys. The Electrum wallet imports and exports address and transaction labels in a JSON format which could be used with other record types, but the format used is not self describing making record type identification difficult. ==Specification== In order to be lightweight, human readable and well structured, this BIP uses a JSON format. Further, the JSON Lines format is used (also called newline-delimited JSON)[https://jsonlines.org/ jsonlines.org]. This allows a document to be split, streamed, or incrementally added to, and limits the potential for formatting errors to invalidate an entire import. It is also a convenient format for command-line processing, which is often line-oriented. Further to the JSON Lines specification, an export of labels from a wallet must be a UTF-8 encoded text file, containing one record per line consisting of a valid JSON object. Lines are separated by \n. Multiline values are not permitted. Each JSON object must contain 3 or 4 key/value pairs, defined as follows: {| class="wikitable" |- ! Key ! Description |- | type | One of tx, addr, pubkey, input, output or xpub |- | ref | Reference to the transaction, address, public key, input, output or extended public key |- | label | The label applied to the reference |- | origin | Optional key origin information referencing the wallet associated with the label |- | spendable | One of true or false, denoting if an output should be spendable by the wallet |} The reference is defined for each type as follows: {| class="wikitable" |- ! Type ! Description ! Example |- | tx | Transaction id in hexadecimal format | f91d0a8a78462bc59398f2c5d7a84fcff491c26ba54c4833478b202796c8aafd |- | addr | Address in base58 or bech32 format | bc1q34aq5drpuwy3wgl9lhup9892qp6svr8ldzyy7c |- | pubkey | 32, 33 or 65 byte public key in hexadecimal format | 0283409659355b6d1cc3c32decd5d561abaac86c37a353b52895a5e6c196d6f448 |- | input | Transaction id and input index separated by a colon | f91d0a8a78462bc59398f2c5d7a84fcff491c26ba54c4833478b202796c8aafd:0 |- | output | Transaction id and output index separated by a colon | f91d0a8a78462bc59398f2c5d7a84fcff491c26ba54c4833478b202796c8aafd:1 |- | xpub | Extended public key as defined by BIP32 | xpub661MyMwAqRbcFtXgS5sYJABqqG9YLmC4Q1Rdap9gSE8Nq... |} Each JSON object must contain both type and ref properties. The label, origin and spendable properties are optional. If the label or spendable properties are omitted, the importing wallet should not alter these values. The spendable property should only appear where type is output. If present, the optional origin property must contain an abbreviated output descriptor (as defined by BIP380[https://github.com/bitcoin/bips/blob/master/bip-0380.mediawiki BIP-0380]) describing a BIP32 compatible originating wallet, including all key origin information but excluding any actual keys, any child path elements, or a checksum. This property should be used to disambiguate transaction labels from different wallets contained in the same export, particularly when exporting multiple accounts derived from the same seed. Care should be taken when exporting due to the privacy sensitive nature of the data. Encryption in transit over untrusted networks is highly recommended, and encryption at rest should also be considered. Unencrypted exports should be deleted as soon as possible. For security reasons no private key types are defined. ==Importing== * An importing wallet may ignore records it does not store, and truncate labels if necessary. A suggested default for maximum label length is 255 characters, and an importing wallet should consider warning the user if truncation is applied. * Wallets importing public key records may derive addresses from them to match against known wallet addresses. * Wallets importing extended public keys may match them against signers, for example in a multisig setup. ==Backwards Compatibility== The nature of this format makes it naturally extensible to handle other record types. However, importing wallets complying to this specification should ignore types not defined here. ==Test Vectors== The following fragment represents a wallet label export:
{ "type": "tx", "ref": "f91d0a8a78462bc59398f2c5d7a84fcff491c26ba54c4833478b202796c8aafd", "label": "Transaction", "origin": "wpkh([d34db33f/84'/0'/0'])" }
{ "type": "addr", "ref": "bc1q34aq5drpuwy3wgl9lhup9892qp6svr8ldzyy7c", "label": "Address" }
{ "type": "pubkey", "ref": "0283409659355b6d1cc3c32decd5d561abaac86c37a353b52895a5e6c196d6f448", "label": "Public Key" }
{ "type": "input", "ref": "f91d0a8a78462bc59398f2c5d7a84fcff491c26ba54c4833478b202796c8aafd:0", "label": "Input" }
{ "type": "output", "ref": "f91d0a8a78462bc59398f2c5d7a84fcff491c26ba54c4833478b202796c8aafd:1", "label": "Output", "spendable": false }
{ "type": "xpub", "ref": "xpub661MyMwAqRbcFtXgS5sYJABqqG9YLmC4Q1Rdap9gSE8NqtwybGhePY2gZ29ESFjqJoCu1Rupje8YtGqsefD265TMg7usUDFdp6W1EGMcet8", "label": "Extended Public Key" }
{ "type": "tx", "ref": "f546156d9044844e02b181026a1a407abfca62e7ea1159f87bbeaa77b4286c74", "label": "Account #1 Transaction", "origin": "wpkh([d34db33f/84'/0'/1'])" }
==Additional Fields== If the goal is solely to move labels between cooperating wallets, then the above values are the minimum needed. However, wallet data exports can serve other purposes. Many values associated with addresses, transactions and outputs are already on hand for the wallet generating the export, and yet would be hard or impossible for importing tools to reconstruct. All of the following values are optional for the exporter to provide, but should be given if they are readily available. === Transactions === * height: An integer giving the block height where this fully confirmed transaction can be found. For transactions that are confirmed by less than 6 blocks, omit this field or provide a value of zero. (Background: Until it is fully confirmed, the "height" of a transaction is in flux and may vary due to chain reorgs. However, the consumer of the labels, may not know the current block height, so it cannot know if the height is "real" (firm, fixed) or just transitory. Therefore, it is important to omit the height unless the generating wallet considers the transaction to be confirmed.) * time: ISO-8601 formatted timestamp of the block given by the "height" field, preferably in UTC, although ISO-8601 can represent local times. Example: 2025-01-23T11:40:35Z. * fee: Integer giving the number of Satoshis that went to the miner for this transaction. * value: Signed integer giving the number of Satoshis that came into the wallet by this transaction. Will be negative when sats leave the wallet. Could be zero if it is a consolidation transaction that moves from old UTXO to new. * rate: Exchange rate at time of transaction. This is the value of a Bitcoin, expressed in another currency, at the time of the transaction, based on user preferences for data source. Multiple currencies can be given. Keys are ISO 4217 currency codes where possible. Example: "rate": { "USD": 105620.00 } === Address, Inputs, and Outputs === * keypath: The data needed to build full descriptor down to the specific address. This extends origin with the final two components that are unhardened (in the typical case, assuming BIP-84). Provide string /1/123 for wpkh([d34db33f/84'/0'/0'/1/123]). If the first character is not /, then it should be interpreted as a full descriptor, independent of origin (if any). === Inputs and Outputs === * value: Integer with the number of Satoshis (nValue) of the input or output. * fmv: Fair market value of the input/output relative to some other currency, typically fiat. The value should be a mapping, from currency code to decimal number. Example: "fmv": { "USD": 1233.45 }. Most situations will have only a single currency value, and it represents the real price of the goods/services expressed in some fiat currency. This is not an exchange *rate*, but an absolute value. By dividing by the value (above), it is possible to calculate an effective change rate for the transaction. * height and time: Same definition as defined in Transactions. === Address === * heights: a list of block heights that contain any activity related to this address, include outputs that deposit to the address, and transactions that spend UTXOs of this address. Omit heights for transactions that are not fully confirmed. An empty array indicates the address is unused for confirmed transactions. == Comment on Types in JSON == JSON can serialize a number of basic types, including string, integer and boolean (true/false). Decimal values (123.45) can also be serialized, but some parsing libraries may interpret them as floating point values, which is generally not what we want in financial applications. When hand-crafting JSON data, be careful not to write "false" (with quotes), since that is a string with 5 characters and not a boolean. ==Reference Implementation== * [https://github.com/Labelbase/python-bip329 Python-BIP329 package] ==References== ================================================ FILE: bip-0330/minisketch.py ================================================ #!/usr/bin/env python3 import random ######## ENCODING and DECODING ######## FIELD_BITS = 32 FIELD_MODULUS = (1 << FIELD_BITS) + 0b10001101 def mul2(x): """Compute 2*x in GF(2^FIELD_BITS)""" return (x << 1) ^ (FIELD_MODULUS if x.bit_length() >= FIELD_BITS else 0) def mul(x, y): """Compute x*y in GF(2^FIELD_BITS)""" ret = 0 for bit in [(x >> i) & 1 for i in range(x.bit_length())]: ret ^= bit * y y = mul2(y) return ret ######## ENCODING only ######## def sketch(shortids, capacity): """Compute the bytes of a sketch for given shortids and given capacity.""" odd_sums = [0 for _ in range(capacity)] for shortid in shortids: squared = mul(shortid, shortid) for i in range(capacity): odd_sums[i] ^= shortid shortid = mul(shortid, squared) return b''.join(elem.to_bytes(4, 'little') for elem in odd_sums) ######## DECODING only ######## def inv(x): """Compute 1/x in GF(2^FIELD_BITS)""" t = x for i in range(FIELD_BITS - 2): t = mul(mul(t, t), x) return mul(t, t) def berlekamp_massey(s): """Given a sequence of LFSR outputs, find the coefficients of the LFSR.""" C, B, L, m, b = [1], [1], 0, 1, 1 for n in range(len(s)): d = s[n] for i in range(1, L + 1): d ^= mul(C[i], s[n - i]) if d == 0: m += 1 else: T = list(C) while len(C) <= len(B) + m: C += [0] t = mul(d, inv(b)) for i in range(len(B)): C[i + m] ^= mul(t, B[i]) if 2 * L <= n: L, B, b, m = n + 1 - L, T, d, 1 else: m += 1 return C[0:L + 1] def poly_monic(p): """Return the monic multiple of p, or 0 if the input is 0.""" if len(p) == 0: return [] i = inv(p[-1]) return [mul(v, i) for v in p] def poly_divmod(m, p): """Compute the polynomial quotient p/m, and replace p with p mod m.""" assert(len(m) > 0 and m[-1] == 1) div = [0 for _ in range(len(p) - len(m) + 1)] while len(p) >= len(m): div[len(p) - len(m)] = p[-1] for i in range(len(m)): p[len(p) - len(m) + i] ^= mul(p[-1], m[i]) assert(p[-1] == 0) p.pop() while (len(p) > 0 and p[-1] == 0): p.pop() return div def poly_gcd(a, b): """Compute the GCD of a and b (destroys the inputs).""" if len(a) < len(b): a, b = b, a while len(b): if len(b) == 1: return [1] b = poly_monic(b) poly_divmod(b, a) a, b = b, a return a def poly_sqr(p): """Compute the coefficients of the square of polynomial with coefficients p.""" return [0 if i & 1 else mul(p[i // 2], p[i // 2]) for i in range(2 * len(p))] def poly_trace(m, a): """Compute the coefficients of the trace polynomial of (a*x) mod m.""" out = [0, a] for i in range(FIELD_BITS - 1): out = poly_sqr(out) while len(out) < 2: out += [0] out[1] = a poly_divmod(m, out) return out def find_roots_inner(p, a): """Recursive helper function for find_roots (destroys p). a is randomizer.""" # p must be monic assert(len(p) > 0 and p[-1] == 1) # Deal with degree 0 and degree 1 inputs if len(p) == 1: return [] elif len(p) == 2: return [p[0]] # Otherwise, split p in left*right using parameter a_vals[0]. t = poly_monic(poly_trace(p, a)) left = poly_gcd(list(p), t) right = poly_divmod(list(left), p) # Invoke recursion with the remaining a_vals. ret_right = find_roots_inner(right, mul2(a)) ret_left = find_roots_inner(left, mul2(a)) # Concatenate roots return ret_left + ret_right def find_roots(p): """Find the roots of polynomial with coefficients p.""" # Compute x^(2^FIELD_BITS)+x mod p in a roundabout way. t = poly_trace(p, 1) t2 = poly_sqr(t) for i in range(len(t)): t2[i] ^= t[i] poly_divmod(p, t2) # If distinct from 0, p is not fully factorizable into non-repeating roots. if len(t2): return None # Invoke the recursive splitting algorithm return find_roots_inner(list(p), random.randrange(1, 2**32-1)) def decode(sketch): """Recover the shortids from a sketch.""" odd_sums = [int.from_bytes(sketch[i*4:(i+1)*4], 'little') for i in range(len(sketch) // 4)] sums = [] for i in range(len(odd_sums) * 2): if i & 1: sums.append(mul(sums[(i-1)//2], sums[(i-1)//2])) else: sums.append(odd_sums[(i+1)//2]) return find_roots(list(reversed(berlekamp_massey(sums)))) ================================================ FILE: bip-0330.mediawiki ================================================
  BIP: 330
  Layer: Peer Services
  Title: Transaction announcements reconciliation
  Authors: Gleb Naumenko 
           Pieter Wuille 
  Status: Draft
  Type: Specification
  Assigned: 2019-09-25
  License: CC0-1.0
  License-Code: MIT
==Abstract== This document specifies a P2P protocol extension for reconciliation of transaction announcements between 2 nodes, which is a building block for efficient transaction relay protocols (e.g., [https://arxiv.org/pdf/1905.10518.pdf Erlay]). This is a step towards increasing the connectivity of the network for almost no bandwidth cost. ==Motivation== Currently in the Bitcoin network, every 32-byte transaction ID is announced in at least one direction between every pair of connected peers, via INV messages. This results in high cost of announcing transactions: ''O(nodes * connections_per_node)''. A reconciliation-based protocol which uses the technique suggested in this document can have better scaling properties than INV-based flooding. Increasing the connectivity of the network makes the network more robust to partitioning attacks; thus, improving the bandwidth scaling of transaction relay to ''O(nodes)'' (and without a high constant overhead) would allow us to improve the security of the network by increasing connectivity. It would also reduce the bandwidth required to run a Bitcoin node and potentially enable more users to run full nodes. ===Erlay=== [https://arxiv.org/pdf/1905.10518.pdf Erlay] is an example of a high-level transaction relay protocol which employs set reconciliation for bandwidth efficiency. Note that what we are going to describe here is a modified version from the protocol (it is different from what is presented in the paper). Erlay uses both flooding (announcing using INV messages to all peers) and reconciliation to announce transactions. Flooding is expensive, so Erlay seeks to use it only when necessary to facilitate rapid relay over a small subset of connections. Efficient set reconciliation is meant to deliver transactions to those nodes which didn't receive a transaction via flooding, and also just make sure remaining connections are in sync (directly connected pairs of nodes are aware they have nothing to learn from each other). Efficient set reconciliation works as follows: 1) every node keeps a reconciliation set for each peer, in which transactions are placed which would have been announced using INV messages absent this protocol 2) once in a while every node chooses a peer from its reconciliation queue to reconcile with, resulting in both sides learning the transactions known to the other side 3) after every reconciliation round, the corresponding reconciliation set is cleared A more detailed description of a set reconciliation round can be found below. Erlay allows us to: * save a significant portion of the bandwidth consumed by a node * increase network connectivity for almost no bandwidth or latency cost * keep transaction propagation latency at the same level This document proposes a P2P-layer extension which is required to enable efficient reconciliation-based protocols (like Erlay) for transaction relay. ==Specification== ===New data structures=== Several new data structures are introduced to the P2P protocol first, to aid with efficient transaction relay. ====32-bit short transaction IDs==== = Short IDs are computed as follows: * Let ''salt1'' and ''salt2'' be the entropy contributed by both sides; see the "sendtxrcncl" message further for details how they are exchanged. * Sort the two salts such that ''salt1 ≤ salt2'' (which side sent what doesn't matter). * Compute ''h = TaggedHash("Tx Relay Salting", salt1, salt2)'', where the two salts are encoded in 64-bit little-endian byte order, and TaggedHash is specified by [https://github.com/bitcoin/bips/blob/master/bip-0340.mediawiki BIP-340]. * Let ''k0'' be the 64-bit integer obtained by interpreting the first 8 bytes of ''h'' in little-endian byte order. * Let ''k1'' be the 64-bit integer obtained by interpreting the second 8 bytes of ''h'' in little-endian byte order. * Let ''s = SipHash-2-4((k0,k1),wtxid)'', where ''wtxid'' is the transaction hash including witness data as defined by BIP141. * The short ID is equal to ''1 + (s mod 0xFFFFFFFF)''. This results in approximately uniformly distributed IDs in the range ''[1..0xFFFFFFFF]'', which is a requirement for using them as elements in 32-bit sketches. See the next paragraph for details. ====Short transaction ID sketches==== Reconciliation-based relay uses [https://www.cs.bu.edu/~reyzin/code/fuzzy.html PinSketch] BCH-based secure sketches as introduced by the [https://www.cs.bu.edu/~reyzin/fuzzy.html Fuzzy Extractors paper]. They are a form of set checksums with the following properties: * Sketches have a predetermined capacity, and when the number of elements in the set does not exceed the capacity, it is always possible to recover the entire set from the sketch by decoding the sketch. A sketch of nonzero b-bit elements with capacity c can be stored in bc bits. * A sketch of the [https://en.wikipedia.org/wiki/Symmetric_difference symmetric difference] between the two sets (i.e., all elements that occur in one but not both input sets), can be obtained by combining the sketches of those sets. The sketches used here consists of elements of the [https://en.wikipedia.org/wiki/Finite_field finite field] ''GF(232)''. Specifically, we represent finite field elements as polynomials in ''x'' over ''GF(2)'' modulo ''x327 + x3 + x2 + 1''. To map integers to finite field elements, simply treat each bit ''i'' (with value ''2i'') in the integer as the coefficient of ''xi'' in the polynomial representation. For example the integer ''101 = 26 + 25 + 22 + 1'' is mapped to field element ''x6 + x5 + x2 + 1''. These field elements can be added and multiplied together, but the specifics of that are out of scope for this document. A short ID sketch with capacity ''c'' consists of a sequence of ''c'' field elements. The first is the sum of all short IDs in the set, the second is the sum of the 3rd powers of all short IDs, the third is the sum of the 5th powers etc., up to the last element with is the sum of the ''(2c-1)''th powers. These elements are then encoded as 32-bit integers in little endian byte order, resulting in a ''4c''-byte serialization. The following Python 3.2+ code implements the creation of sketches:
FIELD_BITS = 32
FIELD_MODULUS = (1 << FIELD_BITS) + 0b10001101

def mul2(x):
    """Compute 2*x in GF(2^FIELD_BITS)"""
    return (x << 1) ^ (FIELD_MODULUS if x.bit_length() >= FIELD_BITS else 0)

def mul(x, y):
    """Compute x*y in GF(2^FIELD_BITS)"""
    ret = 0
    for bit in [(x >> i) & 1 for i in range(x.bit_length())]:
        ret, y = ret ^ bit * y, mul2(y)
    return ret

def create_sketch(shortids, capacity):
    """Compute the bytes of a sketch for given shortids and given capacity."""
    odd_sums = [0 for _ in range(capacity)]
    for shortid in shortids:
        squared = mul(shortid, shortid)
        for i in range(capacity):
            odd_sums[i] ^= shortid
            shortid = mul(shortid, squared)
    return b''.join(elem.to_bytes(4, 'little') for elem in odd_sums)
The [https://github.com/sipa/minisketch/ minisketch] library implements the construction, merging, and decoding of these sketches efficiently. ===Intended Protocol Flow=== Set reconciliation primarily consists of the transmission and decoding of a reconciliation set sketch upon request. Since sketches are based on the WTXIDs, the negotiation and support of Erlay should be enabled only if both peers signal [https://github.com/bitcoin/bips/blob/master/bip-0339.mediawiki BIP-339] support. [[File:bip-0330/recon_scheme_merged.png|framed|center|Protocol flow]] ====Sketch extension==== If a node is unable to reconstruct the set difference from the received sketch, the node then makes a request for sketch extension. The peer would then send an extension, which is a sketch of a higher capacity (allowing to decode more differences) over the same transactions minus the sketch part which was already sent initially (to save bandwidth). To allow this optimization, the initiator is supposed to locally store a sketch received initially. This optimization is possible because extending a sketch is just concatenating new elements to an array. ===New messages=== Several new protocol messages are added: sendtxrcncl, reqrecon, sketch, reqsketchext, reconcildiff. This section describes their serialization, contents, and semantics. In what follows, all integers are serialized in little-endian byte order. Boolean values are encoded as a single byte that must be 0 or 1 exactly. Arrays are serialized with the CompactSize prefix that encodes their length, as is common in other P2P messages. ====sendtxrcncl==== The sendtxrcncl message announces support for the reconciliation protocol. It is expected to be only sent once, and ignored by nodes that don't support it. Should be sent before "verack" and accompanied by "wtxidrelay" (in any order). If "sendtxrcncl" was sent after "verack", the sender should be disconnected. If "sendtxrcncl" was sent before "verack", but by "verack" the "wtxidrelay" message was not received, "sendtxrcncl" should be ignored. The connection should proceed normally, but as if reconciliation was not supported. Must not be sent if peer specified no support for transaction relay (fRelay=0) in "version". Otherwise, the sender should be disconnected. Its payload consists of: {|class="wikitable" ! Data type !! Name !! Description |- | uint32 || version || Sender must set this to 1 currently, otherwise receiver should ignore the message. v1 is the lowest protocol version, everything below that is a protocol violation. |- | uint64 || salt || The salt used in the short transaction ID computation. |} After both peers have confirmed support by sending "sendtxrcncl", the initiator of the P2P connection assumes the role of reconciliation initiator (will send "reqrecon" messages) and the other peer assumes the role of reconciliation responder (will respond to "reqrecon" messages). "reqrecon" messages can only be sent by the reconciliation initiator. ====reqrecon==== The reqrecon message initiates a reconciliation round. {|class="wikitable" ! Data type !! Name !! Description |- | uint16 || set_size || Size of the sender's reconciliation set, used to estimate set difference. |- | uint16 || q || Coefficient used to estimate set difference. Multiplied by PRECISION=(2^15) - 1 and rounded up by the sender and divided by PRECISION by the receiver. |} Upon receipt of a "reqrecon" message, the receiver: * Constructs and sends a "sketch" message (see below), with a sketch of certain ''capacity=f(set_size, local_set_size, q)'' (the exact function is suggested below), where ''local_set_size'' represents size of the receiver's reconciliation set. * Makes a snapshot of their current reconciliation set, and clears the set itself. The snapshot is kept until a "reconcildiff" message is received by the node. No new "reqrecon" message can be sent until a "reconcildiff" message is sent. ====sketch==== The sketch message is used to communicate a sketch required to perform set reconciliation. {|class="wikitable" ! Data type !! Name !! Description |- | byte[] || skdata || The sketch of the sender's reconciliation snapshot |} The sketch message may be received in two cases. 1. Initial sketch. Upon receipt of a "sketch" message, a node computes the difference sketch by combining the received sketch with a sketch computed locally for a corresponding reconciliation set. The receiving node then tries to decode the difference sketch and based on the result: * If the decoding failed, the receiving node requests an extension sketch by sending a "reqsketchext" message. Alternatively, the node may terminate the reconciliation right away by sending a "reconcildiff" message is sent with the failure flag set (success=false). * If the decoding succeeded, a "reconcildiff" message with success=true. The receiver also makes snapshot of their current reconciliation set, and clears the set itself. The snapshot is kept until a "reconcildiff" message is sent by the node. It is needed to enable sketch extension. 2. Sketch extension. By combining the sketch extension with the initially received sketch, an extended sketch is obtained. The receiving node then computes the extended difference sketch by combining the received extended sketch with an extended sketch computed locally over a corresponding reconciliation set snapshot. The receiving node then tries to decode the extended difference sketch and based on the result: * If the decoding failed, the receiving node terminates the reconciliation right away by sending a "reconcildiff" message is sent with the failure flag set (success=false). * If the decoding succeeded, a "reconcildiff" message with success=true. In either cases, a "reconcildiff" with success=false should also be accompanied with announcing all transactions from the reconciliation set (or set snapshot if failed after extension) as a fallback to flooding. A "reconcildiff" with success=true should contain unknown short IDs of the transactions from the decoded difference, corresponding to the transactions missing on the sender's side. Known short IDs from the difference correspond to what the receiver of the message is missing, and they should be announced via an "inv" message. ====reqsketchext==== The reqsketchext message is used by reconciliation initiator to signal that initial set reconciliation has failed and a sketch extension is needed to find set difference. It has an empty payload. Upon receipt of a "reqsketchext" message, a node responds to it with a "sketch" message, which contains a sketch extension: a sketch (of the same transactions sketched initially) of higher capacity without the part sent initially. ====reconcildiff==== The reconcildiff message is used by reconciliation initiator to announce transactions which are found to be missing during set reconciliation on the sender's side. {|class="wikitable" ! Data type !! Name !! Description |- | uint8 || success || Indicates whether sender of the message succeeded at set difference decoding. |- | uint32[] || ask_shortids || The short IDs that the sender did not have. |} Upon receipt a "reconcildiff" message with ''success=1'' (reconciliation success), a node sends an "inv" message for the transactions requested by 32-bit IDs (first vector) containing their wtxids (with parent transactions occurring before their dependencies). If ''success=0'' (reconciliation failure), receiver should announce all transactions from the reconciliation set via an "inv" message. In both cases, transactions the sender of the message thinks the receiver is missing are announced via an "inv" message. The regular "inv" deduplication should apply. The snapshot of the corresponding reconciliation set is cleared by the sender and the receiver of the message. The sender should also send their own "inv" message along with the reconcildiff message to announce transactions which are missing on the receiver's side. ==Local state== This BIP suggests a stateful protocol and it requires storing several variables at every node to operate properly. ====Reconciliation salt==== When negotiating reconciliation support, peers send each other their contribution to the reconciliation salt (see how we construct short IDs above). These salts (or just the resulting salt) should be stored on both sides of the connection. ====Reconciliation sets==== Every node stores a set of wtxids for every peer which supports transaction reconciliation, representing the transactions which would have been sent according to the regular flooding protocol. Incoming transactions are added to sets when those transactions are received (if they satisfy the policies such as minimum fee set by a peer). A reconciliation set is moved to the corresponding set snapshot after the transmission of the initial sketch. ====Reconciliation set snapshot==== After transmitting the initial sketch (either sending or receiving of the reconcildiff message), every node should store the snapshot of the current reconciliation set, and clear the set. This is important to make sketch extension more stable (extension should be computed over the set snapshot). Otherwise, extension would contain transactions received after sending out the initial sketch. The snapshot is cleared after the end of the reconciliation round (sending or receiving of the reconcildiff message). ====Sketch capacity estimation and q-coefficient==== Earlier we suggested that upon receiving a reconciliation request, a node should estimate the sketch capacity it should send: ''capacity=f(set_size, local_set_size, q)''. We suggest the following function: ''capacity=|set_size - local_set_size| + q * min(set_size, local_set_size) + c''. Intuitively, ''q'' represents the discrepancy in sets: the closer the sets are, the lower optimal ''q'' is. Per the Erlay paper, ''q'' should be derived as an optimal ''q'' value for the previous reconciliation with a given peer, once the actual set sizes and set difference are known. For example, if in previous round ''set_size=30'' and ''local_set_size=20'', and the *actual* difference was ''12'', then a node should compute ''q'' as following: ''q=(12 - |30-20|) / min(30, 20)=0.1'' The derivation of ''q'' can be changed according to the version of the protocol. For example, a static value could be chosen for simplicity. However, we suggest that ''q'' remains a parameter sent in every reconciliation request to enable future compatibility with more sophisticated (non-static) choices of this parameter. As for the ''c'' parameter, it is suggested to use ''c=1'' to avoid sending empty sketches and reduce the overhead caused by under-estimations. ==Backward compatibility== Older clients remain fully compatible and interoperable after this change. Clients which do not implement this protocol remain fully compatible after this change using existing protocols, because transaction announcement reconciliation is used only for peers that negotiate support for it. ==Rationale== ====Why use PinSketch for set reconciliation?==== PinSketch is more bandwidth efficient than IBLT, especially for the small differences in sets we expect to operate over. PinSketch is as bandwidth efficient as CPISync, but PinSketch has quadratic decoding complexity, while CPISync have cubic decoding complexity. This makes PinSketch significantly faster. ====Why use 32-bit short transaction IDs?==== To use Minisketch in practice, transaction IDs should be shortened (ideally, not more than 64 bits per element). A small number of bits per transaction also allows saving extra bandwidth and make operations over sketches faster. According to our estimates, 32 bits provides low collision rate in a non-adversarial model (which is enabled by using independent salts per-link). ====Why use sketch extensions instead of bisection?==== Bisection is an alternative to sketch extensions, per which a second sketch with the same initial capacity is computed over half of the txID space. Due to the linearity of sketches, transmitting just this one allows a reconciliation initiator to compute the sketch of the same capacity of another half. Two sketches allow the initiator to reconstruct twice as many differences as was allowed by an initial sketch. In practice this allows the initiator to amortize the bandwidth overhead of initial reconciliation failure, similarly to extension sketches, making the overhead negligible. The main benefit of sketch extensions is a much simpler implementation. Implementing bisection is hard (see [https://github.com/naumenkogs/bitcoin/commit/b5c92a41e4cc0599504cf838d20212f1a403e573 implementation]) because, in the end, we have to operate with two sketches and handle scenarios where one sketch decoded and another sketch failed. It becomes even more difficult if in the future we decide to allow more than one extension/bisection. Bisection in this case have to be recursive (and spawn 4/8/16/... sketches), while for extensions we always end up with one extended sketch. Sketch extensions are also more flexible: extending a sketch of capacity 10 with 4 more means just computing a sketch of capacity 14 and sending the extension, while for bisection increasing the capacity to something different than 10*2/10*4/10*8/... is sophisticated implementation-wise. The only advantage of bisection is that it doesn't require computing sketches of higher capacities (exponential cost). We believe that since the protocol is currently designed to operate in the conditions where sketches usually have at most the capacity of 20, this efficiency is not crucial. ==Implementation== https://github.com/bitcoin/bitcoin/pull/21515 ==Acknowledgments== A large fraction of this proposal was done during designing Erlay with Gregory Maxwell, Sasha Fedorova and Ivan Beschastnikh. We would like to thank Suhas Daftuar for contributions to the design and BIP structure. We would like to thank Ben Woosley for contributions to the high-level description of the idea. ==Copyright== This document is licensed under the Creative Commons CC0 1.0 Universal license. ================================================ FILE: bip-0331.mediawiki ================================================
  BIP: 331
  Layer: Peer Services
  Title: Ancestor Package Relay
  Authors: Gloria Zhao 
  Status: Draft
  Type: Specification
  Assigned: 2022-08-08
  License: BSD-3-Clause
  Discussion: 2022-05-17 https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2022-May/020493.html [bitcoin-dev] post
==Abstract== Peer-to-peer protocol messages enabling nodes to request and relay the unconfirmed ancestor package of a given transaction, and to request and relay transactions in batches. ==Motivation== ===Propagate High Feerate Transactions=== Since v0.13, Bitcoin Core has used ancestor packages instead of individual transactions to evaluate the incentive compatibility of transactions in the mempool [https://github.com/bitcoin/bitcoin/pull/7594 Add tracking of ancestor packages] and selecting them for inclusion in blocks [https://github.com/bitcoin/bitcoin/pull/7600 Select transactions using feerate-with-ancestors]. Incentive-compatible mempool and miner policies help create a fair, fee-based market for block space. While miners maximize transaction fees in order to earn higher block rewards, non-mining users participating in transaction relay reap many benefits from employing policies that result in a mempool with similar contents, including faster compact block relay and more accurate fee estimation. Additionally, users may take advantage of mempool and miner policy to bump the priority of their transactions by attaching high-fee descendants (Child Pays for Parent or CPFP). Only individually considering transactions for submission to the mempool creates a limitation in the node's ability to determine which transactions to include in the mempool, since it cannot take into account descendants until all the transactions are in the mempool. Similarly, it cannot use a transaction's descendants when considering which of two conflicting transactions to keep (Replace by Fee or RBF). When a user's transaction does not meet a mempool's minimum feerate and they cannot create a replacement transaction directly, their transaction will simply be rejected by this mempool or evicted if already included. They also cannot attach a descendant to pay for replacing a conflicting transaction; it would be rejected for spending inputs that do not exist. This limitation harms users' ability to fee-bump their transactions. Further, it presents security and complexity issues in contracting protocols which rely on presigned, time-sensitive transactions'''Examples of time-sensitive pre-signed transactions in L2 protocols.''' * [https://github.com/lightning/bolts/blob/master/03-transactions.md#htlc-timeout-and-htlc-success-transactions HTCL-Timeout in LN Penalty] * [https://github.com/revault/practical-revault/blob/master/transactions.md#cancel_tx Unvault Cancel in Revault] * [https://github.com/discreetlogcontracts/dlcspecs/blob/master/Transactions.md#refund-transaction Refund Transaction in Discreet Log Contracts] * [https://gist.github.com/instagibbs/60264606e181451e977e439a49f69fe1 Updates in Eltoo] * [https://github.com/ElementsProject/peerswap/blob/master/docs/peer-protocol.md#claim-transaction Claim Transactions in PeerSwap] to prevent cheating. In other words, a key security assumption of many contracting protocols is that all parties can propagate and confirm transactions in a timely manner. Increasing attention has been brought to "pinning attacks," a type of censorship in which the attacker uses mempool policy restrictions to prevent a transaction from being relayed or getting mined. '''Concerns for pinning attacks in L2 protocols''' * [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2022-May/020458.html Greg Sanders, "Bringing a nuke to a knife fight: Transaction introspection to stop RBF pinning"] * [https://lists.linuxfoundation.org/pipermail/lightning-dev/2020-April/002639.html Matt Corallo, "RBF Pinning with Counterparties and Competing Interest"] * [https://lists.linuxfoundation.org/pipermail/lightning-dev/2020-June/002758.html Antoine Riard, "Pinning : The Good, The Bad, The Ugly"] * [https://github.com/t-bast/lightning-docs/blob/master/pinning-attacks.md Bastien Teinturier, "Pinning Attacks"] * [https://gist.github.com/instagibbs/60264606e181451e977e439a49f69fe1 Greg Sanders, "Eltoo Pinning"] These transactions must meet a certain confirmation target to be effective, but their feerates are negotiated well ahead of broadcast time. If the forecast feerate was too low and no fee-bumping options are available, attackers can steal money from their counterparties. Always overestimating fees may sidestep this issue (but only while mempool traffic is low and predictable), but this solution is not guaranteed to work and wastes users' money. For some attacks, the available defenses require nodes to have a bird's-eye view of Bitcoin nodes' mempools, which is an unreasonable security requirement. Part of the solution is to enable nodes to consider packages of transactions as a unit, e.g. one or more low-fee ancestor transactions with a high-fee descendant, instead of separately. A package-aware mempool policy can help determine if it would actually be economically rational to accept a transaction to the mempool if it doesn't meet fee requirements individually. Network-wide adoption of these policies would create a more purely-feerate-based market for block space and allow contracting protocols to adjust fees (and therefore mining priority) at broadcast time. Theoretically, developing a safe and incentive-compatible package mempool acceptance policy is sufficient to solve this issue. Nodes could opportunistically accept packages (e.g. by trying combinations of transactions rejected from their mempools), but this practice would likely be inefficient at best and open new Denial of Service attacks at worst. As such, this proposal suggests adding new p2p messages enabling nodes to request and share package-validation-related information with one another, resulting in a more efficient and reliable way to propagate packages. ===Handle Orphans Better=== Txid-based transaction relay is problematic since a transaction's witness may be malleated without changing its txid; a node cannot use txid to deduplicate transactions it has already downloaded or validated. Ideally, two nodes that both support BIP339 wtxid-based transaction relay shouldn't ever need to use txid-based transaction relay. A single use case of txid-based relay remains: handling "orphan" transactions that spend output(s) from an unconfirmed transaction the receiving node is unaware of. Orphan transactions are very common for new nodes that have just completed Initial Block Download and do not have an up-to-date mempool. Nodes also download transactions from multiple peers. If the peer from which a child transaction was requested responds faster than the peer from which its parent was requested, that child is seen as an orphan transaction. Nodes may handle orphans by storing them in a cache and requesting any missing parent(s) by txid (prevouts specify txid, not wtxid). These parents may end up being orphans as well, if they also spend unconfirmed inputs that the node is unaware of. This method of handling orphans is problematic for two reasons: it requires nodes to allocate memory for unvalidated data received on the p2p network and it relies on txid-based relay between two wtxid-relay peers. This proposal makes orphan resolution more efficient and no longer require txid-based relay. ==Definitions== Given any two transactions Tx0 and Tx1 where Tx1 spends an output of Tx0, Tx0 is a '''parent''' of Tx1 and Tx1 is a '''child''' of Tx0. A transaction's '''ancestors''' include, recursively, its parents, the parents of its parents, etc. A transaction's '''descendants''' include, recursively, its children, the children of its children, etc. A transaction's parent is its ancestor, but an ancestor is not necessarily a parent. A '''package''' is a list of transactions, representable by a connected Directed Acyclic Graph (a directed edge exists between a transaction that spends the output of another transaction). In this proposal, a package is limited to unconfirmed transactions. An '''ancestor package''' consists of an unconfirmed transaction with all of its unconfirmed ancestors. In a '''topologically sorted''' package, each parent appears somewhere in the list before its child. ==Specification== Ancestor Package Relay includes two parts: a package information round and a transaction data download round. The package information round is used to help a receiver learn what transactions are in a package and decide whether they want to download them. The transaction data round is used to help a node download multiple transactions in one message instead of as separate messages. '''Why are package information and transaction data rounds both necessary?''' Several alternative designs were considered. One should measure alternative solutions based on the resources used to communicate (not necessarily trustworthy) information: We would like to minimize network bandwidth, avoid downloading a transaction more than once, avoid downloading transactions that are eventually rejected, and minimize storage allocated for not-yet-validated transactions.
'''No Package Information Round:''' One proposal is to just use the child's wtxid to refer to the package and always send the entire package together, skipping the package information round. However, this protocol would make it very likely for honest nodes to redownload duplicate transactions. See the following example, where the high-feerate ancestors were already downloaded and accepted individually. [[File:./bip-0331/no_package_info.png|600px]]
'''Package Information Only:''' Just having package information gives enough information for the receiver to accept the packages. That is, rather than using "getpkgtxns" and "pkgtxns" messages, send "getdata" and download the transactions individually. While this option is a potential fallback if batched transaction download fails for some reason, it shouldn't be used as the default because it always requires storage of unvalidated transactions. [[File:./bip-0331/package_info_only.png|1000px]]
Package relay is negotiated between two peers during the version handshake using a "sendpackages" message. The versions field within "sendpackages" is interpreted as a bitfield; peers may relay multiple versions of packages. Package relay requires both peers to support wtxid-based relay because package transactions are referenced by their wtxids. '''Why do we need multiple versions? Why can't we just support arbitrary packages?''' Attempting to support arbitrary packages in mempool validation may result in very complex logic, new Denial of Service attack vectors, and policy limitations that could be leveraged to censor transactions (aka "pinning attacks"). This protocol is extensible to support other types of packages based on future desired use cases. Future package information messages may describe different types of packages and/or contain more information than a list of wtxids, e.g. feerate or relationships between transactions. '''Why use a bitfield instead of a numbering system?''' It should be possible to support some subset of the existing package types. [[File:./bip-0331/version_negotiation.png|400px]] Nodes indicate support for batched transaction data round ("getpkgtxns", "pkgtxns", and "MSG_PKGTXNS") using the PKG_RELAY_PKGTXNS = (1 << 0) bit in their "sendpackages" messages during version handshake. They indicate support for the ancestor package information round ("ancpkginfo", "MSG_ANCPKGINFO") using the PKG_RELAY_ANC = (1 << 1) bit in their "sendpackages" messages during version handshake. ===Protocol Flow Examples=== This package relay protocol satisfies both use cases (orphan transaction handling and high-feerate transaction paying for low-feerate ancestors). ====Orphan Transaction Handling==== Upon receiving an orphan transaction, a node may request ancestor package information delineating the wtxids of the transaction's unconfirmed ancestors. This is done without using txid-based relay. The package information can be used to request transaction data. As these transactions are dependent upon one another to be valid, the transactions can be requested and sent as a batch. Contrast this protocol with legacy orphan handling, which requires requesting the missing transactions by their txids and may require new round trips for each generation of missing parents. [[File:./bip-0331/orphan_handling_flow.png|1000px]] ====Fee-Bumped Transactions==== Too-low-feerate transactions (i.e. below the node's minimum mempool feerate) with high-feerate descendants can also be relayed this way. If the peers are using BIP133 fee filters and a low-feerate transaction is below the node's fee filter, the sender will not announce it. The high-feerate transaction will be sent by the sender, and received and handled as an orphan by the receiver, the transactions are validated as a package, and so the protocol naturally works for this use case. This does not mean BIP133 is required for package relay to work, provided that nodes do not immediately reject transactions previously found to be too low feerate. If the low-feerate transaction was sent and rejected, the receiver should later re-request and accept it after learning that it is the ancestor of another transaction, and that they meet the receiver's mempool policy requirements when validated together. [[File:./bip-0331/package_cpfp_flow.png|600px]] This protocol is receiver-initiated only; nodes do not proactively announce packages to their peers. '''Why no sender-initiated protocol?''' Sender-initiated package relay can, theoretically, save a round trip by notifying the receiver ahead of time that they will probably need to request and validate a group of transactions together in order for them to be accepted. As with any proactive communication, there is a chance that the receiver already knows this information, so this network bandwidth may be wasted. Shortened latency is less significant than wasted bandwidth. The logic used to decide when to announce a package proactively determines whether it is a net increase or decrease for overall bandwidth usage. However, it is difficult to design anything to save bandwidth without any idea of what its bandwidth usage actually looks like in practice. No historical data is available, as one of the primary goals of this protocol is to enable currently-rejected transactions to propagate. After deploying receiver-initiated package relay, we can observe its usage and then introduce a sender-initiated package relay protocol informed by data collected from the p2p network. ===Combined Hash=== A "combined hash" serves as a unique "package id" for some list of transactions and helps provide a meaningful but short "notfound" response to "getpkgtxns." The combined hash of a package of transactions is equal to the sha256 hash of each transaction's wtxid concatenated in lexicographical order. ===New Messages=== Four new protocol messages and two inv types are added. ====sendpackages==== {| | Field Name || Type || Size || Purpose |- |versions || uint64_t || 8 || Bit field that is 64 bits wide, denoting the package versions supported by the sender. |- |} # The "sendpackages" message has the structure defined above, with pchCommand == "sendpackages". # During version handshake, nodes should send one "sendpackages" message indicating they support package relay, with the versions field indicating which versions they support. # The "sendpackages" message MUST be sent before sending a "verack" message. If a "sendpackages" message is received after "verack", the sender may be disconnected. # Upon successful connection ("verack" sent by both peers), a node may relay packages with the peer if they did not set "fRelay" to false in the "version" message, both peers sent "wtxidrelay", and both peers sent "sendpackages" for matching version bit(s). Unknown bits (including versions==0) should be ignored. Peers should relay packages corresponding to versions that both sent "sendpackages" for.'''Is it ok to send "sendpackages" to a peer that specified fRelay=false in their "version" message?''' Yes, this is allowed in order to reduce the number of negotiation steps. This means nodes can announce features without first checking what the other peer has sent, and then apply negotiation logic at the end based on what was sent and received. See [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2022-May/020510.html this discussion]. ====ancpkginfo==== {| | Field Name || Type || Size || Purpose |- |txns_length||CompactSize||1 or 3 bytes|| The number of transactions provided. |- |txns||List of wtxids||txns_length * 32|| The wtxids of each transaction in the package. |} # The "ancpkginfo" message has the structure defined above, with pchCommand == "ancpkginfo". # The "txns" field should contain a list of wtxids which constitute the ancestor package of the last wtxid. For the receiver's convenience, the sender should - but is not required to - sort the wtxids in topological order. The topological sort can be achieved by sorting the transactions by mempool acceptance order (if parents are always accepted before children). Apart from the last wtxid which is used to learn which transaction the message corresponds to, there is no enforced ordering. Nodes should not disconnect or punish a peer who provides a list not sorted in topological order.'''Why not include feerate information to help the receiver decide whether these transactions are worth downloading?''' A simple feerate is typically insufficient; the receiver must also know the dependency relationships between transactions and their respective sizes. '''Should a peer be punished if they provide incorrect package info, e.g. a list of unrelated transactions?''' Ideally, there should be a way to enforce that peers are providing correct information to each other. However, two peers may have different views of what a transaction's unconfirmed ancestors are based on their chainstate. For example, during a reorg or when two blocks are found at the same time, one peer may see a transaction as confirmed while the other peer does not. As such, it is impossible to accurately enforce this without also knowing the peer's chainstate. It was [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2022-May/020493.html originally proposed] to include a block hash in "ancpkginfo" to avoid unwarranted disconnections. However, it does not make much sense to stop or delay transaction data requests due to mismatched chainstates, and the chainstate may change again between package information and transaction data rounds. Instead, differences in chainstate should be handled at the validation level. The node has already spent network bandwidth downloading these transactions; it should make a best effort to validate them. See [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2022-June/020558.html discussion]. '''Why not require topological order?''' It is not possible to determine whether a list of transactions is topologically sorted without first establishing that the list contains a full ancestor package. It is not possible to determine whether a list of transactions contains a full ancestor package without knowing what the chainstate is. # Upon receipt of a "ancpkginfo" message, the node may use it to request the transactions it does not already have (e.g. using "getpkgtxns" or "tx"). # Upon receipt of a malformed "ancpkginfo" message, the sender may be disconnected. An "ancpkginfo" message is malformed if it contains duplicate wtxids or conflicting transactions (spending the same inputs). The receiver may learn that a package info was malformed after downloading the transactions. # A node MUST NOT send a "ancpkginfo" message that has not been requested by the recipient. Upon receipt of an unsolicited "ancpkginfo", a node may disconnect the sender. # This message must only be used if both peers set PKG_RELAY_ANC in their "sendpackages" message. If an "ancpkginfo" message is received from a peer with which this type of package relay was not negotiated, no response should be sent and the sender may be disconnected. ====MSG_ANCPKGINFO==== # A new inv type (MSG_ANCPKGINFO == 0x7) is added, for use only in getdata requests pertaining to ancestor packages. # As a getdata request type, it indicates that the sender wants an "ancpkginfo" containing all of the unconfirmed ancestors of a transaction, referenced by wtxid. # Upon receipt of a "getdata(MSG_ANCPKGINFO)" request, the node should respond with an "ancpkginfo" message corresponding to the transaction's unconfirmed ancestor package, or with "notfound". The wtxid of the requested transaction must be the last item in the "ancpkginfo" response list, as the last item is used to determine which transaction the "ancpkginfo" pertains to. # The inv type must only be used in a "getdata" message. An "inv(MSG_ANCPKGINFO)" must never be sent. If an "inv(MSG_ANCPKGINFO)" is received, the sender may be disconnected. # This inv type must only be used if both peers set PKG_RELAY_ANC in their "sendpackages" message. If a "getdata" message with type MSG_ANCPKGINFO is received from a peer with which this type of package relay was not negotiated, no response should be sent and the sender may be disconnected. ====getpkgtxns==== {| | Field Name || Type || Size || Purpose |- |txns_length||CompactSize||1 or 3 bytes|| The number of transactions requested. |- |txns||List of wtxids||txns_length * 32|| The wtxids of each transaction in the package. |} # The "getpkgtxns" message has the structure defined above, with pchCommand == "getpkgtxns". # A "getpkgtxns" message should be used to request some list of transactions specified by witness transaction id. It indicates that the node wants to receive either all the specified transactions or none of them. This message is intended to allow nodes to avoid downloading and storing transactions that cannot be validated without each other. The list of transactions does not need to correspond to a previously-received ancpkginfo message. # Upon receipt of a "getpkgtxns" message, a node should respond with either a "pkgtxns" containing all of the requested transactions in the same order specified in the "getpkgtxns" request or one "notfound" message of type MSG_PKGTXNS and combined hash of all of the wtxids in the "getpkgtxns" request (only one "notfound" message and nothing else), indicating one or more of the transactions is unavailable. # A "getpkgtxns" message must contain at most 100 wtxids. Upon receipt of a "getpkgtxns" message with more than 100 wtxids, a node may ignore the message (to avoid calculating the combined hash) and disconnect the sender. # This message must only be used if both peers set PKG_RELAY_PKGTXNS in their "sendpackages" message. If a "getpkgtxns" message is received from a peer with which this type of package relay was not negotiated, no response should be sent and the sender may be disconnected. ====pkgtxns==== {| | Field Name || Type || Size || Purpose |- |txns_length||CompactSize||1 or 3 bytes|| The number of transactions provided. |- |txns||List of transactions||variable|| The transactions in the package. |} # The "pkgtxns" message has the structure defined above, with pchCommand == "pkgtxns". # A "pkgtxns" message should contain the transaction data requested using "getpkgtxns". # A "pkgtxns" message should only be sent to a peer that requested the package using "getpkgtxns". If a node receives an unsolicited package, it may choose to validate the transactions or not, and the sender may be disconnected. # This message must only be used if both peers set PKG_RELAY_PKGTXNS in their "sendpackages" message. If a "pkgtxns" message is received from a peer with which this type of package relay was not negotiated, no response should be sent and the sender may be disconnected. ====MSG_PKGTXNS==== # A new inv type (MSG_PKGTXNS == 0x6) is added, for use only in "notfound" messages pertaining to package transactions. # As a "notfound" type, it indicates that the sender is unable to send all the transactions requested in a prior "getpkgtxns" message. The hash used is equal to the combined hash of the wtxids in the getpkgtxns request. # This inv type should only be used in "notfound" messages, i.e. "inv(MSG_PKGTXNS)" and "getdata(MSG_PKGTXNS)" must never be sent. Upon receipt of an "inv" or "getdata" message of this type, the sender may be disconnected. # This inv type must only be used if both peers set PKG_RELAY_PKGTXNS in their "sendpackages" message. ==Compatibility== Older clients remain fully compatible and interoperable after this change. Clients implementing this protocol will only attempt to send and request packages if agreed upon during the version handshake. '''Will package relay cause non-package relay nodes to waste bandwidth on low-feerate transactions?''' If a node supports package relay, it may accept low-feerate transactions (e.g. paying zero fees) into its mempool, but non-package relay nodes would most likely reject them. To mitigate bandwidth waste, a package relay node should not announce descendants of below-fee-filter transactions to non-package relay peers. '''Is Package Erlay possible?''' A client using BIP330 reconciliation-based transaction relay (Erlay) is able to use package relay without interference. After reconciliation, any transaction with unconfirmed ancestors may have those ancestors resolved using ancestor package relay. [[File:./bip-0331/package_erlay.png|700px]] ==Extensibility== This protocol can be extended to include more types of package information in the future, while continuing to use the same messages for transaction data download. One would define a new package information message (named "*pkginfo" in the diagram below), allocate its corresponding inv type (named "*PKGINFO" in the diagram below), and specify how to signal support using the versions field of "sendpackages" (an additional bit named "PKG_RELAY_*" in the diagram below). A future version of package relay may allow a sender-initiated dialogue by specifying that the package info type inv type can be used in an "inv" message.
[[File:./bip-0331/sender_init_future_version.png|700px]] ==Implementation== Sample implementation for Bitcoin Core: https://github.com/bitcoin/bitcoin/pull/27742 A prerequisite for implementing a safe package relay protocol is a mempool acceptance policy that safely validates packages of transactions. '''Package Mempool Acceptance Policy''' Accepting packages from peers should not significantly increase a node's DoS attack surface; processing packages should not permit waste or exhaustion of the node and network's resources. Additionally, a sensible mempool acceptance policy should result in the most incentive-compatible subset of the package in the mempool in order to avoid adding more pinning attacks or censorship vectors. For example, It should not be assumed that packages are CPFPs. An ancestor package may include a high-feerate parent and low-feerate child; the policy may choose to accept the parent but not the child. If one or more transactions are policy-invalid, other transactions that are not dependent upon them should still be considered. ==Acknowledgements== Thank you to Suhas Daftuar, John Newbery, Anthony Towns, Martin Zumsande, and others for input on the design. Thank you to Will Clark, Sergi Delgado, Fabian Jahr, John Newbery, Greg Sanders, Stéphan Vuylsteke, Pieter Wuille, and others for input on this document. Much of this work is inspired by ideas and code by Suhas Daftuar and Antoine Riard. '''Prior Work on Package Relay''' * [https://gist.github.com/sdaftuar/8756699bfcad4d3806ba9f3396d4e66a Strawman Proposal] * [https://github.com/bitcoin/bitcoin/issues/14895 Package relay design questions] * [https://github.com/bitcoin/bitcoin/pull/16401 Add package acceptance logic to mempool] * [https://github.com/bitcoin/bitcoin/pull/19621 [RFC] Package-relay: sender-initiated] ==References and Rationale== ================================================ FILE: bip-0337.mediawiki ================================================
  BIP: 337
  Layer: API/RPC
  Title: Compressed Transactions
  Authors: Tom Briar 
  Status: Draft
  Type: Specification
  Assigned: 2024-02-01
  License: BSD-3-Clause
  Discussion: https://github.com/bitcoin/bitcoin/pull/29134
              https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2023-August/021924.html
== Introduction == === Abstract === This document proposes a serialization scheme for compressing Bitcoin transactions. The compressed Bitcoin transactions can reach a serialized size of less than 50% of the original serialized transaction. One method for compressing involves reducing the transaction outpoints in a potentially lossy way. Therefore, it is an optional path for compression. Compressing the outpoints is necessary for compressed transactions to reach less than 70% of the original size. === Motivation === Typical Bitcoin transactions usually contain a large amount of white space and padding due to specific fields that are often one of a minimal number of possibilities. We can use this fact and a few similar methods to create an encoding for 90% of Bitcoin transactions that are roughly 25-50% smaller. There exists a working-in-progress app that allows the use of steganography to encode data in images to be passed around via various social media groups. When used in conjunction with this compression scheme and an elligator squared encryption, this would allow for a very secure and private form of broadcasting bitcoin transactions. === Rationale === The four main methods to achieve a lower transaction size are: 1. Packing transaction metadata before it and each of its inputs and outputs to determine the following data structure. 2. Replacing 32-bit numeric values with either variable-length integers (VarInts) or compact integers (CompactSizes). 3. Using compressed signatures and public key recovery upon decompression. 4. Replacing the 36-byte Outpoint txid/vout pair with a block height and index. === Backwards Compatibility === There are no concerns with backwards compatibility. === Specification === ==== Primitives ==== {| class="wikitable" style="margin:auto" |- ! Name !! Width !! Description |- | CompactSize || 1-5 Bytes || For 0-253, encode the value directly in one byte. For 254-65535, encode 254 followed by two little-endian bytes. For 65536-(2^32-1), encode 255 followed by four little-endian bytes. |- | CompactSize Flag || 2 Bits || 1, 2, or 3 indicate literal values. 0 indicates that a CompactSize encoding of the value will follow. |- | VarInt || 1+ Bytes || 7-bit little-endian encoding, with each 7-bit word encoded in a byte. The highest bit of each byte is one if more bytes follow, and 0 for the last byte. |- | VLP-Bytestream || 2+ Bytes || A VarInt Length Prefixed Bytestream. It uses the prefixed VarInt to determine the length of the following byte stream. |} ==== General Schema ==== {| class="wikitable" style="margin:auto" |- ! Name !! Width !! Description |- | Transaction metadata || 1 Bytes || Information on the structure of the transaction. See [[#transaction-metadata|Transaction Metadata]] |- | Version || 0-5 Bytes || If present according to the metadata field, a CompactSize encoding of the transaction version. |- | Input Count || 0-5 Bytes || If present according to the metadata field, a CompactSize encoding of the transaction input count. |- | Output Count || 0-5 Bytes || If present according to the metadata field, a CompactSize encoding of the transaction output count. |- | LockTime || 0-5 Bytes || If present according to the metadata field, a CompactSize encoding of the transaction LockTime. |- | Minimum Blockheight || 1-5 Bytes || If present according to the metadata field, a VarInt encoding of the minimum block height for transaction compressed inputs and LockTime. |- | Input Metadata+Output Metadata || 1+ Bytes || An encoding containing the metadata for all the inputs followed by all the outputs of the transaction. For each input, see [[#input-metadata|Input Metadata]], and for each output, see [[#output-metadata|Output Metadata]]. |- | Input Data || 66+ Bytes || See [[#input-data|Input Data]]. |- | Output Data || 3+ Bytes || See [[#output-data|Output Data]]. |} ==== Transaction Metadata ==== {| class="wikitable" style="margin:auto" |- ! Name !! Width !! Description |- | Version || 2 Bits || A CompactSize flag for the transaction version. |- | Input Count || 2 Bits || A CompactSize flag for the transaction input count. |- | Output Count || 2 Bits || A CompactSize flag for the transaction output count. |- | LockTime || 1 Bit || A boolean to indicate if the transaction has a LockTime. |- | Minimum Blockheight || 1 Bit || A boolean to indicate if the transaction minimum block height is greater than zero. |} ==== Input Metadata ==== {| class="wikitable" style="margin:auto" |- ! Name !! Width !! Description |- | Compressed Signature || 1 Bit || A Boolean to determine if this input's signature is compressed. The signature is only compressed for P2TR on a key spend and for P2SH when it is a wrapped P2SH-WPKH. |- | Standard Hash || 1 Bit || A Boolean to determine if this input's signature hash type is standard (0x00 for Taproot, 0x01 for Legacy/Segwit). |- | Standard Sequence || 2 Bits || A CompactSize flag for this input's sequence. Encode literal values as follows: 1 = 0x00000000, 2 = 0xFFFFFFFE, 3 = 0xFFFFFFFF. |- | Compressed OutPoint || 1 bit || A Boolean to determine if the input's outpoint is compressed. |} ==== Output Metadata ==== {| class="wikitable" style="margin:auto" |- ! Name !! Width !! Description |- | Encoded Script Type || 3 Bits || [[#script-type-encoding|Encoded Script Type]]. |} ==== Script Type Encoding ==== {| class="wikitable" style="margin:auto" |- ! Script Type !! Value |- | Uncompressed Custom Script || 0b000 |- | Uncompressed P2PK || 0b001 |- | Compressed P2PK || 0b010 |- | P2PKH || 0b011 |- | P2SH || 0b100 |- | P2WPKH || 0b101 |- | P2WSH || 0b110 |- | P2TR || 0b111 |} ==== Input Data ==== {| class="wikitable" style="margin:auto" |- ! Name !! Width !! Description |- | Outpoint || 2-37 Bytes || The Outpoint Txid/Vout are determined to be compressed or otherwise by the "Compressed Outpoint" Boolean in the input metadata. For each compressed outpoint see [[#compressed-outpoint|Compressed Outpoint]]. For each uncompressed outpoint see [[#uncompressed-outpoint|Uncompressed Outpoint]]. |- | Signature || 64+ Bytes || The Signature is determined to be compressed or otherwise by the output script of the previous transaction. For each compressed signature see [[#compressed-signature|Compressed Signature]]. For each uncompressed signature see [[#uncompressed-signature|Uncompressed Signature]]. |- | Sequence || 0-5 Bytes || If present due to a non-standard sequence, a VarInt encoding of the sequence. |} ==== Compressed Outpoint ==== {| class="wikitable" style="margin:auto" |- ! Name !! Width !! Description |- | Txid Block Height || 1-5 Bytes || A VarInt containing the offset from Minimum Blockheight for this Txid. |- | Txid Block Index || 1-5 Bytes || A VarInt containing the flattened index from the Txid block height for the Vout. |} ==== Uncompressed Outpoint ==== {| class="wikitable" style="margin:auto" |- ! Name !! Width !! Description |- | Txid || 32 Bytes || Contains the 32 Byte Txid. |- | Vout || 1-5 Bytes || A CompactSize Containing the Vout of the Txid. |} ==== Compressed Signature ==== {| class="wikitable" style="margin:auto" |- ! Name !! Width !! Description |- | Signature || 64 Bytes || Contains the 64 Byte signature. |- | Pubkey Hash || 0-20 Bytes || If input is P2SH-P2WPKH contains the 20 byte hash of the public key. |- | Hash Type || 0-1 Bytes || An Optional Byte containing the Hash Type if it was non-standard. |} ==== Uncompressed Signature ==== {| class="wikitable" style="margin:auto" |- ! Name !! Width !! Description |- | Signature || 2+ Bytes || A VLP-Bytestream containing the signature. |} ==== Output Data ==== {| class="wikitable" style="margin:auto" |- ! Name !! Width !! Description |- | Output Script || 2+ Bytes || A VLP-Bytestream containing the output script. |- | Amount || 1-9 Bytes || A VarInt containing the output amount. |} ==== Ideal Transaction ==== The compression scheme was designed to be optimal for a "typical" transaction, spending a few close-in-age inputs and having one or two outputs. Here are size values for such a transaction, which demonstrate the effectiveness of the compression. {| class="wikitable" style="margin:auto" |- ! Field !! Requirements !! Savings Up To |- | Version || Less than four || 30 Bits |- | Input Count || Less than four || 30 Bits |- | Output Count || Less than four || 30 Bits |- | LockTime || 0 || 30 Bits |- | Input Sequence || 0x00, 0xFFFFFFFE, or 0xFFFFFFFF || 62 Bits For Each Input |- | Input Txid || Compressed Outpoint || 23 - 31 Bytes For Each Input |- | Input Vout || Compressed Outpoint || (-1) - 3 Bytes For Each Input |- | Input Signature || Non-custom Script Signing || 40 - 72 Bytes For Each Legacy Input |- | Input Hash Type || 0x00 for Taproot, 0x01 for Legacy || 7 Bits For Each Input |- | Output Script || Non-custom Scripts || 2 - 5 Bytes For Each Output |- | Output Amount || No Restrictions || (-1) - 7 Bytes For Each Output |} === Reference Implementation === This reference implementation adds two new RPC endpoints, compressrawtransaction and decompressrawtransaction. The first accepts a raw hex-encoded transaction and returns a compact hex-encoded transaction; also included in the output is a list of warnings to help ensure there are no unexpected uncompressed values. The second accepts a compact hex transaction and returns the uncompressed raw hex-encoded transaction. https://github.com/bitcoin/bitcoin/pull/29134 === Test Vectors === ==== Taproot ==== ===== Uncompressed ===== 020000000001017ad1d0cc314504ec06f1b5c786c50cf3cda30bd5be88cf08ead571b0ce7481fb0000000000fdffffff0188130000000000001600142da377ed4978fefa043a58489912f8e28e16226201408ce65b3170d3fbc68e3b6980650514dc53565f915d14351f83050ff50c8609495b7aa96271c3c99cdac1a92b1b45e77a4a870251fc1673596793adf2494565e500000000 ===== Compressed ===== 96b1ec7f968001b0218ce65b3170d3fbc68e3b6980650514dc53565f915d14351f83050ff50c8609495b7aa96271c3c99cdac1a92b1b45e77a4a870251fc1673596793adf2494565e58efefefe7d2da377ed4978fefa043a58489912f8e28e162262a608 ==== P2WPKH ==== ===== Uncompressed ===== 0200000000010144bcf05ab48b8789268a7ca07133241ad654c0739ac7165015b2d669eadb10ea0000000000fdffffff0188130000000000001600142da377ed4978fefa043a58489912f8e28e16226202473044022043ab639a98dfbc704f16a35bf25b8b72acb4cb928fd772285f1fcf63725caa85022001c9ff354504e7024708bce61f30370c8db13da8170cef4e8e4c4cdad0f71bfe0121030072484c24705512bfb1f7f866d95f808d81d343e552bc418113e1b9a1da0eb400000000 ===== Compressed ===== 96b1ec71968001932643ab639a98dfbc704f16a35bf25b8b72acb4cb928fd772285f1fcf63725caa8501c9ff354504e7024708bce61f30370c8db13da8170cef4e8e4c4cdad0f71bfe8efefefe7d2da377ed4978fefa043a58489912f8e28e162262a608 ==== P2SH-P2WPKH ==== ===== Uncompressed ===== 0200000000010192fb2e4332b43dc9a73febba67f3b7d97ba890673cb08efde2911330f77bbdfc00000000171600147a1979232206857167b401fdac1ffbf33f8204fffdffffff0188130000000000001600142da377ed4978fefa043a58489912f8e28e16226202473044022041eb682e63c25b85a5a400b11d41cf4b9c25f309090a5f3e0b69dc15426da90402205644ddc3d5179bab49cce4bf69ebfaeab1afa34331c1a0a70be2927d2836b0e8012103c483f1b1bd24dd23b3255a68d87ef9281f9d080fd707032ccb81c1cc56c5b00200000000 ===== Compressed ===== 96b1ec7c9e8001981641eb682e63c25b85a5a400b11d41cf4b9c25f309090a5f3e0b69dc15426da9045644ddc3d5179bab49cce4bf69ebfaeab1afa34331c1a0a70be2927d2836b0e87a1979232206857167b401fdac1ffbf33f8204ff8efefefe7d2da377ed4978fefa043a58489912f8e28e162262a608 ==== P2PKH ==== ===== Uncompressed ===== 02000000015f5be26862482fe2fcc900f06ef26ee256fb205bc4773e5a402d0c1b88b82043000000006a473044022031a20f5d9212023b510599c9d53d082f8e07faaa2d51482e078f8e398cb50d770220635abd99220ad713a081c4f20b83cb3f491ed8bd032cb151a3521ed144164d9c0121027977f1b6357cead2df0a0a19570088a1eb9115468b2dfa01439493807d8f1294fdffffff0188130000000000001600142da377ed4978fefa043a58489912f8e28e16226200000000 ===== Compressed ===== 96b1ec7c968001981431a20f5d9212023b510599c9d53d082f8e07faaa2d51482e078f8e398cb50d77635abd99220ad713a081c4f20b83cb3f491ed8bd032cb151a3521ed144164d9c8efefefe7d2da377ed4978fefa043a58489912f8e28e162262a608 == Acknowledgements == Thank you to Andrew Poelstra, who helped invent and develop the ideas in the proposal and the code for reference implementation. ================================================ FILE: bip-0338.mediawiki ================================================
  BIP: 338
  Layer: Peer Services
  Title: Disable transaction relay message
  Authors: Suhas Daftuar 
  Status: Closed
  Type: Specification
  Assigned: 2020-09-03
  License: BSD-2-Clause
==Abstract== This BIP describes a change to the p2p protocol to allow a node to tell a peer that a connection will not be used for transaction relay, to support block-relay-only connections that are currently in use on the network. ==Motivation== This proposal is part of an effort to increase the number of inbound connections that a peer can service, by distinguishing peers which will not relay transactions from those that do. Since 2019, software has been deployed[1] which initiates connections on the Bitcoin network and sets the transaction relay field (introduced by BIP 37 and also defined in BIP 60) to false, to prevent transaction relay from occurring on the connection. Additionally, addr messages received from the peer are ignored by this software. The purpose of these connections is two-fold: by making additional low-bandwidth connections on which blocks can propagate, the robustness of a node to network partitioning attacks is strengthened. Additionally, by not relaying transactions and ignoring received addresses, the ability of an adversary to learn the complete network graph (or a subgraph) is reduced[2], which in turn increases the cost or difficulty to an attacker seeking to carry out a network partitioning attack (when compared with having such knowledge). The low-bandwidth / minimal-resource nature of these connections is currently known only by the initiator of the connection; this is because the transaction relay field in the version message is not a permanent setting for the lifetime of the connection. Consequently, a node receiving an inbound connection with transaction relay disabled cannot distinguish between a peer that will never enable transaction relay (as described in BIP 37) and one that will. Moreover, the node also cannot determine that the incoming connection will ignore relayed addresses; with that knowledge a node would likely choose other peers to receive announced addresses instead. This proposal adds a new, optional message that a node can send a peer when initiating a connection to that peer, to indicate that connection should not be used for transaction relay for the connection's lifetime. In addition, without a current mechanism to negotiate whether addresses should be relayed on a connection, this BIP suggests that address messages not be sent on links where transaction relay has been disabled. After this BIP is deployed, nodes could more easily implement inbound connection limiting that differentiates low-resource nodes (such as those sending disabletx) from full-relay peers, potentially allowing for an increase in the number of block-relay-only connections that can be made on the network. ==Specification== # A new disabletx message is added, which is defined as an empty message with message type set to "disabletx". # The protocol version of nodes implementing this BIP must be set to 70017 or higher. # If a node sets the transaction relay field in the version message to a peer to false, then the disabletx message MAY also be sent in response to a version message from that peer if the peer's protocol version is >= 70017. If sent, the disabletx message MUST be sent prior to sending a verack. # A node MUST NOT send the disabletx message if the transaction relay field in the version message is omitted or set to true. # A node that has sent or received a disabletx message to/from a peer MUST NOT send any of these messages to the peer: ## inv messages for transactions ## notfound messages for transactions ## getdata messages for transactions ## getdata messages for merkleblock (BIP 37) ## filteradd/filterload/filterclear (BIP 37) ## feefilter (BIP 133) ## mempool (BIP 35) ## tx message # It is RECOMMENDED that a node that has sent or received a disabletx message to/from a peer not send any of these messages to the peer: ## addr/getaddr ## addrv2 (BIP 155) # The behavior regarding sending or processing other message types is not specified by this BIP. # Nodes MAY decide to not remain connected to peers that send this message (for example, if trying to find a peer that will relay transactions). ==Compatibility== Nodes with protocol version >= 70017 that do not implement this BIP, and nodes with protocol version < 70017, will continue to remain compatible with implementing software: transactions would not be relayed to peers sending the disabletx message (provided that BIP 37 or BIP 60 has been implemented), and while periodic address relay may still take place, software implementing this BIP should not be disconnecting such peers solely for that reason. Disabling address relay is suggested but not required by this BIP, to allow for future protocol extensions that might specify more carefully how address relay is to be negotiated. This BIP's recommendations for software to not relay addresses is intended to be interpreted as guidance in the absence of any such future protocol extension, to accommodate existing software behavior. Note that all messages specified in BIP 152, including blocktxn and getblocktxn, are permitted between peers that have sent/received a disabletx message, subject to the feature negotiation of BIP 152. This proposal is compatible with, but independent of, BIP 37. ==Implementation== https://github.com/bitcoin/bitcoin/pull/20726 ==References== # Bitcoin Core has [https://github.com/bitcoin/bitcoin/pull/15759 implemented this functionality] since version 0.19.0.1, released in November 2019. # For example, see https://www.cs.umd.edu/projects/coinscope/coinscope.pdf and https://arxiv.org/pdf/1812.00942.pdf. ==Copyright== This BIP is licensed under the 2-clause BSD license. ================================================ FILE: bip-0339.mediawiki ================================================
  BIP: 339
  Layer: Peer Services
  Title: WTXID-based transaction relay
  Authors: Suhas Daftuar 
  Status: Deployed
  Type: Specification
  Assigned: 2020-02-03
  License: BSD-2-Clause
==Abstract== This BIP describes two changes to the p2p protocol to support transaction relay based on the BIP 141 wtxid of a transaction, rather than its txid. ==Motivation== Historically, the inv messages sent on the Bitcoin peer-to-peer network to announce transactions refer to transactions by their txid, which is a hash of the transaction that does not include the witness (see BIP 141). This has been the case even since Segregated Witness (BIP 141/143/144) has been adopted by the network. Not committing to the witness in transaction announcements creates inefficiencies: because a transaction's witness can be malleated without altering the txid, a node in receipt of a witness transaction that the node does not accept will generally still download that same transaction when announced by other peers. This is because the alternative -- of not downloading a given txid after rejecting a transaction with that txid -- would allow a third party to interfere with transaction relay by malleating a transaction's witness and announcing the resulting invalid transaction to nodes, preventing relay of the valid version of the transaction as well. We can eliminate this concern by using the wtxid in place of the txid when announcing and fetching transactions. ==Specification== # A new wtxidrelay message is added, which is defined as an empty message where pchCommand == "wtxidrelay". # The protocol version of nodes implementing this BIP must be set to 70016 or higher. # The wtxidrelay message MUST be sent in response to a version message from a peer whose protocol version is >= 70016 and prior to sending a verack. A wtxidrelay message received after a verack message MUST be ignored or treated as invalid. # A new inv type MSG_WTX (0x00000005) is added, for use in both inv messages and getdata requests, indicating that the hash being referenced is a transaction's wtxid. In the case of getdata requests, MSG_WTX implies that the transaction being requested should be serialized with witness as well, as described in BIP 144. # After a node has received a wtxidrelay message from a peer, the node MUST use the MSG_WTX inv type when announcing transactions to that peer. # After a node has received a wtxidrelay message from a peer, the node SHOULD use a MSG_WTX getdata message to request any announced transactions. A node MAY still request transactions from that peer using MSG_TX getdata messages, such as for transactions not recently announced by that peer (like the parents of recently announced transactions). ==Backward compatibility== As wtxid-based transaction relay is only enabled between peers that both support it, older clients remain fully compatible and interoperable after this change. ==Implementation== https://github.com/bitcoin/bitcoin/pull/18044 ==Copyright== This BIP is licensed under the 2-clause BSD license. ================================================ FILE: bip-0340/LICENSE ================================================ BSD-2-Clause OR MIT OR CC0-1.0 The contents of this directory are provided under one of the following sets of terms, at your choice: - The BSD-2-Clause License https://opensource.org/license/BSD-2-Clause - The MIT License https://opensource.org/license/MIT - CC0 1.0 https://creativecommons.org/publicdomain/zero/1.0/ ================================================ FILE: bip-0340/reference.py ================================================ from typing import Tuple, Optional, Any import hashlib # Set DEBUG to True to get a detailed debug output including # intermediate values during key generation, signing, and # verification. This is implemented via calls to the # debug_print_vars() function. # # If you want to print values on an individual basis, use # the pretty() function, e.g., print(pretty(foo)). DEBUG = False p = 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEFFFFFC2F n = 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141 # Points are tuples of X and Y coordinates and the point at infinity is # represented by the None keyword. G = (0x79BE667EF9DCBBAC55A06295CE870B07029BFCDB2DCE28D959F2815B16F81798, 0x483ADA7726A3C4655DA4FBFC0E1108A8FD17B448A68554199C47D08FFB10D4B8) Point = Tuple[int, int] # This implementation can be sped up by storing the midstate after hashing # tag_hash instead of rehashing it all the time. def tagged_hash(tag: str, msg: bytes) -> bytes: tag_hash = hashlib.sha256(tag.encode()).digest() return hashlib.sha256(tag_hash + tag_hash + msg).digest() def is_infinite(P: Optional[Point]) -> bool: return P is None def x(P: Point) -> int: assert not is_infinite(P) return P[0] def y(P: Point) -> int: assert not is_infinite(P) return P[1] def point_add(P1: Optional[Point], P2: Optional[Point]) -> Optional[Point]: if P1 is None: return P2 if P2 is None: return P1 if (x(P1) == x(P2)) and (y(P1) != y(P2)): return None if P1 == P2: lam = (3 * x(P1) * x(P1) * pow(2 * y(P1), p - 2, p)) % p else: lam = ((y(P2) - y(P1)) * pow(x(P2) - x(P1), p - 2, p)) % p x3 = (lam * lam - x(P1) - x(P2)) % p return (x3, (lam * (x(P1) - x3) - y(P1)) % p) def point_mul(P: Optional[Point], n: int) -> Optional[Point]: R = None for i in range(256): if (n >> i) & 1: R = point_add(R, P) P = point_add(P, P) return R def bytes_from_int(x: int) -> bytes: return x.to_bytes(32, byteorder="big") def bytes_from_point(P: Point) -> bytes: return bytes_from_int(x(P)) def xor_bytes(b0: bytes, b1: bytes) -> bytes: return bytes(x ^ y for (x, y) in zip(b0, b1)) def lift_x(x: int) -> Optional[Point]: if x >= p: return None y_sq = (pow(x, 3, p) + 7) % p y = pow(y_sq, (p + 1) // 4, p) if pow(y, 2, p) != y_sq: return None return (x, y if y & 1 == 0 else p-y) def int_from_bytes(b: bytes) -> int: return int.from_bytes(b, byteorder="big") def hash_sha256(b: bytes) -> bytes: return hashlib.sha256(b).digest() def has_even_y(P: Point) -> bool: assert not is_infinite(P) return y(P) % 2 == 0 def pubkey_gen(seckey: bytes) -> bytes: d0 = int_from_bytes(seckey) if not (1 <= d0 <= n - 1): raise ValueError('The secret key must be an integer in the range 1..n-1.') P = point_mul(G, d0) assert P is not None return bytes_from_point(P) def schnorr_sign(msg: bytes, seckey: bytes, aux_rand: bytes) -> bytes: d0 = int_from_bytes(seckey) if not (1 <= d0 <= n - 1): raise ValueError('The secret key must be an integer in the range 1..n-1.') if len(aux_rand) != 32: raise ValueError('aux_rand must be 32 bytes instead of %i.' % len(aux_rand)) P = point_mul(G, d0) assert P is not None d = d0 if has_even_y(P) else n - d0 t = xor_bytes(bytes_from_int(d), tagged_hash("BIP0340/aux", aux_rand)) k0 = int_from_bytes(tagged_hash("BIP0340/nonce", t + bytes_from_point(P) + msg)) % n if k0 == 0: raise RuntimeError('Failure. This happens only with negligible probability.') R = point_mul(G, k0) assert R is not None k = n - k0 if not has_even_y(R) else k0 e = int_from_bytes(tagged_hash("BIP0340/challenge", bytes_from_point(R) + bytes_from_point(P) + msg)) % n sig = bytes_from_point(R) + bytes_from_int((k + e * d) % n) debug_print_vars() if not schnorr_verify(msg, bytes_from_point(P), sig): raise RuntimeError('The created signature does not pass verification.') return sig def schnorr_verify(msg: bytes, pubkey: bytes, sig: bytes) -> bool: if len(pubkey) != 32: raise ValueError('The public key must be a 32-byte array.') if len(sig) != 64: raise ValueError('The signature must be a 64-byte array.') P = lift_x(int_from_bytes(pubkey)) r = int_from_bytes(sig[0:32]) s = int_from_bytes(sig[32:64]) if (P is None) or (r >= p) or (s >= n): debug_print_vars() return False e = int_from_bytes(tagged_hash("BIP0340/challenge", sig[0:32] + pubkey + msg)) % n R = point_add(point_mul(G, s), point_mul(P, n - e)) if (R is None) or (not has_even_y(R)) or (x(R) != r): debug_print_vars() return False debug_print_vars() return True # # The following code is only used to verify the test vectors. # import csv import os import sys def test_vectors() -> bool: all_passed = True with open(os.path.join(sys.path[0], 'test-vectors.csv'), newline='') as csvfile: reader = csv.reader(csvfile) reader.__next__() for row in reader: (index, seckey_hex, pubkey_hex, aux_rand_hex, msg_hex, sig_hex, result_str, comment) = row pubkey = bytes.fromhex(pubkey_hex) msg = bytes.fromhex(msg_hex) sig = bytes.fromhex(sig_hex) result = result_str == 'TRUE' print('\nTest vector', ('#' + index).rjust(3, ' ') + ':') if seckey_hex != '': seckey = bytes.fromhex(seckey_hex) pubkey_actual = pubkey_gen(seckey) if pubkey != pubkey_actual: print(' * Failed key generation.') print(' Expected key:', pubkey.hex().upper()) print(' Actual key:', pubkey_actual.hex().upper()) all_passed = False aux_rand = bytes.fromhex(aux_rand_hex) try: sig_actual = schnorr_sign(msg, seckey, aux_rand) if sig == sig_actual: print(' * Passed signing test.') else: print(' * Failed signing test.') print(' Expected signature:', sig.hex().upper()) print(' Actual signature:', sig_actual.hex().upper()) all_passed = False except RuntimeError as e: print(' * Signing test raised exception:', e) all_passed = False result_actual = schnorr_verify(msg, pubkey, sig) if result == result_actual: print(' * Passed verification test.') else: print(' * Failed verification test.') print(' Expected verification result:', result) print(' Actual verification result:', result_actual) if comment: print(' Comment:', comment) all_passed = False print() if all_passed: print('All test vectors passed.') else: print('Some test vectors failed.') return all_passed # # The following code is only used for debugging # import inspect def pretty(v: Any) -> Any: if isinstance(v, bytes): return '0x' + v.hex() if isinstance(v, int): return pretty(bytes_from_int(v)) if isinstance(v, tuple): return tuple(map(pretty, v)) return v def debug_print_vars() -> None: if DEBUG: current_frame = inspect.currentframe() assert current_frame is not None frame = current_frame.f_back assert frame is not None print(' Variables in function ', frame.f_code.co_name, ' at line ', frame.f_lineno, ':', sep='') for var_name, var_val in frame.f_locals.items(): print(' ' + var_name.rjust(11, ' '), '==', pretty(var_val)) if __name__ == '__main__': test_vectors() ================================================ FILE: bip-0340/test-vectors.csv ================================================ index,secret key,public key,aux_rand,message,signature,verification result,comment 0,0000000000000000000000000000000000000000000000000000000000000003,F9308A019258C31049344F85F89D5229B531C845836F99B08601F113BCE036F9,0000000000000000000000000000000000000000000000000000000000000000,0000000000000000000000000000000000000000000000000000000000000000,E907831F80848D1069A5371B402410364BDF1C5F8307B0084C55F1CE2DCA821525F66A4A85EA8B71E482A74F382D2CE5EBEEE8FDB2172F477DF4900D310536C0,TRUE, 1,B7E151628AED2A6ABF7158809CF4F3C762E7160F38B4DA56A784D9045190CFEF,DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA659,0000000000000000000000000000000000000000000000000000000000000001,243F6A8885A308D313198A2E03707344A4093822299F31D0082EFA98EC4E6C89,6896BD60EEAE296DB48A229FF71DFE071BDE413E6D43F917DC8DCF8C78DE33418906D11AC976ABCCB20B091292BFF4EA897EFCB639EA871CFA95F6DE339E4B0A,TRUE, 2,C90FDAA22168C234C4C6628B80DC1CD129024E088A67CC74020BBEA63B14E5C9,DD308AFEC5777E13121FA72B9CC1B7CC0139715309B086C960E18FD969774EB8,C87AA53824B4D7AE2EB035A2B5BBBCCC080E76CDC6D1692C4B0B62D798E6D906,7E2D58D8B3BCDF1ABADEC7829054F90DDA9805AAB56C77333024B9D0A508B75C,5831AAEED7B44BB74E5EAB94BA9D4294C49BCF2A60728D8B4C200F50DD313C1BAB745879A5AD954A72C45A91C3A51D3C7ADEA98D82F8481E0E1E03674A6F3FB7,TRUE, 3,0B432B2677937381AEF05BB02A66ECD012773062CF3FA2549E44F58ED2401710,25D1DFF95105F5253C4022F628A996AD3A0D95FBF21D468A1B33F8C160D8F517,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF,7EB0509757E246F19449885651611CB965ECC1A187DD51B64FDA1EDC9637D5EC97582B9CB13DB3933705B32BA982AF5AF25FD78881EBB32771FC5922EFC66EA3,TRUE,test fails if msg is reduced modulo p or n 4,,D69C3509BB99E412E68B0FE8544E72837DFA30746D8BE2AA65975F29D22DC7B9,,4DF3C3F68FCC83B27E9D42C90431A72499F17875C81A599B566C9889B9696703,00000000000000000000003B78CE563F89A0ED9414F5AA28AD0D96D6795F9C6376AFB1548AF603B3EB45C9F8207DEE1060CB71C04E80F593060B07D28308D7F4,TRUE, 5,,EEFDEA4CDB677750A420FEE807EACF21EB9898AE79B9768766E4FAA04A2D4A34,,243F6A8885A308D313198A2E03707344A4093822299F31D0082EFA98EC4E6C89,6CFF5C3BA86C69EA4B7376F31A9BCB4F74C1976089B2D9963DA2E5543E17776969E89B4C5564D00349106B8497785DD7D1D713A8AE82B32FA79D5F7FC407D39B,FALSE,public key not on the curve 6,,DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA659,,243F6A8885A308D313198A2E03707344A4093822299F31D0082EFA98EC4E6C89,FFF97BD5755EEEA420453A14355235D382F6472F8568A18B2F057A14602975563CC27944640AC607CD107AE10923D9EF7A73C643E166BE5EBEAFA34B1AC553E2,FALSE,has_even_y(R) is false 7,,DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA659,,243F6A8885A308D313198A2E03707344A4093822299F31D0082EFA98EC4E6C89,1FA62E331EDBC21C394792D2AB1100A7B432B013DF3F6FF4F99FCB33E0E1515F28890B3EDB6E7189B630448B515CE4F8622A954CFE545735AAEA5134FCCDB2BD,FALSE,negated message 8,,DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA659,,243F6A8885A308D313198A2E03707344A4093822299F31D0082EFA98EC4E6C89,6CFF5C3BA86C69EA4B7376F31A9BCB4F74C1976089B2D9963DA2E5543E177769961764B3AA9B2FFCB6EF947B6887A226E8D7C93E00C5ED0C1834FF0D0C2E6DA6,FALSE,negated s value 9,,DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA659,,243F6A8885A308D313198A2E03707344A4093822299F31D0082EFA98EC4E6C89,0000000000000000000000000000000000000000000000000000000000000000123DDA8328AF9C23A94C1FEECFD123BA4FB73476F0D594DCB65C6425BD186051,FALSE,sG - eP is infinite. Test fails in single verification if has_even_y(inf) is defined as true and x(inf) as 0 10,,DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA659,,243F6A8885A308D313198A2E03707344A4093822299F31D0082EFA98EC4E6C89,00000000000000000000000000000000000000000000000000000000000000017615FBAF5AE28864013C099742DEADB4DBA87F11AC6754F93780D5A1837CF197,FALSE,sG - eP is infinite. Test fails in single verification if has_even_y(inf) is defined as true and x(inf) as 1 11,,DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA659,,243F6A8885A308D313198A2E03707344A4093822299F31D0082EFA98EC4E6C89,4A298DACAE57395A15D0795DDBFD1DCB564DA82B0F269BC70A74F8220429BA1D69E89B4C5564D00349106B8497785DD7D1D713A8AE82B32FA79D5F7FC407D39B,FALSE,sig[0:32] is not an X coordinate on the curve 12,,DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA659,,243F6A8885A308D313198A2E03707344A4093822299F31D0082EFA98EC4E6C89,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEFFFFFC2F69E89B4C5564D00349106B8497785DD7D1D713A8AE82B32FA79D5F7FC407D39B,FALSE,sig[0:32] is equal to field size 13,,DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA659,,243F6A8885A308D313198A2E03707344A4093822299F31D0082EFA98EC4E6C89,6CFF5C3BA86C69EA4B7376F31A9BCB4F74C1976089B2D9963DA2E5543E177769FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141,FALSE,sig[32:64] is equal to curve order 14,,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEFFFFFC30,,243F6A8885A308D313198A2E03707344A4093822299F31D0082EFA98EC4E6C89,6CFF5C3BA86C69EA4B7376F31A9BCB4F74C1976089B2D9963DA2E5543E17776969E89B4C5564D00349106B8497785DD7D1D713A8AE82B32FA79D5F7FC407D39B,FALSE,public key is not a valid X coordinate because it exceeds the field size 15,0340034003400340034003400340034003400340034003400340034003400340,778CAA53B4393AC467774D09497A87224BF9FAB6F6E68B23086497324D6FD117,0000000000000000000000000000000000000000000000000000000000000000,,71535DB165ECD9FBBC046E5FFAEA61186BB6AD436732FCCC25291A55895464CF6069CE26BF03466228F19A3A62DB8A649F2D560FAC652827D1AF0574E427AB63,TRUE,message of size 0 (added 2022-12) 16,0340034003400340034003400340034003400340034003400340034003400340,778CAA53B4393AC467774D09497A87224BF9FAB6F6E68B23086497324D6FD117,0000000000000000000000000000000000000000000000000000000000000000,11,08A20A0AFEF64124649232E0693C583AB1B9934AE63B4C3511F3AE1134C6A303EA3173BFEA6683BD101FA5AA5DBC1996FE7CACFC5A577D33EC14564CEC2BACBF,TRUE,message of size 1 (added 2022-12) 17,0340034003400340034003400340034003400340034003400340034003400340,778CAA53B4393AC467774D09497A87224BF9FAB6F6E68B23086497324D6FD117,0000000000000000000000000000000000000000000000000000000000000000,0102030405060708090A0B0C0D0E0F1011,5130F39A4059B43BC7CAC09A19ECE52B5D8699D1A71E3C52DA9AFDB6B50AC370C4A482B77BF960F8681540E25B6771ECE1E5A37FD80E5A51897C5566A97EA5A5,TRUE,message of size 17 (added 2022-12) 18,0340034003400340034003400340034003400340034003400340034003400340,778CAA53B4393AC467774D09497A87224BF9FAB6F6E68B23086497324D6FD117,0000000000000000000000000000000000000000000000000000000000000000,99999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999,403B12B0D8555A344175EA7EC746566303321E5DBFA8BE6F091635163ECA79A8585ED3E3170807E7C03B720FC54C7B23897FCBA0E9D0B4A06894CFD249F22367,TRUE,message of size 100 (added 2022-12) ================================================ FILE: bip-0340/test-vectors.py ================================================ import sys from reference import * def is_square(x): return int(pow(x, (p - 1) // 2, p)) == 1 def has_square_y(P): """Determine if P has a square Y coordinate. Used in an earlier draft of BIP340.""" assert not is_infinite(P) return is_square(P[1]) def vector0(): seckey = bytes_from_int(3) msg = bytes_from_int(0) aux_rand = bytes_from_int(0) sig = schnorr_sign(msg, seckey, aux_rand) pubkey = pubkey_gen(seckey) # We should have at least one test vector where the seckey needs to be # negated and one where it doesn't. In this one the seckey doesn't need to # be negated. x = int_from_bytes(seckey) P = point_mul(G, x) assert(y(P) % 2 == 0) # For historical reasons (pubkey tiebreaker was squareness and not evenness) # we should have at least one test vector where the point reconstructed # from the public key has a square and one where it has a non-square Y # coordinate. In this one Y is non-square. pubkey_point = lift_x(int_from_bytes(pubkey)) assert(not has_square_y(pubkey_point)) # For historical reasons (R tiebreaker was squareness and not evenness) # we should have at least one test vector where the point reconstructed # from the R.x coordinate has a square and one where it has a non-square Y # coordinate. In this one Y is non-square. R = lift_x(int_from_bytes(sig[0:32])) assert(not has_square_y(R)) return (seckey, pubkey, aux_rand, msg, sig, "TRUE", None) def vector1(): seckey = bytes_from_int(0xB7E151628AED2A6ABF7158809CF4F3C762E7160F38B4DA56A784D9045190CFEF) msg = bytes_from_int(0x243F6A8885A308D313198A2E03707344A4093822299F31D0082EFA98EC4E6C89) aux_rand = bytes_from_int(1) sig = schnorr_sign(msg, seckey, aux_rand) # The point reconstructed from the R.x coordinate has a square Y coordinate. R = lift_x(int_from_bytes(sig[0:32])) assert(has_square_y(R)) return (seckey, pubkey_gen(seckey), aux_rand, msg, sig, "TRUE", None) def vector2(): seckey = bytes_from_int(0xC90FDAA22168C234C4C6628B80DC1CD129024E088A67CC74020BBEA63B14E5C9) msg = bytes_from_int(0x7E2D58D8B3BCDF1ABADEC7829054F90DDA9805AAB56C77333024B9D0A508B75C) aux_rand = bytes_from_int(0xC87AA53824B4D7AE2EB035A2B5BBBCCC080E76CDC6D1692C4B0B62D798E6D906) sig = schnorr_sign(msg, seckey, aux_rand) # The point reconstructed from the public key has a square Y coordinate. pubkey = pubkey_gen(seckey) pubkey_point = lift_x(int_from_bytes(pubkey)) assert(has_square_y(pubkey_point)) # This signature vector would not verify if the implementer checked the # evenness of the X coordinate of R instead of the Y coordinate. R = lift_x(int_from_bytes(sig[0:32])) assert(R[0] % 2 == 1) return (seckey, pubkey, aux_rand, msg, sig, "TRUE", None) def vector3(): seckey = bytes_from_int(0x0B432B2677937381AEF05BB02A66ECD012773062CF3FA2549E44F58ED2401710) # Need to negate this seckey before signing x = int_from_bytes(seckey) P = point_mul(G, x) assert(y(P) % 2 != 0) msg = bytes_from_int(0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF) aux_rand = bytes_from_int(0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF) sig = schnorr_sign(msg, seckey, aux_rand) return (seckey, pubkey_gen(seckey), aux_rand, msg, sig, "TRUE", "test fails if msg is reduced modulo p or n") # Signs with a given nonce. This can be INSECURE and is only INTENDED FOR # GENERATING TEST VECTORS. Results in an invalid signature if y(kG) is not # even. def insecure_schnorr_sign_fixed_nonce(msg, seckey0, k): if len(msg) != 32: raise ValueError('The message must be a 32-byte array.') seckey0 = int_from_bytes(seckey0) if not (1 <= seckey0 <= n - 1): raise ValueError('The secret key must be an integer in the range 1..n-1.') P = point_mul(G, seckey0) seckey = seckey0 if has_even_y(P) else n - seckey0 R = point_mul(G, k) e = int_from_bytes(tagged_hash("BIP0340/challenge", bytes_from_point(R) + bytes_from_point(P) + msg)) % n return bytes_from_point(R) + bytes_from_int((k + e * seckey) % n) # Creates a signature with a small x(R) by using k = -1/2 def vector4(): one_half = n - 0x7fffffffffffffffffffffffffffffff5d576e7357a4501ddfe92f46681b20a0 seckey = bytes_from_int(0x763758E5CBEEDEE4F7D3FC86F531C36578933228998226672F13C4F0EBE855EB) msg = bytes_from_int(0x4DF3C3F68FCC83B27E9D42C90431A72499F17875C81A599B566C9889B9696703) sig = insecure_schnorr_sign_fixed_nonce(msg, seckey, one_half) return (None, pubkey_gen(seckey), None, msg, sig, "TRUE", None) default_seckey = bytes_from_int(0xB7E151628AED2A6ABF7158809CF4F3C762E7160F38B4DA56A784D9045190CFEF) default_msg = bytes_from_int(0x243F6A8885A308D313198A2E03707344A4093822299F31D0082EFA98EC4E6C89) default_aux_rand = bytes_from_int(0xC87AA53824B4D7AE2EB035A2B5BBBCCC080E76CDC6D1692C4B0B62D798E6D906) # Public key is not on the curve def vector5(): # This creates a dummy signature that doesn't have anything to do with the # public key. seckey = default_seckey msg = default_msg sig = schnorr_sign(msg, seckey, default_aux_rand) pubkey_int = 0xEEFDEA4CDB677750A420FEE807EACF21EB9898AE79B9768766E4FAA04A2D4A34 pubkey = bytes_from_int(pubkey_int) assert(lift_x(pubkey_int) is None) return (None, pubkey, None, msg, sig, "FALSE", "public key not on the curve") def vector6(): seckey = default_seckey msg = default_msg k = 6 sig = insecure_schnorr_sign_fixed_nonce(msg, seckey, k) # Y coordinate of R is not even R = point_mul(G, k) assert(not has_even_y(R)) return (None, pubkey_gen(seckey), None, msg, sig, "FALSE", "has_even_y(R) is false") def vector7(): seckey = default_seckey msg = int_from_bytes(default_msg) neg_msg = bytes_from_int(n - msg) sig = schnorr_sign(neg_msg, seckey, default_aux_rand) return (None, pubkey_gen(seckey), None, bytes_from_int(msg), sig, "FALSE", "negated message") def vector8(): seckey = default_seckey msg = default_msg sig = schnorr_sign(msg, seckey, default_aux_rand) sig = sig[0:32] + bytes_from_int(n - int_from_bytes(sig[32:64])) return (None, pubkey_gen(seckey), None, msg, sig, "FALSE", "negated s value") def bytes_from_point_inf0(P): if P == None: return bytes_from_int(0) return bytes_from_int(P[0]) def vector9(): seckey = default_seckey msg = default_msg # Override bytes_from_point in schnorr_sign to allow creating a signature # with k = 0. k = 0 bytes_from_point_tmp = bytes_from_point.__code__ bytes_from_point.__code__ = bytes_from_point_inf0.__code__ sig = insecure_schnorr_sign_fixed_nonce(msg, seckey, k) bytes_from_point.__code__ = bytes_from_point_tmp return (None, pubkey_gen(seckey), None, msg, sig, "FALSE", "sG - eP is infinite. Test fails in single verification if has_even_y(inf) is defined as true and x(inf) as 0") def bytes_from_point_inf1(P): if P == None: return bytes_from_int(1) return bytes_from_int(P[0]) def vector10(): seckey = default_seckey msg = default_msg # Override bytes_from_point in schnorr_sign to allow creating a signature # with k = 0. k = 0 bytes_from_point_tmp = bytes_from_point.__code__ bytes_from_point.__code__ = bytes_from_point_inf1.__code__ sig = insecure_schnorr_sign_fixed_nonce(msg, seckey, k) bytes_from_point.__code__ = bytes_from_point_tmp return (None, pubkey_gen(seckey), None, msg, sig, "FALSE", "sG - eP is infinite. Test fails in single verification if has_even_y(inf) is defined as true and x(inf) as 1") # It's cryptographically impossible to create a test vector that fails if run # in an implementation which merely misses the check that sig[0:32] is an X # coordinate on the curve. This test vector just increases test coverage. def vector11(): seckey = default_seckey msg = default_msg sig = schnorr_sign(msg, seckey, default_aux_rand) # Replace R's X coordinate with an X coordinate that's not on the curve x_not_on_curve = 0x4A298DACAE57395A15D0795DDBFD1DCB564DA82B0F269BC70A74F8220429BA1D assert(lift_x(x_not_on_curve) is None) sig = bytes_from_int(x_not_on_curve) + sig[32:64] return (None, pubkey_gen(seckey), None, msg, sig, "FALSE", "sig[0:32] is not an X coordinate on the curve") # It's cryptographically impossible to create a test vector that fails if run # in an implementation which merely misses the check that sig[0:32] is smaller # than the field size. This test vector just increases test coverage. def vector12(): seckey = default_seckey msg = default_msg sig = schnorr_sign(msg, seckey, default_aux_rand) # Replace R's X coordinate with an X coordinate that's equal to field size sig = bytes_from_int(p) + sig[32:64] return (None, pubkey_gen(seckey), None, msg, sig, "FALSE", "sig[0:32] is equal to field size") # It's cryptographically impossible to create a test vector that fails if run # in an implementation which merely misses the check that sig[32:64] is smaller # than the curve order. This test vector just increases test coverage. def vector13(): seckey = default_seckey msg = default_msg sig = schnorr_sign(msg, seckey, default_aux_rand) # Replace s with a number that's equal to the curve order sig = sig[0:32] + bytes_from_int(n) return (None, pubkey_gen(seckey), None, msg, sig, "FALSE", "sig[32:64] is equal to curve order") # Test out of range pubkey # It's cryptographically impossible to create a test vector that fails if run # in an implementation which accepts out of range pubkeys because we can't find # a secret key for such a public key and therefore can not create a signature. # This test vector just increases test coverage. def vector14(): # This creates a dummy signature that doesn't have anything to do with the # public key. seckey = default_seckey msg = default_msg sig = schnorr_sign(msg, seckey, default_aux_rand) pubkey_int = p + 1 pubkey = bytes_from_int(pubkey_int) assert(lift_x(pubkey_int) is None) # If an implementation would reduce a given public key modulo p then the # pubkey would be valid assert(lift_x(pubkey_int % p) is not None) return (None, pubkey, None, msg, sig, "FALSE", "public key is not a valid X coordinate because it exceeds the field size") def varlen_vector(msg_int): seckey = bytes_from_int(int(16 * "0340", 16)) pubkey = pubkey_gen(seckey) aux_rand = bytes_from_int(0) msg = msg_int.to_bytes((msg_int.bit_length() + 7) // 8, "big") sig = schnorr_sign(msg, seckey, aux_rand) comment = "message of size %d (added 2022-12)" return (seckey, pubkey, aux_rand, msg, sig, "TRUE", comment % len(msg)) vector15 = lambda : varlen_vector(0) vector16 = lambda : varlen_vector(0x11) vector17 = lambda : varlen_vector(0x0102030405060708090A0B0C0D0E0F1011) vector18 = lambda : varlen_vector(int(100 * "99", 16)) vectors = [ vector0(), vector1(), vector2(), vector3(), vector4(), vector5(), vector6(), vector7(), vector8(), vector9(), vector10(), vector11(), vector12(), vector13(), vector14(), vector15(), vector16(), vector17(), vector18(), ] # Converts the byte strings of a test vector into hex strings def bytes_to_hex(seckey, pubkey, aux_rand, msg, sig, result, comment): return (seckey.hex().upper() if seckey is not None else None, pubkey.hex().upper(), aux_rand.hex().upper() if aux_rand is not None else None, msg.hex().upper(), sig.hex().upper(), result, comment) vectors = list(map(lambda vector: bytes_to_hex(vector[0], vector[1], vector[2], vector[3], vector[4], vector[5], vector[6]), vectors)) def print_csv(vectors): writer = csv.writer(sys.stdout) writer.writerow(("index", "secret key", "public key", "aux_rand", "message", "signature", "verification result", "comment")) for (i,v) in enumerate(vectors): writer.writerow((i,)+v) print_csv(vectors) ================================================ FILE: bip-0340.mediawiki ================================================
  BIP: 340
  Title: Schnorr Signatures for secp256k1
  Authors: Pieter Wuille 
           Jonas Nick 
           Tim Ruffing 
  Comments-Summary: No comments yet.
  Comments-URI: https://github.com/bitcoin/bips/wiki/Comments:BIP-0340
  Status: Deployed
  Type: Specification
  Assigned: 2020-01-19
  License: BSD-2-Clause
  License-Code: BSD-2-Clause OR MIT OR CC0-1.0
  Discussion: 2018-07-06: https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2018-July/016203.html [bitcoin-dev] Schnorr signatures BIP
== Introduction == === Abstract === This document proposes a standard for 64-byte Schnorr signatures over the elliptic curve ''secp256k1''. === Copyright === This document is licensed under the 2-clause BSD license. === Motivation === Bitcoin has traditionally used [https://en.wikipedia.org/wiki/Elliptic_Curve_Digital_Signature_Algorithm ECDSA] signatures over the [https://www.secg.org/sec2-v2.pdf secp256k1 curve] with [https://en.wikipedia.org/wiki/SHA-2 SHA256] hashes for authenticating transactions. These are [https://www.secg.org/sec1-v2.pdf standardized], but have a number of downsides compared to [http://publikationen.ub.uni-frankfurt.de/opus4/files/4280/schnorr.pdf Schnorr signatures] over the same curve: * '''Provable security''': Schnorr signatures are provably secure. In more detail, they are ''strongly unforgeable under chosen message attack (SUF-CMA)''Informally, this means that without knowledge of the secret key but given valid signatures of arbitrary messages, it is not possible to come up with further valid signatures. [https://www.di.ens.fr/~pointche/Documents/Papers/2000_joc.pdf in the random oracle model assuming the hardness of the elliptic curve discrete logarithm problem (ECDLP)] and [http://www.neven.org/papers/schnorr.pdf in the generic group model assuming variants of preimage and second preimage resistance of the used hash function]A detailed security proof in the random oracle model, which essentially restates [https://www.di.ens.fr/~pointche/Documents/Papers/2000_joc.pdf the original security proof by Pointcheval and Stern] more explicitly, can be found in [https://eprint.iacr.org/2016/191 a paper by Kiltz, Masny and Pan]. All these security proofs assume a variant of Schnorr signatures that use ''(e,s)'' instead of ''(R,s)'' (see Design above). Since we use a unique encoding of ''R'', there is an efficiently computable bijection that maps ''(R,s)'' to ''(e,s)'', which allows to convert a successful SUF-CMA attacker for the ''(e,s)'' variant to a successful SUF-CMA attacker for the ''(R,s)'' variant (and vice-versa). Furthermore, the proofs consider a variant of Schnorr signatures without key prefixing (see Design above), but it can be verified that the proofs are also correct for the variant with key prefixing. As a result, all the aforementioned security proofs apply to the variant of Schnorr signatures proposed in this document.. In contrast, the [https://nbn-resolving.de/urn:nbn:de:hbz:294-60803 best known results for the provable security of ECDSA] rely on stronger assumptions. * '''Non-malleability''': The SUF-CMA security of Schnorr signatures implies that they are non-malleable. On the other hand, ECDSA signatures are inherently malleableIf ''(r,s)'' is a valid ECDSA signature for a given message and key, then ''(r,n-s)'' is also valid for the same message and key. If ECDSA is restricted to only permit one of the two variants (as Bitcoin does through a policy rule on the network), it can be [https://nbn-resolving.de/urn:nbn:de:hbz:294-60803 proven] non-malleable under stronger than usual assumptions.; a third party without access to the secret key can alter an existing valid signature for a given public key and message into another signature that is valid for the same key and message. This issue is discussed in [[bip-0062.mediawiki|BIP62]] and [[bip-0146.mediawiki|BIP146]]. * '''Linearity''': Schnorr signatures provide a simple and efficient method that enables multiple collaborating parties to produce a signature that is valid for the sum of their public keys. This is the building block for various higher-level constructions that improve efficiency and privacy, such as multisignatures and others (see Applications below). For all these advantages, there are virtually no disadvantages, apart from not being standardized. This document seeks to change that. As we propose a new standard, a number of improvements not specific to Schnorr signatures can be made: * '''Signature encoding''': Instead of using [https://en.wikipedia.org/wiki/X.690#DER_encoding DER]-encoding for signatures (which are variable size, and up to 72 bytes), we can use a simple fixed 64-byte format. * '''Public key encoding''': Instead of using [https://www.secg.org/sec1-v2.pdf ''compressed''] 33-byte encodings of elliptic curve points which are common in Bitcoin today, public keys in this proposal are encoded as 32 bytes. * '''Batch verification''': The specific formulation of ECDSA signatures that is standardized cannot be verified more efficiently in batch compared to individually, unless additional witness data is added. Changing the signature scheme offers an opportunity to address this. * '''Completely specified''': To be safe for usage in consensus systems, the verification algorithm must be completely specified at the byte level. This guarantees that nobody can construct a signature that is valid to some verifiers but not all. This is traditionally not a requirement for digital signature schemes, and the lack of exact specification for the DER parsing of ECDSA signatures has caused problems for Bitcoin [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2015-July/009697.html in the past], needing [[bip-0066.mediawiki|BIP66]] to address it. In this document we aim to meet this property by design. For batch verification, which is inherently non-deterministic as the verifier can choose their batches, this property implies that the outcome of verification may only differ from individual verifications with negligible probability, even to an attacker who intentionally tries to make batch- and non-batch verification differ. By reusing the same curve and hash function as Bitcoin uses for ECDSA, we are able to retain existing mechanisms for choosing secret and public keys, and we avoid introducing new assumptions about the security of elliptic curves and hash functions. == Description == We first build up the algebraic formulation of the signature scheme by going through the design choices. Afterwards, we specify the exact encodings and operations. === Design === '''Schnorr signature variant''' Elliptic Curve Schnorr signatures for message ''m'' and public key ''P'' generally involve a point ''R'', integers ''e'' and ''s'' picked by the signer, and the base point ''G'' which satisfy ''e = hash(R || m)'' and ''s⋅G = R + e⋅P''. Two formulations exist, depending on whether the signer reveals ''e'' or ''R'': # Signatures are pairs ''(e, s)'' that satisfy ''e = hash(s⋅G - e⋅P || m)''. This variant avoids minor complexity introduced by the encoding of the point ''R'' in the signature (see paragraphs "Encoding R and public key point P" and "Implicit Y coordinates" further below in this subsection). Moreover, revealing ''e'' instead of ''R'' allows for potentially shorter signatures: Whereas an encoding of ''R'' inherently needs about 32 bytes, the hash ''e'' can be tuned to be shorter than 32 bytes, and [http://www.neven.org/papers/schnorr.pdf a short hash of only 16 bytes suffices to provide SUF-CMA security at the target security level of 128 bits]. However, a major drawback of this optimization is that finding collisions in a short hash function is easy. This complicates the implementation of secure signing protocols in scenarios in which a group of mutually distrusting signers work together to produce a single joint signature (see Applications below). In these scenarios, which are not captured by the SUF-CMA model due its assumption of a single honest signer, a promising attack strategy for malicious co-signers is to find a collision in the hash function in order to obtain a valid signature on a message that an honest co-signer did not intend to sign. # Signatures are pairs ''(R, s)'' that satisfy ''s⋅G = R + hash(R || m)⋅P''. This supports batch verification, as there are no elliptic curve operations inside the hashes. Batch verification enables significant speedups.The speedup that results from batch verification can be demonstrated with the cryptography library [https://github.com/jonasnick/secp256k1/blob/schnorrsig-batch-verify/doc/speedup-batch.md libsecp256k1]. Since we would like to avoid the fragility that comes with short hashes, the ''e'' variant does not provide significant advantages. We choose the ''R''-option, which supports batch verification. '''Key prefixing''' Using the verification rule above directly makes Schnorr signatures vulnerable to "related-key attacks" in which a third party can convert a signature ''(R, s)'' for public key ''P'' into a signature ''(R, s + a⋅hash(R || m))'' for public key ''P + a⋅G'' and the same message ''m'', for any given additive tweak ''a'' to the signing key. This would render signatures insecure when keys are generated using [[bip-0032.mediawiki#public-parent-key--public-child-key|BIP32's unhardened derivation]] and other methods that rely on additive tweaks to existing keys such as Taproot. To protect against these attacks, we choose ''key prefixed''A limitation of committing to the public key (rather than to a short hash of it, or not at all) is that it removes the ability for public key recovery or verifying signatures against a short public key hash. These constructions are generally incompatible with batch verification. Schnorr signatures which means that the public key is prefixed to the message in the challenge hash input. This changes the equation to ''s⋅G = R + hash(R || P || m)⋅P''. [https://eprint.iacr.org/2015/1135.pdf It can be shown] that key prefixing protects against related-key attacks with additive tweaks. In general, key prefixing increases robustness in multi-user settings, e.g., it seems to be a requirement for proving multiparty signing protocols (such as MuSig, MuSig2, and FROST) secure (see Applications below). We note that key prefixing is not strictly necessary for transaction signatures as used in Bitcoin currently, because signed transactions indirectly commit to the public keys already, i.e., ''m'' contains a commitment to ''pk''. However, this indirect commitment should not be relied upon because it may change with proposals such as SIGHASH_NOINPUT ([[bip-0118.mediawiki|BIP118]]), and would render the signature scheme unsuitable for other purposes than signing transactions, e.g., [https://bitcoin.org/en/developer-reference#signmessage signing ordinary messages]. '''Encoding R and public key point P''' There exist several possibilities for encoding elliptic curve points: # Encoding the full X and Y coordinates of ''P'' and ''R'', resulting in a 64-byte public key and a 96-byte signature. # Encoding the full X coordinate and one bit of the Y coordinate to determine one of the two possible Y coordinates. This would result in 33-byte public keys and 65-byte signatures. # Encoding only the X coordinate, resulting in 32-byte public keys and 64-byte signatures. Using the first option would be slightly more efficient for verification (around 10%), but we prioritize compactness, and therefore choose option 3. '''Implicit Y coordinates''' In order to support efficient verification and batch verification, the Y coordinate of ''P'' and of ''R'' cannot be ambiguous (every valid X coordinate has two possible Y coordinates). We have a choice between several options for symmetry breaking: # Implicitly choosing the Y coordinate that is in the lower half. # Implicitly choosing the Y coordinate that is evenSince ''p'' is odd, negation modulo ''p'' will map even numbers to odd numbers and the other way around. This means that for a valid X coordinate, one of the corresponding Y coordinates will be even, and the other will be odd.. # Implicitly choosing the Y coordinate that is a quadratic residue (i.e. has a square root modulo ''p''). The second option offers the greatest compatibility with existing key generation systems, where the standard 33-byte compressed public key format consists of a byte indicating the oddness of the Y coordinate, plus the full X coordinate. To avoid gratuitous incompatibilities, we pick that option for ''P'', and thus our X-only public keys become equivalent to a compressed public key that is the X-only key prefixed by the byte 0x02. For consistency, the same is done for ''R''An earlier version of this draft used the third option instead, based on a belief that this would in general trade signing efficiency for verification efficiency. When using Jacobian coordinates, a common optimization in ECC implementations, it is possible to determine if a Y coordinate is a quadratic residue by computing the Legendre symbol, without converting to affine coordinates first (which needs a modular inversion). As modular inverses and Legendre symbols have similar [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2020-August/018081.html performance] in practice, this trade-off is not worth it.. Despite halving the size of the set of valid public keys, implicit Y coordinates are not a reduction in security. Informally, if a fast algorithm existed to compute the discrete logarithm of an X-only public key, then it could also be used to compute the discrete logarithm of a full public key: apply it to the X coordinate, and then optionally negate the result. This shows that breaking an X-only public key can be at most a small constant term faster than breaking a full one.This can be formalized by a simple reduction that reduces an attack on Schnorr signatures with implicit Y coordinates to an attack to Schnorr signatures with explicit Y coordinates. The reduction works by reencoding public keys and negating the result of the hash function, which is modeled as random oracle, whenever the challenge public key has an explicit Y coordinate that is odd. A proof sketch can be found [https://medium.com/blockstream/reducing-bitcoin-transaction-sizes-with-x-only-pubkeys-f86476af05d7 here].. '''Tagged Hashes''' Cryptographic hash functions are used for multiple purposes in the specification below and in Bitcoin in general. To make sure hashes used in one context can't be reinterpreted in another one, hash functions can be tweaked with a context-dependent tag name, in such a way that collisions across contexts can be assumed to be infeasible. Such collisions obviously can not be ruled out completely, but only for schemes using tagging with a unique name. As for other schemes collisions are at least less likely with tagging than without. For example, without tagged hashing a BIP340 signature could also be valid for a signature scheme where the only difference is that the arguments to the hash function are reordered. Worse, if the BIP340 nonce derivation function was copied or independently created, then the nonce could be accidentally reused in the other scheme leaking the secret key. This proposal suggests to include the tag by prefixing the hashed data with ''SHA256(tag) || SHA256(tag)''. Because this is a 64-byte long context-specific constant and the ''SHA256'' block size is also 64 bytes, optimized implementations are possible (identical to SHA256 itself, but with a modified initial state). Using SHA256 of the tag name itself is reasonably simple and efficient for implementations that don't choose to use the optimization. In general, tags can be arbitrary byte arrays, but are suggested to be textual descriptions in UTF-8 encoding. '''Final scheme''' As a result, our final scheme ends up using public key ''pk'' which is the X coordinate of a point ''P'' on the curve whose Y coordinate is even and signatures ''(r,s)'' where ''r'' is the X coordinate of a point ''R'' whose Y coordinate is even. The signature satisfies ''s⋅G = R + tagged_hash(r || pk || m)⋅P''. === Specification === The following conventions are used, with constants as defined for [https://www.secg.org/sec2-v2.pdf secp256k1]. We note that adapting this specification to other elliptic curves is not straightforward and can result in an insecure schemeAmong other pitfalls, using the specification with a curve whose order is not close to the size of the range of the nonce derivation function is insecure.. * Lowercase variables represent integers or byte arrays. ** The constant ''p'' refers to the field size, ''0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEFFFFFC2F''. ** The constant ''n'' refers to the curve order, ''0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141''. * Uppercase variables refer to points on the curve with equation ''y2 = x3 + 7'' over the integers modulo ''p''. ** ''is_infinite(P)'' returns whether or not ''P'' is the point at infinity. ** ''x(P)'' and ''y(P)'' are integers in the range ''0..p-1'' and refer to the X and Y coordinates of a point ''P'' (assuming it is not infinity). ** The constant ''G'' refers to the base point, for which ''x(G) = 0x79BE667EF9DCBBAC55A06295CE870B07029BFCDB2DCE28D959F2815B16F81798'' and ''y(G) = 0x483ADA7726A3C4655DA4FBFC0E1108A8FD17B448A68554199C47D08FFB10D4B8''. ** Addition of points refers to the usual [https://en.wikipedia.org/wiki/Elliptic_curve#The_group_law elliptic curve group operation]. ** [https://en.wikipedia.org/wiki/Elliptic_curve_point_multiplication Multiplication (⋅) of an integer and a point] refers to the repeated application of the group operation. * Functions and operations: ** ''||'' refers to byte array concatenation. ** The function ''x[i:j]'', where ''x'' is a byte array and ''i, j ≥ 0'', returns a ''(j - i)''-byte array with a copy of the ''i''-th byte (inclusive) to the ''j''-th byte (exclusive) of ''x''. ** The function ''bytes(x)'', where ''x'' is an integer, returns the 32-byte encoding of ''x'', most significant byte first. ** The function ''bytes(P)'', where ''P'' is a point, returns ''bytes(x(P))''. ** The function ''int(x)'', where ''x'' is a 32-byte array, returns the 256-bit unsigned integer whose most significant byte first encoding is ''x''. ** The function ''has_even_y(P)'', where ''P'' is a point for which ''not is_infinite(P)'', returns ''y(P) mod 2 = 0''. ** The function ''lift_x(x)'', where ''x'' is a 256-bit unsigned integer, returns the point ''P'' for which ''x(P) = x'' Given a candidate X coordinate ''x'' in the range ''0..p-1'', there exist either exactly two or exactly zero valid Y coordinates. If no valid Y coordinate exists, then ''x'' is not a valid X coordinate either, i.e., no point ''P'' exists for which ''x(P) = x''. The valid Y coordinates for a given candidate ''x'' are the square roots of ''c = x3 + 7 mod p'' and they can be computed as ''y = ±c(p+1)/4 mod p'' (see [https://en.wikipedia.org/wiki/Quadratic_residue#Prime_or_prime_power_modulus Quadratic residue]) if they exist, which can be checked by squaring and comparing with ''c''. and ''has_even_y(P)'', or fails if ''x'' is greater than ''p-1'' or no such point exists. The function ''lift_x(x)'' is equivalent to the following pseudocode: *** Fail if ''x ≥ p''. *** Let ''c = x3 + 7 mod p''. *** Let ''y = c(p+1)/4 mod p''. *** Fail if ''c ≠ y2 mod p''. *** Return the unique point ''P'' such that ''x(P) = x'' and ''y(P) = y'' if ''y mod 2 = 0'' or ''y(P) = p-y'' otherwise. ** The function ''hashname(x)'' where ''x'' is a byte array returns the 32-byte hash ''SHA256(SHA256(tag) || SHA256(tag) || x)'', where ''tag'' is the UTF-8 encoding of ''name''. ==== Public Key Generation ==== Input: * The secret key ''sk'': a 32-byte array, freshly generated uniformly at random The algorithm ''PubKey(sk)'' is defined as: * Let ''d' = int(sk)''. * Fail if ''d' = 0'' or ''d' ≥ n''. * Return ''bytes(d'⋅G)''. Note that we use a very different public key format (32 bytes) than the ones used by existing systems (which typically use elliptic curve points as public keys, or 33-byte or 65-byte encodings of them). A side effect is that ''PubKey(sk) = PubKey(bytes(n - int(sk))'', so every public key has two corresponding secret keys. ==== Public Key Conversion ==== As an alternative to generating keys randomly, it is also possible and safe to repurpose existing key generation algorithms for ECDSA in a compatible way. The secret keys constructed by such an algorithm can be used as ''sk'' directly. The public keys constructed by such an algorithm (assuming they use the 33-byte compressed encoding) need to be converted by dropping the first byte. Specifically, [[bip-0032.mediawiki|BIP32]] and schemes built on top of it remain usable. ==== Default Signing ==== Input: * The secret key ''sk'': a 32-byte array * The message ''m'': a byte array * Auxiliary random data ''a'': a 32-byte array The algorithm ''Sign(sk, m)'' is defined as: * Let ''d' = int(sk)'' * Fail if ''d' = 0'' or ''d' ≥ n'' * Let ''P = d'⋅G'' * Let ''d = d' '' if ''has_even_y(P)'', otherwise let ''d = n - d' ''. * Let ''t'' be the byte-wise xor of ''bytes(d)'' and ''hashBIP0340/aux(a)''The auxiliary random data is hashed (with a unique tag) as a precaution against situations where the randomness may be correlated with the private key itself. It is xored with the private key (rather than combined with it in a hash) to reduce the number of operations exposed to the actual secret key.. * Let ''rand = hashBIP0340/nonce(t || bytes(P) || m)''Including the [https://moderncrypto.org/mail-archive/curves/2020/001012.html public key as input to the nonce hash] helps ensure the robustness of the signing algorithm by preventing leakage of the secret key if the calculation of the public key ''P'' is performed incorrectly or maliciously, for example if it is left to the caller for performance reasons.. * Let ''k' = int(rand) mod n''Note that in general, taking a uniformly random 256-bit integer modulo the curve order will produce an unacceptably biased result. However, for the secp256k1 curve, the order is sufficiently close to ''2256'' that this bias is not observable (''1 - n / 2256'' is around ''1.27 * 2-128'').. * Fail if ''k' = 0''. * Let ''R = k'⋅G''. * Let ''k = k' '' if ''has_even_y(R)'', otherwise let ''k = n - k' ''. * Let ''e = int(hashBIP0340/challenge(bytes(R) || bytes(P) || m)) mod n''. * Let ''sig = bytes(R) || bytes((k + ed) mod n)''. * If ''Verify(bytes(P), m, sig)'' (see below) returns failure, abortVerifying the signature before leaving the signer prevents random or attacker provoked computation errors. This prevents publishing invalid signatures which may leak information about the secret key. It is recommended, but can be omitted if the computation cost is prohibitive.. * Return the signature ''sig''. The auxiliary random data should be set to fresh randomness generated at signing time, resulting in what is called a ''synthetic nonce''. Using 32 bytes of randomness is optimal. If obtaining randomness is expensive, 16 random bytes can be padded with 16 null bytes to obtain a 32-byte array. If randomness is not available at all at signing time, a simple counter wide enough to not repeat in practice (e.g., 64 bits or wider) and padded with null bytes to a 32 byte-array can be used, or even the constant array with 32 null bytes. Using any non-repeating value increases protection against [https://moderncrypto.org/mail-archive/curves/2017/000925.html fault injection attacks]. Using unpredictable randomness additionally increases protection against other side-channel attacks, and is '''recommended whenever available'''. Note that while this means the resulting nonce is not deterministic, the randomness is only supplemental to security. The normal security properties (excluding side-channel attacks) do not depend on the quality of the signing-time RNG. ==== Alternative Signing ==== It should be noted that various alternative signing algorithms can be used to produce equally valid signatures. The 32-byte ''rand'' value may be generated in other ways, producing a different but still valid signature (in other words, this is not a ''unique'' signature scheme). '''No matter which method is used to generate the ''rand'' value, the value must be a fresh uniformly random 32-byte string which is not even partially predictable for the attacker.''' For nonces without randomness, this implies that the same inputs must not be presented in another context. This can be most reliably accomplished by not reusing the same private key across different signing schemes. For example, if the ''rand'' value was computed as per RFC6979 and the same secret key is used in deterministic ECDSA with RFC6979, the signatures can leak the secret key through nonce reuse. '''Nonce exfiltration protection''' It is possible to strengthen the nonce generation algorithm using a second device. In this case, the second device contributes randomness which the actual signer provably incorporates into its nonce. This prevents certain attacks where the signer's device is compromised and intentionally tries to leak the secret key through its nonce selection. '''Multisignatures''' This signature scheme is compatible with various types of multisignature and threshold schemes such as [https://eprint.iacr.org/2020/1261.pdf MuSig2], where a single public key requires holders of multiple secret keys to participate in signing (see Applications below). '''It is important to note that multisignature signing schemes in general are insecure with the ''rand'' generation from the default signing algorithm above (or any other deterministic method).''' '''Precomputed public key data''' For many uses, the compressed 33-byte encoding of the public key corresponding to the secret key may already be known, making it easy to evaluate ''has_even_y(P)'' and ''bytes(P)''. As such, having signers supply this directly may be more efficient than recalculating the public key from the secret key. However, if this optimization is used and additionally the signature verification at the end of the signing algorithm is dropped for increased efficiency, signers must ensure the public key is correctly calculated and not taken from untrusted sources. ==== Verification ==== Input: * The public key ''pk'': a 32-byte array * The message ''m'': a byte array * A signature ''sig'': a 64-byte array The algorithm ''Verify(pk, m, sig)'' is defined as: * Let ''P = lift_x(int(pk))''; fail if that fails. * Let ''r = int(sig[0:32])''; fail if ''r ≥ p''. * Let ''s = int(sig[32:64])''; fail if ''s ≥ n''. * Let ''e = int(hashBIP0340/challenge(bytes(r) || bytes(P) || m)) mod n''. * Let ''R = s⋅G - e⋅P''. * Fail if ''is_infinite(R)''. * Fail if ''not has_even_y(R)''. * Fail if ''x(R) ≠ r''. * Return success iff no failure occurred before reaching this point. For every valid secret key ''sk'' and message ''m'', ''Verify(PubKey(sk),m,Sign(sk,m))'' will succeed. Note that the correctness of verification relies on the fact that ''lift_x'' always returns a point with an even Y coordinate. A hypothetical verification algorithm that treats points as public keys, and takes the point ''P'' directly as input would fail any time a point with odd Y is used. While it is possible to correct for this by negating points with odd Y coordinate before further processing, this would result in a scheme where every (message, signature) pair is valid for two public keys (a type of malleability that exists for ECDSA as well, but we don't wish to retain). We avoid these problems by treating just the X coordinate as public key. ==== Batch Verification ==== Input: * The number ''u'' of signatures * The public keys ''pk1..u'': ''u'' 32-byte arrays * The messages ''m1..u'': ''u'' byte arrays * The signatures ''sig1..u'': ''u'' 64-byte arrays The algorithm ''BatchVerify(pk1..u, m1..u, sig1..u)'' is defined as: * Generate ''u-1'' random integers ''a2...u'' in the range ''1...n-1''. They are generated deterministically using a [https://en.wikipedia.org/wiki/Cryptographically_secure_pseudorandom_number_generator CSPRNG] seeded by a cryptographic hash of all inputs of the algorithm, i.e. ''seed = seed_hash(pk1..pku || m1..mu || sig1..sigu )''. A safe choice is to instantiate ''seed_hash'' with SHA256 and use [https://tools.ietf.org/html/rfc8439 ChaCha20] with key ''seed'' as a CSPRNG to generate 256-bit integers, skipping integers not in the range ''1...n-1''. * For ''i = 1 .. u'': ** Let ''Pi = lift_x(int(pki))''; fail if it fails. ** Let ''ri = int(sigi[0:32])''; fail if ''ri ≥ p''. ** Let ''si = int(sigi[32:64])''; fail if ''si ≥ n''. ** Let ''ei = int(hashBIP0340/challenge(bytes(ri) || bytes(Pi) || mi)) mod n''. ** Let ''Ri = lift_x(ri)''; fail if ''lift_x(ri)'' fails. * Fail if ''(s1 + a2s2 + ... + ausu)⋅G ≠ R1 + a2⋅R2 + ... + au⋅Ru + e1⋅P1 + (a2e2)⋅P2 + ... + (aueu)⋅Pu''. * Return success iff no failure occurred before reaching this point. If all individual signatures are valid (i.e., ''Verify'' would return success for them), ''BatchVerify'' will always return success. If at least one signature is invalid, ''BatchVerify'' will return success with at most a negligible probability. === Usage Considerations === ==== Messages of Arbitrary Size ==== The signature scheme specified in this BIP accepts byte strings of arbitrary size as input messages.In theory, the message size is restricted due to the fact that SHA256 accepts byte strings only up to size of 2^61-1 bytes. It is understood that implementations may reject messages which are too large in their environment or application context, e.g., messages which exceed predefined buffers or would otherwise cause resource exhaustion. Earlier revisions of this BIP required messages to be exactly 32 bytes. This restriction puts a burden on callers who typically need to perform pre-hashing of the actual input message by feeding it through SHA256 (or another collision-resistant cryptographic hash function) to create a 32-byte digest which can be passed to signing or verification (as for example done in [[bip-0341.mediawiki|BIP341]].) Since pre-hashing may not always be desirable, e.g., when actual messages are shorter than 32 bytes,Another reason to omit pre-hashing is to protect against certain types of cryptanalytic advances against the hash function used for pre-hashing: If pre-hashing is used, an attacker that can find collisions in the pre-hashing function can necessarily forge signatures under chosen-message attacks. If pre-hashing is not used, an attacker that can find collisions in SHA256 (as used inside the signature scheme) may not be able to forge signatures. However, this seeming advantage is mostly irrelevant in the context of Bitcoin, which already relies on collision resistance of SHA256 in other places, e.g., for transaction hashes. the restriction to 32-byte messages has been lifted. We note that pre-hashing is recommended for performance reasons in applications that deal with large messages. If large messages are not pre-hashed, the algorithms of the signature scheme will perform more hashing internally. In particular, the signing algorithm needs two sequential hashing passes over the message, which means that the full message must necessarily be kept in memory during signing, and large messages entail a runtime penalty.Typically, messages of 56 bytes or longer enjoy a performance benefit from pre-hashing, assuming the speed of SHA256 inside the signing algorithm matches that of the pre-hashing done by the calling application. ==== Domain Separation ==== It is good cryptographic practice to use a key pair only for a single purpose. Nevertheless, there may be situations in which it may be desirable to use the same key pair in multiple contexts, i.e., to sign different types of messages within the same application or even messages in entirely different applications (e.g., a secret key may be used to sign Bitcoin transactions as well plain text messages). As a consequence, applications should ensure that a signed application message intended for one context is never deemed valid in a different context (e.g., a signed plain text message should never be misinterpreted as a signed Bitcoin transaction, because this could cause unintended loss of funds). This is called "domain separation" and it is typically realized by partitioning the message space. Even if key pairs are intended to be used only within a single context, domain separation is a good idea because it makes it easy to add more contexts later. As a best practice, we recommend applications to use exactly one of the following methods to pre-process application messages before passing it to the signature scheme: * Either, pre-hash the application message using ''hashname'', where ''name'' identifies the context uniquely (e.g., "foo-app/signed-bar"), * or prefix the actual message with a 33-byte string that identifies the context uniquely (e.g., the UTF-8 encoding of "foo-app/signed-bar", padded with null bytes to 33 bytes). As the two pre-processing methods yield different message sizes (32 bytes vs. at least 33 bytes), there is no risk of collision between them. == Applications == There are several interesting applications beyond simple signatures. While recent academic papers claim that they are also possible with ECDSA, consensus support for Schnorr signature verification would significantly simplify the constructions. === Multisignatures and Threshold Signatures === By means of an interactive scheme such as [https://eprint.iacr.org/2020/1261.pdf MuSig2] ([[bip-0327.mediawiki|BIP327]]), participants can aggregate their public keys into a single public key which they can jointly sign for. This allows ''n''-of-''n'' multisignatures which, from a verifier's perspective, are no different from ordinary signatures, giving improved privacy and efficiency versus ''CHECKMULTISIG'' or other means. Moreover, Schnorr signatures are compatible with [https://en.wikipedia.org/wiki/Distributed_key_generation distributed key generation], which enables interactive threshold signatures schemes, e.g., the schemes by [http://cacr.uwaterloo.ca/techreports/2001/corr2001-13.ps Stinson and Strobl (2001)], by [https://link.springer.com/content/pdf/10.1007/s00145-006-0347-3.pdf Gennaro, Jarecki, Krawczyk, and Rabin (2007)], or the [https://eprint.iacr.org/2020/852.pdf FROST] scheme including its variants such as [https://eprint.iacr.org/2023/899.pdf FROST3]. These protocols make it possible to realize ''k''-of-''n'' threshold signatures, which ensure that any subset of size ''k'' of the set of ''n'' signers can sign but no subset of size less than ''k'' can produce a valid Schnorr signature. === Adaptor Signatures === [https://download.wpsoftware.net/bitcoin/wizardry/mw-slides/2018-05-18-l2/slides.pdf Adaptor signatures] can be produced by a signer by offsetting his public nonce ''R'' with a known point ''T = t⋅G'', but not offsetting the signature's ''s'' value. A correct signature (or partial signature, as individual signers' contributions to a multisignature are called) on the same message with same nonce will then be equal to the adaptor signature offset by ''t'', meaning that learning ''t'' is equivalent to learning a correct signature. This can be used to enable atomic swaps or even [https://eprint.iacr.org/2018/472 general payment channels] in which the atomicity of disjoint transactions is ensured using the signatures themselves, rather than Bitcoin script support. The resulting transactions will appear to verifiers to be no different from ordinary single-signer transactions, except perhaps for the inclusion of locktime refund logic. Adaptor signatures, beyond the efficiency and privacy benefits of encoding script semantics into constant-sized signatures, have additional benefits over traditional hash-based payment channels. Specifically, the secret values ''t'' may be reblinded between hops, allowing long chains of transactions to be made atomic while even the participants cannot identify which transactions are part of the chain. Also, because the secret values are chosen at signing time, rather than key generation time, existing outputs may be repurposed for different applications without recourse to the blockchain, even multiple times. === Blind Signatures === A blind signature protocol is an interactive protocol that enables a signer to sign a message at the behest of another party without learning any information about the signed message or the signature. Schnorr signatures admit a very [http://publikationen.ub.uni-frankfurt.de/files/4292/schnorr.blind_sigs_attack.2001.pdf simple blind signature scheme] which is however insecure because it's vulnerable to [https://www.iacr.org/archive/crypto2002/24420288/24420288.pdf Wagner's attack]. Known mitigations are to let the signer abort a signing session with a certain probability, which can be [https://eprint.iacr.org/2019/877 proven secure under non-standard cryptographic assumptions], or [https://eprint.iacr.org/2022/1676.pdf to use zero-knowledge proofs]. Blind Schnorr signatures could for example be used in [https://github.com/ElementsProject/scriptless-scripts/blob/master/md/partially-blind-swap.md Partially Blind Atomic Swaps], a construction to enable transferring of coins, mediated by an untrusted escrow agent, without connecting the transactors in the public blockchain transaction graph. == Test Vectors and Reference Code == For development and testing purposes, we provide a [[bip-0340/test-vectors.csv|collection of test vectors in CSV format]], a naive, highly inefficient, and non-constant time [[bip-0340/reference.py|pure Python 3.7 reference implementation of the signing and verification algorithm]] as well as the [[bip-0340/test-vectors.py|script used to generate the test vectors]] under the BSD-2-Clause License, or the MIT License, or CC0 1.0, at your choice. The reference implementation is for demonstration purposes only and not to be used in production environments. == Changelog == To help implementers understand updates to this BIP, we keep a list of substantial changes. * 2022-08: Fix function signature of lift_x in reference code * 2023-04: Allow messages of arbitrary size * 2024-05: Update "Applications" section with more recent references * 2025-04: Change license of test vectors and code == Footnotes == == Acknowledgements == This document is the result of many discussions around Schnorr based signatures over the years, and had input from Johnson Lau, Greg Maxwell, Andrew Poelstra, Rusty Russell, and Anthony Towns. The authors further wish to thank all those who provided valuable feedback and reviews, including the participants of the [https://github.com/ajtowns/taproot-review structured reviews]. ================================================ FILE: bip-0341/wallet-test-vectors.json ================================================ { "version": 1, "scriptPubKey": [ { "given": { "internalPubkey": "d6889cb081036e0faefa3a35157ad71086b123b2b144b649798b494c300a961d", "scriptTree": null }, "intermediary": { "merkleRoot": null, "tweak": "b86e7be8f39bab32a6f2c0443abbc210f0edac0e2c53d501b36b64437d9c6c70", "tweakedPubkey": "53a1f6e454df1aa2776a2814a721372d6258050de330b3c6d10ee8f4e0dda343" }, "expected": { "scriptPubKey": "512053a1f6e454df1aa2776a2814a721372d6258050de330b3c6d10ee8f4e0dda343", "bip350Address": "bc1p2wsldez5mud2yam29q22wgfh9439spgduvct83k3pm50fcxa5dps59h4z5" } }, { "given": { "internalPubkey": "187791b6f712a8ea41c8ecdd0ee77fab3e85263b37e1ec18a3651926b3a6cf27", "scriptTree": { "id": 0, "script": "20d85a959b0290bf19bb89ed43c916be835475d013da4b362117393e25a48229b8ac", "leafVersion": 192 } }, "intermediary": { "leafHashes": [ "5b75adecf53548f3ec6ad7d78383bf84cc57b55a3127c72b9a2481752dd88b21" ], "merkleRoot": "5b75adecf53548f3ec6ad7d78383bf84cc57b55a3127c72b9a2481752dd88b21", "tweak": "cbd8679ba636c1110ea247542cfbd964131a6be84f873f7f3b62a777528ed001", "tweakedPubkey": "147c9c57132f6e7ecddba9800bb0c4449251c92a1e60371ee77557b6620f3ea3" }, "expected": { "scriptPubKey": "5120147c9c57132f6e7ecddba9800bb0c4449251c92a1e60371ee77557b6620f3ea3", "bip350Address": "bc1pz37fc4cn9ah8anwm4xqqhvxygjf9rjf2resrw8h8w4tmvcs0863sa2e586", "scriptPathControlBlocks": [ "c1187791b6f712a8ea41c8ecdd0ee77fab3e85263b37e1ec18a3651926b3a6cf27" ] } }, { "given": { "internalPubkey": "93478e9488f956df2396be2ce6c5cced75f900dfa18e7dabd2428aae78451820", "scriptTree": { "id": 0, "script": "20b617298552a72ade070667e86ca63b8f5789a9fe8731ef91202a91c9f3459007ac", "leafVersion": 192 } }, "intermediary": { "leafHashes": [ "c525714a7f49c28aedbbba78c005931a81c234b2f6c99a73e4d06082adc8bf2b" ], "merkleRoot": "c525714a7f49c28aedbbba78c005931a81c234b2f6c99a73e4d06082adc8bf2b", "tweak": "6af9e28dbf9d6aaf027696e2598a5b3d056f5fd2355a7fd5a37a0e5008132d30", "tweakedPubkey": "e4d810fd50586274face62b8a807eb9719cef49c04177cc6b76a9a4251d5450e" }, "expected": { "scriptPubKey": "5120e4d810fd50586274face62b8a807eb9719cef49c04177cc6b76a9a4251d5450e", "bip350Address": "bc1punvppl2stp38f7kwv2u2spltjuvuaayuqsthe34hd2dyy5w4g58qqfuag5", "scriptPathControlBlocks": [ "c093478e9488f956df2396be2ce6c5cced75f900dfa18e7dabd2428aae78451820" ] } }, { "given": { "internalPubkey": "ee4fe085983462a184015d1f782d6a5f8b9c2b60130aff050ce221ecf3786592", "scriptTree": [ { "id": 0, "script": "20387671353e273264c495656e27e39ba899ea8fee3bb69fb2a680e22093447d48ac", "leafVersion": 192 }, { "id": 1, "script": "06424950333431", "leafVersion": 250 } ] }, "intermediary": { "leafHashes": [ "8ad69ec7cf41c2a4001fd1f738bf1e505ce2277acdcaa63fe4765192497f47a7", "f224a923cd0021ab202ab139cc56802ddb92dcfc172b9212261a539df79a112a" ], "merkleRoot": "6c2dc106ab816b73f9d07e3cd1ef2c8c1256f519748e0813e4edd2405d277bef", "tweak": "9e0517edc8259bb3359255400b23ca9507f2a91cd1e4250ba068b4eafceba4a9", "tweakedPubkey": "712447206d7a5238acc7ff53fbe94a3b64539ad291c7cdbc490b7577e4b17df5" }, "expected": { "scriptPubKey": "5120712447206d7a5238acc7ff53fbe94a3b64539ad291c7cdbc490b7577e4b17df5", "bip350Address": "bc1pwyjywgrd0ffr3tx8laflh6228dj98xkjj8rum0zfpd6h0e930h6saqxrrm", "scriptPathControlBlocks": [ "c0ee4fe085983462a184015d1f782d6a5f8b9c2b60130aff050ce221ecf3786592f224a923cd0021ab202ab139cc56802ddb92dcfc172b9212261a539df79a112a", "faee4fe085983462a184015d1f782d6a5f8b9c2b60130aff050ce221ecf37865928ad69ec7cf41c2a4001fd1f738bf1e505ce2277acdcaa63fe4765192497f47a7" ] } }, { "given": { "internalPubkey": "f9f400803e683727b14f463836e1e78e1c64417638aa066919291a225f0e8dd8", "scriptTree": [ { "id": 0, "script": "2044b178d64c32c4a05cc4f4d1407268f764c940d20ce97abfd44db5c3592b72fdac", "leafVersion": 192 }, { "id": 1, "script": "07546170726f6f74", "leafVersion": 192 } ] }, "intermediary": { "leafHashes": [ "64512fecdb5afa04f98839b50e6f0cb7b1e539bf6f205f67934083cdcc3c8d89", "2cb2b90daa543b544161530c925f285b06196940d6085ca9474d41dc3822c5cb" ], "merkleRoot": "ab179431c28d3b68fb798957faf5497d69c883c6fb1e1cd9f81483d87bac90cc", "tweak": "639f0281b7ac49e742cd25b7f188657626da1ad169209078e2761cefd91fd65e", "tweakedPubkey": "77e30a5522dd9f894c3f8b8bd4c4b2cf82ca7da8a3ea6a239655c39c050ab220" }, "expected": { "scriptPubKey": "512077e30a5522dd9f894c3f8b8bd4c4b2cf82ca7da8a3ea6a239655c39c050ab220", "bip350Address": "bc1pwl3s54fzmk0cjnpl3w9af39je7pv5ldg504x5guk2hpecpg2kgsqaqstjq", "scriptPathControlBlocks": [ "c1f9f400803e683727b14f463836e1e78e1c64417638aa066919291a225f0e8dd82cb2b90daa543b544161530c925f285b06196940d6085ca9474d41dc3822c5cb", "c1f9f400803e683727b14f463836e1e78e1c64417638aa066919291a225f0e8dd864512fecdb5afa04f98839b50e6f0cb7b1e539bf6f205f67934083cdcc3c8d89" ] } }, { "given": { "internalPubkey": "e0dfe2300b0dd746a3f8674dfd4525623639042569d829c7f0eed9602d263e6f", "scriptTree": [ { "id": 0, "script": "2072ea6adcf1d371dea8fba1035a09f3d24ed5a059799bae114084130ee5898e69ac", "leafVersion": 192 }, [ { "id": 1, "script": "202352d137f2f3ab38d1eaa976758873377fa5ebb817372c71e2c542313d4abda8ac", "leafVersion": 192 }, { "id": 2, "script": "207337c0dd4253cb86f2c43a2351aadd82cccb12a172cd120452b9bb8324f2186aac", "leafVersion": 192 } ] ] }, "intermediary": { "leafHashes": [ "2645a02e0aac1fe69d69755733a9b7621b694bb5b5cde2bbfc94066ed62b9817", "ba982a91d4fc552163cb1c0da03676102d5b7a014304c01f0c77b2b8e888de1c", "9e31407bffa15fefbf5090b149d53959ecdf3f62b1246780238c24501d5ceaf6" ], "merkleRoot": "ccbd66c6f7e8fdab47b3a486f59d28262be857f30d4773f2d5ea47f7761ce0e2", "tweak": "b57bfa183d28eeb6ad688ddaabb265b4a41fbf68e5fed2c72c74de70d5a786f4", "tweakedPubkey": "91b64d5324723a985170e4dc5a0f84c041804f2cd12660fa5dec09fc21783605" }, "expected": { "scriptPubKey": "512091b64d5324723a985170e4dc5a0f84c041804f2cd12660fa5dec09fc21783605", "bip350Address": "bc1pjxmy65eywgafs5tsunw95ruycpqcqnev6ynxp7jaasylcgtcxczs6n332e", "scriptPathControlBlocks": [ "c0e0dfe2300b0dd746a3f8674dfd4525623639042569d829c7f0eed9602d263e6fffe578e9ea769027e4f5a3de40732f75a88a6353a09d767ddeb66accef85e553", "c0e0dfe2300b0dd746a3f8674dfd4525623639042569d829c7f0eed9602d263e6f9e31407bffa15fefbf5090b149d53959ecdf3f62b1246780238c24501d5ceaf62645a02e0aac1fe69d69755733a9b7621b694bb5b5cde2bbfc94066ed62b9817", "c0e0dfe2300b0dd746a3f8674dfd4525623639042569d829c7f0eed9602d263e6fba982a91d4fc552163cb1c0da03676102d5b7a014304c01f0c77b2b8e888de1c2645a02e0aac1fe69d69755733a9b7621b694bb5b5cde2bbfc94066ed62b9817" ] } }, { "given": { "internalPubkey": "55adf4e8967fbd2e29f20ac896e60c3b0f1d5b0efa9d34941b5958c7b0a0312d", "scriptTree": [ { "id": 0, "script": "2071981521ad9fc9036687364118fb6ccd2035b96a423c59c5430e98310a11abe2ac", "leafVersion": 192 }, [ { "id": 1, "script": "20d5094d2dbe9b76e2c245a2b89b6006888952e2faa6a149ae318d69e520617748ac", "leafVersion": 192 }, { "id": 2, "script": "20c440b462ad48c7a77f94cd4532d8f2119dcebbd7c9764557e62726419b08ad4cac", "leafVersion": 192 } ] ] }, "intermediary": { "leafHashes": [ "f154e8e8e17c31d3462d7132589ed29353c6fafdb884c5a6e04ea938834f0d9d", "737ed1fe30bc42b8022d717b44f0d93516617af64a64753b7a06bf16b26cd711", "d7485025fceb78b9ed667db36ed8b8dc7b1f0b307ac167fa516fe4352b9f4ef7" ], "merkleRoot": "2f6b2c5397b6d68ca18e09a3f05161668ffe93a988582d55c6f07bd5b3329def", "tweak": "6579138e7976dc13b6a92f7bfd5a2fc7684f5ea42419d43368301470f3b74ed9", "tweakedPubkey": "75169f4001aa68f15bbed28b218df1d0a62cbbcf1188c6665110c293c907b831" }, "expected": { "scriptPubKey": "512075169f4001aa68f15bbed28b218df1d0a62cbbcf1188c6665110c293c907b831", "bip350Address": "bc1pw5tf7sqp4f50zka7629jrr036znzew70zxyvvej3zrpf8jg8hqcssyuewe", "scriptPathControlBlocks": [ "c155adf4e8967fbd2e29f20ac896e60c3b0f1d5b0efa9d34941b5958c7b0a0312d3cd369a528b326bc9d2133cbd2ac21451acb31681a410434672c8e34fe757e91", "c155adf4e8967fbd2e29f20ac896e60c3b0f1d5b0efa9d34941b5958c7b0a0312dd7485025fceb78b9ed667db36ed8b8dc7b1f0b307ac167fa516fe4352b9f4ef7f154e8e8e17c31d3462d7132589ed29353c6fafdb884c5a6e04ea938834f0d9d", "c155adf4e8967fbd2e29f20ac896e60c3b0f1d5b0efa9d34941b5958c7b0a0312d737ed1fe30bc42b8022d717b44f0d93516617af64a64753b7a06bf16b26cd711f154e8e8e17c31d3462d7132589ed29353c6fafdb884c5a6e04ea938834f0d9d" ] } } ], "keyPathSpending": [ { "given": { "rawUnsignedTx": "02000000097de20cbff686da83a54981d2b9bab3586f4ca7e48f57f5b55963115f3b334e9c010000000000000000d7b7cab57b1393ace2d064f4d4a2cb8af6def61273e127517d44759b6dafdd990000000000fffffffff8e1f583384333689228c5d28eac13366be082dc57441760d957275419a418420000000000fffffffff0689180aa63b30cb162a73c6d2a38b7eeda2a83ece74310fda0843ad604853b0100000000feffffffaa5202bdf6d8ccd2ee0f0202afbbb7461d9264a25e5bfd3c5a52ee1239e0ba6c0000000000feffffff956149bdc66faa968eb2be2d2faa29718acbfe3941215893a2a3446d32acd050000000000000000000e664b9773b88c09c32cb70a2a3e4da0ced63b7ba3b22f848531bbb1d5d5f4c94010000000000000000e9aa6b8e6c9de67619e6a3924ae25696bb7b694bb677a632a74ef7eadfd4eabf0000000000ffffffffa778eb6a263dc090464cd125c466b5a99667720b1c110468831d058aa1b82af10100000000ffffffff0200ca9a3b000000001976a91406afd46bcdfd22ef94ac122aa11f241244a37ecc88ac807840cb0000000020ac9a87f5594be208f8532db38cff670c450ed2fea8fcdefcc9a663f78bab962b0065cd1d", "utxosSpent": [ { "scriptPubKey": "512053a1f6e454df1aa2776a2814a721372d6258050de330b3c6d10ee8f4e0dda343", "amountSats": 420000000 }, { "scriptPubKey": "5120147c9c57132f6e7ecddba9800bb0c4449251c92a1e60371ee77557b6620f3ea3", "amountSats": 462000000 }, { "scriptPubKey": "76a914751e76e8199196d454941c45d1b3a323f1433bd688ac", "amountSats": 294000000 }, { "scriptPubKey": "5120e4d810fd50586274face62b8a807eb9719cef49c04177cc6b76a9a4251d5450e", "amountSats": 504000000 }, { "scriptPubKey": "512091b64d5324723a985170e4dc5a0f84c041804f2cd12660fa5dec09fc21783605", "amountSats": 630000000 }, { "scriptPubKey": "00147dd65592d0ab2fe0d0257d571abf032cd9db93dc", "amountSats": 378000000 }, { "scriptPubKey": "512075169f4001aa68f15bbed28b218df1d0a62cbbcf1188c6665110c293c907b831", "amountSats": 672000000 }, { "scriptPubKey": "5120712447206d7a5238acc7ff53fbe94a3b64539ad291c7cdbc490b7577e4b17df5", "amountSats": 546000000 }, { "scriptPubKey": "512077e30a5522dd9f894c3f8b8bd4c4b2cf82ca7da8a3ea6a239655c39c050ab220", "amountSats": 588000000 } ] }, "intermediary": { "hashAmounts": "58a6964a4f5f8f0b642ded0a8a553be7622a719da71d1f5befcefcdee8e0fde6", "hashOutputs": "a2e6dab7c1f0dcd297c8d61647fd17d821541ea69c3cc37dcbad7f90d4eb4bc5", "hashPrevouts": "e3b33bb4ef3a52ad1fffb555c0d82828eb22737036eaeb02a235d82b909c4c3f", "hashScriptPubkeys": "23ad0f61ad2bca5ba6a7693f50fce988e17c3780bf2b1e720cfbb38fbdd52e21", "hashSequences": "18959c7221ab5ce9e26c3cd67b22c24f8baa54bac281d8e6b05e400e6c3a957e" }, "inputSpending": [ { "given": { "txinIndex": 0, "internalPrivkey": "6b973d88838f27366ed61c9ad6367663045cb456e28335c109e30717ae0c6baa", "merkleRoot": null, "hashType": 3 }, "intermediary": { "internalPubkey": "d6889cb081036e0faefa3a35157ad71086b123b2b144b649798b494c300a961d", "tweak": "b86e7be8f39bab32a6f2c0443abbc210f0edac0e2c53d501b36b64437d9c6c70", "tweakedPrivkey": "2405b971772ad26915c8dcdf10f238753a9b837e5f8e6a86fd7c0cce5b7296d9", "sigMsg": "0003020000000065cd1de3b33bb4ef3a52ad1fffb555c0d82828eb22737036eaeb02a235d82b909c4c3f58a6964a4f5f8f0b642ded0a8a553be7622a719da71d1f5befcefcdee8e0fde623ad0f61ad2bca5ba6a7693f50fce988e17c3780bf2b1e720cfbb38fbdd52e2118959c7221ab5ce9e26c3cd67b22c24f8baa54bac281d8e6b05e400e6c3a957e0000000000d0418f0e9a36245b9a50ec87f8bf5be5bcae434337b87139c3a5b1f56e33cba0", "precomputedUsed": [ "hashAmounts", "hashPrevouts", "hashScriptPubkeys", "hashSequences" ], "sigHash": "2514a6272f85cfa0f45eb907fcb0d121b808ed37c6ea160a5a9046ed5526d555" }, "expected": { "witness": [ "ed7c1647cb97379e76892be0cacff57ec4a7102aa24296ca39af7541246d8ff14d38958d4cc1e2e478e4d4a764bbfd835b16d4e314b72937b29833060b87276c03" ] } }, { "given": { "txinIndex": 1, "internalPrivkey": "1e4da49f6aaf4e5cd175fe08a32bb5cb4863d963921255f33d3bc31e1343907f", "merkleRoot": "5b75adecf53548f3ec6ad7d78383bf84cc57b55a3127c72b9a2481752dd88b21", "hashType": 131 }, "intermediary": { "internalPubkey": "187791b6f712a8ea41c8ecdd0ee77fab3e85263b37e1ec18a3651926b3a6cf27", "tweak": "cbd8679ba636c1110ea247542cfbd964131a6be84f873f7f3b62a777528ed001", "tweakedPrivkey": "ea260c3b10e60f6de018455cd0278f2f5b7e454be1999572789e6a9565d26080", "sigMsg": "0083020000000065cd1d00d7b7cab57b1393ace2d064f4d4a2cb8af6def61273e127517d44759b6dafdd9900000000808f891b00000000225120147c9c57132f6e7ecddba9800bb0c4449251c92a1e60371ee77557b6620f3ea3ffffffffffcef8fb4ca7efc5433f591ecfc57391811ce1e186a3793024def5c884cba51d", "precomputedUsed": [], "sigHash": "325a644af47e8a5a2591cda0ab0723978537318f10e6a63d4eed783b96a71a4d" }, "expected": { "witness": [ "052aedffc554b41f52b521071793a6b88d6dbca9dba94cf34c83696de0c1ec35ca9c5ed4ab28059bd606a4f3a657eec0bb96661d42921b5f50a95ad33675b54f83" ] } }, { "given": { "txinIndex": 3, "internalPrivkey": "d3c7af07da2d54f7a7735d3d0fc4f0a73164db638b2f2f7c43f711f6d4aa7e64", "merkleRoot": "c525714a7f49c28aedbbba78c005931a81c234b2f6c99a73e4d06082adc8bf2b", "hashType": 1 }, "intermediary": { "internalPubkey": "93478e9488f956df2396be2ce6c5cced75f900dfa18e7dabd2428aae78451820", "tweak": "6af9e28dbf9d6aaf027696e2598a5b3d056f5fd2355a7fd5a37a0e5008132d30", "tweakedPrivkey": "97323385e57015b75b0339a549c56a948eb961555973f0951f555ae6039ef00d", "sigMsg": "0001020000000065cd1de3b33bb4ef3a52ad1fffb555c0d82828eb22737036eaeb02a235d82b909c4c3f58a6964a4f5f8f0b642ded0a8a553be7622a719da71d1f5befcefcdee8e0fde623ad0f61ad2bca5ba6a7693f50fce988e17c3780bf2b1e720cfbb38fbdd52e2118959c7221ab5ce9e26c3cd67b22c24f8baa54bac281d8e6b05e400e6c3a957ea2e6dab7c1f0dcd297c8d61647fd17d821541ea69c3cc37dcbad7f90d4eb4bc50003000000", "precomputedUsed": [ "hashAmounts", "hashOutputs", "hashPrevouts", "hashScriptPubkeys", "hashSequences" ], "sigHash": "bf013ea93474aa67815b1b6cc441d23b64fa310911d991e713cd34c7f5d46669" }, "expected": { "witness": [ "ff45f742a876139946a149ab4d9185574b98dc919d2eb6754f8abaa59d18b025637a3aa043b91817739554f4ed2026cf8022dbd83e351ce1fabc272841d2510a01" ] } }, { "given": { "txinIndex": 4, "internalPrivkey": "f36bb07a11e469ce941d16b63b11b9b9120a84d9d87cff2c84a8d4affb438f4e", "merkleRoot": "ccbd66c6f7e8fdab47b3a486f59d28262be857f30d4773f2d5ea47f7761ce0e2", "hashType": 0 }, "intermediary": { "internalPubkey": "e0dfe2300b0dd746a3f8674dfd4525623639042569d829c7f0eed9602d263e6f", "tweak": "b57bfa183d28eeb6ad688ddaabb265b4a41fbf68e5fed2c72c74de70d5a786f4", "tweakedPrivkey": "a8e7aa924f0d58854185a490e6c41f6efb7b675c0f3331b7f14b549400b4d501", "sigMsg": "0000020000000065cd1de3b33bb4ef3a52ad1fffb555c0d82828eb22737036eaeb02a235d82b909c4c3f58a6964a4f5f8f0b642ded0a8a553be7622a719da71d1f5befcefcdee8e0fde623ad0f61ad2bca5ba6a7693f50fce988e17c3780bf2b1e720cfbb38fbdd52e2118959c7221ab5ce9e26c3cd67b22c24f8baa54bac281d8e6b05e400e6c3a957ea2e6dab7c1f0dcd297c8d61647fd17d821541ea69c3cc37dcbad7f90d4eb4bc50004000000", "precomputedUsed": [ "hashAmounts", "hashOutputs", "hashPrevouts", "hashScriptPubkeys", "hashSequences" ], "sigHash": "4f900a0bae3f1446fd48490c2958b5a023228f01661cda3496a11da502a7f7ef" }, "expected": { "witness": [ "b4010dd48a617db09926f729e79c33ae0b4e94b79f04a1ae93ede6315eb3669de185a17d2b0ac9ee09fd4c64b678a0b61a0a86fa888a273c8511be83bfd6810f" ] } }, { "given": { "txinIndex": 6, "internalPrivkey": "415cfe9c15d9cea27d8104d5517c06e9de48e2f986b695e4f5ffebf230e725d8", "merkleRoot": "2f6b2c5397b6d68ca18e09a3f05161668ffe93a988582d55c6f07bd5b3329def", "hashType": 2 }, "intermediary": { "internalPubkey": "55adf4e8967fbd2e29f20ac896e60c3b0f1d5b0efa9d34941b5958c7b0a0312d", "tweak": "6579138e7976dc13b6a92f7bfd5a2fc7684f5ea42419d43368301470f3b74ed9", "tweakedPrivkey": "241c14f2639d0d7139282aa6abde28dd8a067baa9d633e4e7230287ec2d02901", "sigMsg": "0002020000000065cd1de3b33bb4ef3a52ad1fffb555c0d82828eb22737036eaeb02a235d82b909c4c3f58a6964a4f5f8f0b642ded0a8a553be7622a719da71d1f5befcefcdee8e0fde623ad0f61ad2bca5ba6a7693f50fce988e17c3780bf2b1e720cfbb38fbdd52e2118959c7221ab5ce9e26c3cd67b22c24f8baa54bac281d8e6b05e400e6c3a957e0006000000", "precomputedUsed": [ "hashAmounts", "hashPrevouts", "hashScriptPubkeys", "hashSequences" ], "sigHash": "15f25c298eb5cdc7eb1d638dd2d45c97c4c59dcaec6679cfc16ad84f30876b85" }, "expected": { "witness": [ "a3785919a2ce3c4ce26f298c3d51619bc474ae24014bcdd31328cd8cfbab2eff3395fa0a16fe5f486d12f22a9cedded5ae74feb4bbe5351346508c5405bcfee002" ] } }, { "given": { "txinIndex": 7, "internalPrivkey": "c7b0e81f0a9a0b0499e112279d718cca98e79a12e2f137c72ae5b213aad0d103", "merkleRoot": "6c2dc106ab816b73f9d07e3cd1ef2c8c1256f519748e0813e4edd2405d277bef", "hashType": 130 }, "intermediary": { "internalPubkey": "ee4fe085983462a184015d1f782d6a5f8b9c2b60130aff050ce221ecf3786592", "tweak": "9e0517edc8259bb3359255400b23ca9507f2a91cd1e4250ba068b4eafceba4a9", "tweakedPrivkey": "65b6000cd2bfa6b7cf736767a8955760e62b6649058cbc970b7c0871d786346b", "sigMsg": "0082020000000065cd1d00e9aa6b8e6c9de67619e6a3924ae25696bb7b694bb677a632a74ef7eadfd4eabf00000000804c8b2000000000225120712447206d7a5238acc7ff53fbe94a3b64539ad291c7cdbc490b7577e4b17df5ffffffff", "precomputedUsed": [], "sigHash": "cd292de50313804dabe4685e83f923d2969577191a3e1d2882220dca88cbeb10" }, "expected": { "witness": [ "ea0c6ba90763c2d3a296ad82ba45881abb4f426b3f87af162dd24d5109edc1cdd11915095ba47c3a9963dc1e6c432939872bc49212fe34c632cd3ab9fed429c482" ] } }, { "given": { "txinIndex": 8, "internalPrivkey": "77863416be0d0665e517e1c375fd6f75839544eca553675ef7fdf4949518ebaa", "merkleRoot": "ab179431c28d3b68fb798957faf5497d69c883c6fb1e1cd9f81483d87bac90cc", "hashType": 129 }, "intermediary": { "internalPubkey": "f9f400803e683727b14f463836e1e78e1c64417638aa066919291a225f0e8dd8", "tweak": "639f0281b7ac49e742cd25b7f188657626da1ad169209078e2761cefd91fd65e", "tweakedPrivkey": "ec18ce6af99f43815db543f47b8af5ff5df3b2cb7315c955aa4a86e8143d2bf5", "sigMsg": "0081020000000065cd1da2e6dab7c1f0dcd297c8d61647fd17d821541ea69c3cc37dcbad7f90d4eb4bc500a778eb6a263dc090464cd125c466b5a99667720b1c110468831d058aa1b82af101000000002b0c230000000022512077e30a5522dd9f894c3f8b8bd4c4b2cf82ca7da8a3ea6a239655c39c050ab220ffffffff", "precomputedUsed": [ "hashOutputs" ], "sigHash": "cccb739eca6c13a8a89e6e5cd317ffe55669bbda23f2fd37b0f18755e008edd2" }, "expected": { "witness": [ "bbc9584a11074e83bc8c6759ec55401f0ae7b03ef290c3139814f545b58a9f8127258000874f44bc46db7646322107d4d86aec8e73b8719a61fff761d75b5dd981" ] } } ], "auxiliary": { "fullySignedTx": "020000000001097de20cbff686da83a54981d2b9bab3586f4ca7e48f57f5b55963115f3b334e9c010000000000000000d7b7cab57b1393ace2d064f4d4a2cb8af6def61273e127517d44759b6dafdd990000000000fffffffff8e1f583384333689228c5d28eac13366be082dc57441760d957275419a41842000000006b4830450221008f3b8f8f0537c420654d2283673a761b7ee2ea3c130753103e08ce79201cf32a022079e7ab904a1980ef1c5890b648c8783f4d10103dd62f740d13daa79e298d50c201210279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798fffffffff0689180aa63b30cb162a73c6d2a38b7eeda2a83ece74310fda0843ad604853b0100000000feffffffaa5202bdf6d8ccd2ee0f0202afbbb7461d9264a25e5bfd3c5a52ee1239e0ba6c0000000000feffffff956149bdc66faa968eb2be2d2faa29718acbfe3941215893a2a3446d32acd050000000000000000000e664b9773b88c09c32cb70a2a3e4da0ced63b7ba3b22f848531bbb1d5d5f4c94010000000000000000e9aa6b8e6c9de67619e6a3924ae25696bb7b694bb677a632a74ef7eadfd4eabf0000000000ffffffffa778eb6a263dc090464cd125c466b5a99667720b1c110468831d058aa1b82af10100000000ffffffff0200ca9a3b000000001976a91406afd46bcdfd22ef94ac122aa11f241244a37ecc88ac807840cb0000000020ac9a87f5594be208f8532db38cff670c450ed2fea8fcdefcc9a663f78bab962b0141ed7c1647cb97379e76892be0cacff57ec4a7102aa24296ca39af7541246d8ff14d38958d4cc1e2e478e4d4a764bbfd835b16d4e314b72937b29833060b87276c030141052aedffc554b41f52b521071793a6b88d6dbca9dba94cf34c83696de0c1ec35ca9c5ed4ab28059bd606a4f3a657eec0bb96661d42921b5f50a95ad33675b54f83000141ff45f742a876139946a149ab4d9185574b98dc919d2eb6754f8abaa59d18b025637a3aa043b91817739554f4ed2026cf8022dbd83e351ce1fabc272841d2510a010140b4010dd48a617db09926f729e79c33ae0b4e94b79f04a1ae93ede6315eb3669de185a17d2b0ac9ee09fd4c64b678a0b61a0a86fa888a273c8511be83bfd6810f0247304402202b795e4de72646d76eab3f0ab27dfa30b810e856ff3a46c9a702df53bb0d8cc302203ccc4d822edab5f35caddb10af1be93583526ccfbade4b4ead350781e2f8adcd012102f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f90141a3785919a2ce3c4ce26f298c3d51619bc474ae24014bcdd31328cd8cfbab2eff3395fa0a16fe5f486d12f22a9cedded5ae74feb4bbe5351346508c5405bcfee0020141ea0c6ba90763c2d3a296ad82ba45881abb4f426b3f87af162dd24d5109edc1cdd11915095ba47c3a9963dc1e6c432939872bc49212fe34c632cd3ab9fed429c4820141bbc9584a11074e83bc8c6759ec55401f0ae7b03ef290c3139814f545b58a9f8127258000874f44bc46db7646322107d4d86aec8e73b8719a61fff761d75b5dd9810065cd1d" } } ] } ================================================ FILE: bip-0341.mediawiki ================================================
  BIP: 341
  Layer: Consensus (soft fork)
  Title: Taproot: SegWit version 1 spending rules
  Authors: Pieter Wuille 
           Jonas Nick 
           Anthony Towns 
  Comments-Summary: No comments yet.
  Comments-URI: https://github.com/bitcoin/bips/wiki/Comments:BIP-0341
  Status: Deployed
  Type: Specification
  Assigned: 2020-01-19
  License: BSD-3-Clause
  Discussion: 2019-05-06: https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2019-May/016914.html [bitcoin-dev] Taproot proposal
              2019-10-09: https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2019-October/017378.html [bitcoin-dev] Taproot updates
  Requires: 340
==Introduction== ===Abstract=== This document proposes a new SegWit version 1 output type, with spending rules based on Taproot, Schnorr signatures, and Merkle branches. ===Copyright=== This document is licensed under the 3-clause BSD license. ===Motivation=== This proposal aims to improve privacy, efficiency, and flexibility of Bitcoin's scripting capabilities without adding new security assumptions'''What does not adding security assumptions mean?''' Unforgeability of signatures is a necessary requirement to prevent theft. At least when treating script execution as a digital signature scheme itself, unforgeability can be [https://github.com/apoelstra/taproot proven] in the Random Oracle Model assuming the Discrete Logarithm problem is hard. A [https://nbn-resolving.de/urn:nbn:de:hbz:294-60803 proof] for unforgeability of ECDSA in the current script system needs non-standard assumptions on top of that. Note that it is hard in general to model exactly what security for script means, as it depends on the policies and protocols used by wallet software.. Specifically, it seeks to minimize how much information about the spendability conditions of a transaction output is revealed on chain at creation or spending time and to add a number of upgrade mechanisms, while fixing a few minor but long-standing issues. ==Design== A number of related ideas for improving Bitcoin's scripting capabilities have been previously proposed: Schnorr signatures ([[bip-0340.mediawiki|BIP340]]), Merkle branches ("MAST", [[bip-0114.mediawiki|BIP114]], [[bip-0117.mediawiki|BIP117]]), new sighash modes ([[bip-0118.mediawiki|BIP118]]), new opcodes like CHECKSIGFROMSTACK, [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2018-January/015614.html Taproot], [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2018-February/015700.html Graftroot], [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2018-July/016249.html G'root], and [https://bitcointalk.org/index.php?topic=1377298.0 cross-input aggregation]. Combining all these ideas in a single proposal would be an extensive change, be hard to review, and likely miss new discoveries that otherwise could have been made along the way. Not all are equally mature as well. For example, cross-input aggregation [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2018-March/015838.html interacts] in complex ways with upgrade mechanisms, and solutions to that are still [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2018-October/016461.html in flux]. On the other hand, separating them all into independent upgrades would reduce the efficiency and privacy gains to be had, and wallet and service providers may not be inclined to go through many incremental updates. Therefore, we're faced with a tradeoff between functionality and scope creep. In this design we strike a balance by focusing on the structural script improvements offered by Taproot and Merkle branches, as well as changes necessary to make them usable and efficient. For things like sighashes and opcodes we include fixes for known problems, but exclude new features that can be added independently with no downsides. As a result we choose this combination of technologies: * '''Merkle branches''' let us only reveal the actually executed part of the script to the blockchain, as opposed to all possible ways a script can be executed. Among the various known mechanisms for implementing this, one where the Merkle tree becomes part of the script's structure directly maximizes the space savings, so that approach is chosen. * '''Taproot''' on top of that lets us merge the traditionally separate pay-to-pubkey and pay-to-scripthash policies, making all outputs spendable by either a key or (optionally) a script, and indistinguishable from each other. As long as the key-based spending path is used for spending, it is not revealed whether a script path was permitted as well, resulting in space savings and an increase in scripting privacy at spending time. * Taproot's advantages become apparent under the assumption that most applications involve outputs that could be spent by all parties agreeing. That's where '''Schnorr''' signatures come in, as they permit [https://eprint.iacr.org/2018/068 key aggregation]: a public key can be constructed from multiple participant public keys, and which requires cooperation between all participants to sign for. Such multi-party public keys and signatures are indistinguishable from their single-party equivalents. This means that with taproot most applications can use the key-based spending path, which is both efficient and private. This can be generalized to arbitrary M-of-N policies, as Schnorr signatures support threshold signing, at the cost of more complex setup protocols. * As Schnorr signatures also permit '''batch validation''', allowing multiple signatures to be validated together more efficiently than validating each one independently, we make sure all parts of the design are compatible with this. * Where unused bits appear as a result of the above changes, they are reserved for mechanisms for '''future extensions'''. As a result, every script in the Merkle tree has an associated version such that new script versions can be introduced with a soft fork while remaining compatible with BIP 341. Additionally, future soft forks can make use of the currently unused annex in the witness (see [[bip-0341.mediawiki#rationale|Rationale]]). * While the core semantics of the '''signature hashing algorithm''' are not changed, a number of improvements are included in this proposal. The new signature hashing algorithm fixes the verification capabilities of offline signing devices by including amount and scriptPubKey in the signature message, avoids unnecessary hashing, uses '''tagged hashes''' and defines a default sighash byte. * The '''public key is directly included in the output''' in contrast to typical earlier constructions which store a hash of the public key or script in the output. This has the same cost for senders and is more space efficient overall if the key-based spending path is taken. '''Why is the public key directly included in the output?''' While typical earlier constructions store a hash of a script or a public key in the output, this is rather wasteful when a public key is always involved. To guarantee batch verifiability, the public key must be known to every verifier, and thus only revealing its hash as an output would imply adding an additional 32 bytes to the witness. Furthermore, to maintain [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2016-January/012198.html 128-bit collision security] for outputs, a 256-bit hash would be required anyway, which is comparable in size (and thus in cost for senders) to revealing the public key directly. While the usage of public key hashes is often said to protect against ECDLP breaks or quantum computers, this protection is very weak at best: transactions are not protected while being confirmed, and a very [https://web.archive.org/web/20220531184542/https://twitter.com/pwuille/status/1108085284862713856 large portion] of the currency's supply is not under such protection regardless. Actual resistance to such systems can be introduced by relying on different cryptographic assumptions, but this proposal focuses on improvements that do not change the security model. Informally, the resulting design is as follows: a new witness version is added (version 1), whose programs consist of 32-byte encodings of points ''Q''. ''Q'' is computed as ''P + hash(P||m)G'' for a public key ''P'', and the root ''m'' of a Merkle tree whose leaves consist of a version number and a script. These outputs can be spent directly by providing a signature for ''Q'', or indirectly by revealing ''P'', the script and leaf version, inputs that satisfy the script, and a Merkle path that proves ''Q'' committed to that leaf. All hashes in this construction (the hash for computing ''Q'' from ''P'', the hashes inside the Merkle tree's inner nodes, and the signature hashes used) are tagged to guarantee domain separation. == Specification == This section specifies the Taproot consensus rules. Validity is defined by exclusion: a block or transaction is valid if no condition exists that marks it failed. The notation below follows that of [[bip-0340.mediawiki#design|BIP340]]. This includes the ''hashtag(x)'' notation to refer to ''SHA256(SHA256(tag) || SHA256(tag) || x)''. To the best of the authors' knowledge, no existing use of SHA256 in Bitcoin feeds it a message that starts with two single SHA256 outputs, making collisions between ''hashtag'' with other hashes extremely unlikely. === Script validation rules === A Taproot output is a native SegWit output (see [[bip-0141.mediawiki|BIP141]]) with version number 1, and a 32-byte witness program. The following rules only apply when such an output is being spent. Any other outputs, including version 1 outputs with lengths other than 32 bytes, or P2SH-wrapped version 1 outputs'''Why is P2SH-wrapping not supported?''' Using P2SH-wrapped outputs only provides 80-bit collision security due to the use of a 160-bit hash. This is considered low, and becomes a security risk whenever the output includes data from more than a single party (public keys, hashes, ...)., remain unencumbered. * Let ''q'' be the 32-byte array containing the witness program (the second push in the scriptPubKey) which represents a public key according to [[bip-0340.mediawiki#design|BIP340]]. * Fail if the witness stack has 0 elements. * If there are at least two witness elements, and the first byte of the last element is 0x50'''Why is the first byte of the annex 0x50?''' The 0x50 is chosen as it could not be confused with a valid P2WPKH or P2WSH spending. As the control block's initial byte's lowest bit is used to indicate the parity of the public key's Y coordinate, each leaf version needs an even byte value and the immediately following odd byte value that are both not yet used in P2WPKH or P2WSH spending. To indicate the annex, only an "unpaired" available byte is necessary like 0x50. This choice maximizes the available options for future script versions., this last element is called ''annex'' ''a'''''What is the purpose of the annex?''' The annex is a reserved space for future extensions, such as indicating the validation costs of computationally expensive new opcodes in a way that is recognizable without knowing the scriptPubKey of the output being spent. Until the meaning of this field is defined by another softfork, users SHOULD NOT include annex in transactions, or it may lead to PERMANENT FUND LOSS. and is removed from the witness stack. The annex (or the lack of thereof) is always covered by the signature and contributes to transaction weight, but is otherwise ignored during taproot validation. * If there is exactly one element left in the witness stack, key path spending is used: ** The single witness stack element is interpreted as the signature and must be valid (see the next section) for the public key ''q'' (see the next subsection). * If there are at least two witness elements left, script path spending is used: ** Call the second-to-last stack element ''s'', the script. ** The last stack element is called the control block ''c'', and must have length ''33 + 32m'', for a value of ''m'' that is an integer between 0 and 128'''Why is the Merkle path length limited to 128?''' The optimally space-efficient Merkle tree can be constructed based on the probabilities of the scripts in the leaves, using the Huffman algorithm. This algorithm will construct branches with lengths approximately equal to ''log2(1/probability)'', but to have branches longer than 128 you would need to have scripts with an execution chance below 1 in ''2128''. As that is our security bound, scripts that truly have such a low chance can probably be removed entirely., inclusive. Fail if it does not have such a length. ** Let ''p = c[1:33]'' and let ''P = lift_x(int(p))'' where ''lift_x'' and ''[:]'' are defined as in [[bip-0340.mediawiki#design|BIP340]]. Fail if this point is not on the curve. ** Let ''v = c[0] & 0xfe'' and call it the ''leaf version'''''What constraints are there on the leaf version?''' First, the leaf version cannot be odd as ''c[0] & 0xfe'' will always be even, and cannot be ''0x50'' as that would result in ambiguity with the annex. In addition, in order to support some forms of static analysis that rely on being able to identify script spends without access to the output being spent, it is recommended to avoid using any leaf versions that would conflict with a valid first byte of either a valid P2WPKH pubkey or a valid P2WSH script (that is, both ''v'' and ''v | 1'' should be an undefined, invalid or disabled opcode or an opcode that is not valid as the first opcode). The values that comply to this rule are the 32 even values between ''0xc0'' and ''0xfe'' and also ''0x66'', ''0x7e'', ''0x80'', ''0x84'', ''0x96'', ''0x98'', ''0xba'', ''0xbc'', ''0xbe''. Note also that this constraint implies that leaf versions should be shared amongst different witness versions, as knowing the witness version requires access to the output being spent.. ** Let ''k0 = hashTapLeaf(v || compact_size(size of s) || s)''; also call it the ''tapleaf hash''. ** For ''j'' in ''[0,1,...,m-1]'': *** Let ''ej = c[33+32j:65+32j]''. *** Let ''kj+1 depend on whether ''kj < ej'' (lexicographically)'''Why are child elements sorted before hashing in the Merkle tree?''' By doing so, it is not necessary to reveal the left/right directions along with the hashes in revealed Merkle branches. This is possible because we do not actually care about the position of specific scripts in the tree; only that they are actually committed to.: **** If ''kj < ej'': ''kj+1 = hashTapBranch(kj || ej)'''''Why not use a more efficient hash construction for inner Merkle nodes?''' The chosen construction does require two invocations of the SHA256 compression functions, one of which can be avoided in theory (see [[bip-0098.mediawiki|BIP98]]). However, it seems preferable to stick to constructions that can be implemented using standard cryptographic primitives, both for implementation simplicity and analyzability. If necessary, a significant part of the second compression function can be optimized out by [https://github.com/bitcoin/bitcoin/pull/13191 specialization] for 64-byte inputs.. **** If ''kj ≥ ej'': ''kj+1 = hashTapBranch(ej || kj)''. ** Let ''t = hashTapTweak(p || km)''. ** If ''t ≥ 0xFFFFFFFF FFFFFFFF FFFFFFFF FFFFFFFE BAAEDCE6 AF48A03B BFD25E8C D0364141'' (order of secp256k1), fail. ** Let ''Q = P + int(t)G''. ** If ''q ≠ x(Q)'' or ''c[0] & 1 ≠ y(Q) mod 2'', fail'''Why is it necessary to reveal a bit in a script path spend and check that it matches the parity of the Y coordinate of ''Q''?''' The parity of the Y coordinate is necessary to lift the X coordinate ''q'' to a unique point. While this is not strictly necessary for verifying the taproot commitment as described above, it is necessary to allow batch verification. Alternatively, ''Q'' could be forced to have an even Y coordinate, but that would require retrying with different internal public keys (or different messages) until ''Q'' has that property. There is no downside to adding the parity bit because otherwise the control block bit would be unused.. ** Execute the script, according to the applicable script rules'''What are the applicable script rules in script path spends?''' [[bip-0342.mediawiki|BIP342]] specifies validity rules that apply for leaf version 0xc0, but future proposals can introduce rules for other leaf versions., using the witness stack elements excluding the script ''s'', the control block ''c'', and the annex ''a'' if present, as initial stack. This implies that for the future leaf versions (non-''0xC0'') the execution must succeed.'''Why we need to success on future leaf version validation''' This is required to enable future leaf versions as soft forks. ''q'' is referred to as ''taproot output key'' and ''p'' as ''taproot internal key''. === Signature validation rules === We first define a reusable common signature message calculation function, followed by the actual signature validation as it's used in key path spending. ==== Common signature message ==== The function ''SigMsg(hash_type, ext_flag)'' computes the common portion of the message being signed as a byte array. It is implicitly also a function of the spending transaction and the outputs it spends, but these are not listed to keep notation simple. The parameter ''hash_type'' is an 8-bit unsigned value. The SIGHASH encodings from the legacy script system are reused, including SIGHASH_ALL, SIGHASH_NONE, SIGHASH_SINGLE, and SIGHASH_ANYONECANPAY. We define a new ''hashtype'' SIGHASH_DEFAULT (value ''0x00'') which results in signing over the whole transaction just as for SIGHASH_ALL. The following restrictions apply, which cause validation failure if violated: * Using any undefined ''hash_type'' (not ''0x00'', ''0x01'', ''0x02'', ''0x03'', ''0x81'', ''0x82'', or ''0x83'''''Why reject unknown ''hash_type'' values?''' By doing so, it is easier to reason about the worst case amount of signature hashing an implementation with adequate caching must perform.). * Using SIGHASH_SINGLE without a "corresponding output" (an output with the same index as the input being verified). The parameter ''ext_flag'' is an integer in range 0-127, and is used for indicating (in the message) that extensions are appended to the output of ''SigMsg()'''''What extensions use the ''ext_flag'' mechanism?''' [[bip-0342.mediawiki#common-signature-message-extension|BIP342]] reuses the same common signature message algorithm, but adds BIP342-specific data at the end, which is indicated using ''ext_flag = 1''.. If the parameters take acceptable values, the message is the concatenation of the following data, in order (with byte size of each item listed in parentheses). Numerical values in 2, 4, or 8-byte are encoded in little-endian. * Control: ** ''hash_type'' (1). * Transaction data: ** ''nVersion'' (4): the ''nVersion'' of the transaction. ** ''nLockTime'' (4): the ''nLockTime'' of the transaction. ** If the ''hash_type & 0x80'' does not equal SIGHASH_ANYONECANPAY: *** ''sha_prevouts'' (32): the SHA256 of the serialization of all input outpoints. *** ''sha_amounts'' (32): the SHA256 of the serialization of all input amounts. *** ''sha_scriptpubkeys'' (32): the SHA256 of all spent outputs' ''scriptPubKeys'', serialized as script inside CTxOut. *** ''sha_sequences'' (32): the SHA256 of the serialization of all input ''nSequence''. ** If ''hash_type & 3'' does not equal SIGHASH_NONE or SIGHASH_SINGLE: *** ''sha_outputs'' (32): the SHA256 of the serialization of all outputs in CTxOut format. * Data about this input: ** ''spend_type'' (1): equal to ''(ext_flag * 2) + annex_present'', where ''annex_present'' is 0 if no annex is present, or 1 otherwise (the original witness stack has two or more witness elements, and the first byte of the last element is ''0x50'') ** If ''hash_type & 0x80'' equals SIGHASH_ANYONECANPAY: *** ''outpoint'' (36): the COutPoint of this input (32-byte hash + 4-byte little-endian). *** ''amount'' (8): value of the previous output spent by this input. *** ''scriptPubKey'' (35): ''scriptPubKey'' of the previous output spent by this input, serialized as script inside CTxOut. Its size is always 35 bytes. *** ''nSequence'' (4): ''nSequence'' of this input. ** If ''hash_type & 0x80'' does not equal SIGHASH_ANYONECANPAY: *** ''input_index'' (4): index of this input in the transaction input vector. Index of the first input is 0. ** If an annex is present (the lowest bit of ''spend_type'' is set): *** ''sha_annex'' (32): the SHA256 of ''(compact_size(size of annex) || annex)'', where ''annex'' includes the mandatory ''0x50'' prefix. * Data about this output: ** If ''hash_type & 3'' equals SIGHASH_SINGLE: *** ''sha_single_output'' (32): the SHA256 of the corresponding output in CTxOut format. The total length of ''SigMsg()'' is at most ''206'' bytes'''What is the output length of ''SigMsg()''?''' The total length of ''SigMsg()'' can be computed using the following formula: ''174 - is_anyonecanpay * 49 - is_none * 32 + has_annex * 32''.. Note that this does not include the size of sub-hashes such as ''sha_prevouts'', which may be cached across signatures of the same transaction. In summary, the semantics of the [[bip-0143.mediawiki|BIP143]] sighash types remain unchanged, except the following: # The way and order of serialization is changed.'''Why is the serialization in the signature message changed?''' Hashes that go into the signature message and the message itself are now computed with a single SHA256 invocation instead of double SHA256. There is no expected security improvement by doubling SHA256 because this only protects against length-extension attacks against SHA256 which are not a concern for signature messages because there is no secret data. Therefore doubling SHA256 is a waste of resources. The message computation now follows a logical order with transaction level data first, then input data and output data. This allows to efficiently cache the transaction part of the message across different inputs using the SHA256 midstate. Additionally, sub-hashes can be skipped when calculating the message (for example `sha_prevouts` if SIGHASH_ANYONECANPAY is set) instead of setting them to zero and then hashing them as in BIP143. Despite that, collisions are made impossible by committing to the length of the data (implicit in ''hash_type'' and ''spend_type'') before the variable length data. # The signature message commits to the ''scriptPubKey'' of the spent output and if the SIGHASH_ANYONECANPAY flag is not set, the message commits to the ''scriptPubKey''s of ''all'' outputs spent by the transaction. '''Why does the signature message commit to the ''scriptPubKey''?''' This prevents lying to offline signing devices about output being spent, even when the actually executed script (''scriptCode'' in BIP143) is correct. This means it's possible to compactly prove to a hardware wallet what (unused) execution paths existed. Moreover, committing to all spent ''scriptPubKey''s helps offline signing devices to determine the subset that belong to its own wallet. This is useful in [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2020-April/017801.html automated coinjoins].. # If the SIGHASH_ANYONECANPAY flag is not set, the message commits to the amounts of ''all'' transaction inputs.'''Why does the signature message commit to the amounts of all transaction inputs?''' This eliminates the possibility to lie to offline signing devices about the fee of a transaction. # The signature message commits to all input ''nSequence'' if SIGHASH_NONE or SIGHASH_SINGLE are set (unless SIGHASH_ANYONECANPAY is set as well).'''Why does the signature message commit to all input ''nSequence'' if SIGHASH_SINGLE or SIGHASH_NONE are set?''' Because setting them already makes the message commit to the prevouts part of all transaction inputs, it is not useful to treat the ''nSequence'' any different. Moreover, this change makes ''nSequence'' consistent with the view that SIGHASH_SINGLE and SIGHASH_NONE only modify the signature message with respect to transaction outputs and not inputs. # The signature message includes commitments to the taproot-specific data ''spend_type'' and ''annex'' (if present). ==== Taproot key path spending signature validation ==== A Taproot signature is a 64-byte Schnorr signature, as defined in [[bip-0340.mediawiki|BIP340]], with the sighash byte appended in the usual Bitcoin fashion. This sighash byte is optional. If omitted, the resulting signatures are 64 bytes, and a SIGHASH_DEFAULT mode is implied. To validate a signature ''sig'' with public key ''q'': * If the ''sig'' is 64 bytes long, return ''Verify(q, hashTapSighash(0x00 || SigMsg(0x00, 0)), sig)'''''Why is the input to ''hashTapSighash'' prefixed with 0x00?''' This prefix is called the sighash epoch, and allows reusing the ''hashTapSighash'' tagged hash in future signature algorithms that make invasive changes to how hashing is performed (as opposed to the ''ext_flag'' mechanism that is used for incremental extensions). An alternative is having them use a different tag, but supporting a growing number of tags may become undesirable., where ''Verify'' is defined in [[bip-0340.mediawiki#design|BIP340]]. * If the ''sig'' is 65 bytes long, return ''sig[64] ≠ 0x00'''Why can the hash_type not be 0x00 in 65-byte signatures?''' Permitting that would enable malleating (by third parties, including miners) 64-byte signatures into 65-byte ones, resulting in a different `wtxid` and a different fee rate than the creator intended. and Verify(q, hashTapSighash(0x00 || SigMsg(sig[64], 0)), sig[0:64])''. * Otherwise, fail'''Why permit two signature lengths?''' By making the most common type of hash_type implicit, a byte can often be saved.. == Constructing and spending Taproot outputs == This section discusses how to construct and spend Taproot outputs. It only affects wallet software that chooses to implement receiving and spending, and is not consensus critical in any way. Conceptually, every Taproot output corresponds to a combination of a single public key condition (the internal key), and zero or more general conditions encoded in scripts organized in a tree. Satisfying any of these conditions is sufficient to spend the output. '''Initial steps''' The first step is determining what the internal key and the organization of the rest of the scripts should be. The specifics are likely application dependent, but here are some general guidelines: * When deciding between scripts with conditionals (OP_IF etc.) and splitting them up into multiple scripts (each corresponding to one execution path through the original script), it is generally preferable to pick the latter. * When a single condition requires signatures with multiple keys, key aggregation techniques like MuSig can be used to combine them into a single key. The details are out of scope for this document, but note that this may complicate the signing procedure. * If one or more of the spending conditions consist of just a single key (after aggregation), the most likely one should be made the internal key. If no such condition exists, it may be worthwhile adding one that consists of an aggregation of all keys participating in all scripts combined; effectively adding an "everyone agrees" branch. If that is inacceptable, pick as internal key a "Nothing Up My Sleeve" (NUMS) point, i.e., a point with unknown discrete logarithm. One example of such a point is ''H = lift_x(0x50929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac0)'' which is [https://github.com/ElementsProject/secp256k1-zkp/blob/11af7015de624b010424273be3d91f117f172c82/src/modules/rangeproof/main_impl.h#L16 constructed] by taking the hash of the standard uncompressed encoding of the [https://www.secg.org/sec2-v2.pdf secp256k1] base point ''G'' as X coordinate. In order to avoid leaking the information that key path spending is not possible it is recommended to pick a fresh integer ''r'' in the range ''0...n-1'' uniformly at random and use ''H + rG'' as internal key. It is possible to prove that this internal key does not have a known discrete logarithm with respect to ''G'' by revealing ''r'' to a verifier who can then reconstruct how the internal key was created. * If the spending conditions do not require a script path, the output key should commit to an unspendable script path instead of having no script path. This can be achieved by computing the output key point as ''Q = P + int(hashTapTweak(bytes(P)))G''. '''Why should the output key always have a taproot commitment, even if there is no script path?''' If the taproot output key is an aggregate of keys, there is the possibility for a malicious party to add a script path without being noticed by the other parties. This allows to bypass the multiparty policy and to steal the coin. MuSig key aggregation does not have this issue because it already causes the internal key to be randomized. The attack works as follows: Assume Alice and Mallory want to aggregate their keys into a taproot output key without a script path. In order to prevent key cancellation and related attacks they use [https://eprint.iacr.org/2018/483.pdf MSDL-pop] instead of MuSig. The MSDL-pop protocol requires all parties to provide a proof of possession of their corresponding secret key and the aggregated key is just the sum of the individual keys. After Mallory receives Alice's key ''A'', Mallory creates ''M = M0 + int(t)G'' where ''M0'' is Mallory's original key and ''t'' allows a script path spend with internal key ''P = A + M0'' and a script that only contains Mallory's key. Mallory sends a proof of possession of ''M'' to Alice and both parties compute output key ''Q = A + M = P + int(t)G''. Alice will not be able to notice the script path, but Mallory can unilaterally spend any coin with output key ''Q''. * The remaining scripts should be organized into the leaves of a binary tree. This can be a balanced tree if each of the conditions these scripts correspond to are equally likely. If probabilities for each condition are known, consider constructing the tree as a Huffman tree. '''Computing the output script''' Once the spending conditions are split into an internal key internal_pubkey and a binary tree whose leaves are (leaf_version, script) tuples, the output script can be computed using the Python3 algorithms below. These algorithms take advantage of helper functions from the [[bip-0340/reference.py|BIP340 reference code]] for integer conversion, point multiplication, and tagged hashes. First, we define taproot_tweak_pubkey for 32-byte [[bip-0340.mediawiki|BIP340]] public key arrays. The function returns a bit indicating the tweaked public key's Y coordinate as well as the public key byte array. The parity bit will be required for spending the output with a script path. In order to allow spending with the key path, we define taproot_tweak_seckey to compute the secret key for a tweaked public key. For any byte string h it holds that taproot_tweak_pubkey(pubkey_gen(seckey), h)[1] == pubkey_gen(taproot_tweak_seckey(seckey, h)). Note that because tweaks are applied to 32-byte public keys, `taproot_tweak_seckey` may need to negate the secret key before applying the tweak. def taproot_tweak_pubkey(pubkey, h): t = int_from_bytes(tagged_hash("TapTweak", pubkey + h)) if t >= SECP256K1_ORDER: raise ValueError P = lift_x(int_from_bytes(pubkey)) if P is None: raise ValueError Q = point_add(P, point_mul(G, t)) return 0 if has_even_y(Q) else 1, bytes_from_int(x(Q)) def taproot_tweak_seckey(seckey0, h): seckey0 = int_from_bytes(seckey0) P = point_mul(G, seckey0) seckey = seckey0 if has_even_y(P) else SECP256K1_ORDER - seckey0 t = int_from_bytes(tagged_hash("TapTweak", bytes_from_int(x(P)) + h)) if t >= SECP256K1_ORDER: raise ValueError return bytes_from_int((seckey + t) % SECP256K1_ORDER) The following function, taproot_output_script, returns a byte array with the scriptPubKey (see [[bip-0141.mediawiki|BIP141]]). ser_script refers to a function that prefixes its input with a CompactSize-encoded length. def taproot_tree_helper(script_tree): if isinstance(script_tree, tuple): leaf_version, script = script_tree h = tagged_hash("TapLeaf", bytes([leaf_version]) + ser_script(script)) return ([((leaf_version, script), bytes())], h) left, left_h = taproot_tree_helper(script_tree[0]) right, right_h = taproot_tree_helper(script_tree[1]) ret = [(l, c + right_h) for l, c in left] + [(l, c + left_h) for l, c in right] if right_h < left_h: left_h, right_h = right_h, left_h return (ret, tagged_hash("TapBranch", left_h + right_h)) def taproot_output_script(internal_pubkey, script_tree): """Given a internal public key and a tree of scripts, compute the output script. script_tree is either: - a (leaf_version, script) tuple (leaf_version is 0xc0 for [[bip-0342.mediawiki|BIP342]] scripts) - a list of two elements, each with the same structure as script_tree itself - None """ if script_tree is None: h = bytes() else: _, h = taproot_tree_helper(script_tree) _, output_pubkey = taproot_tweak_pubkey(internal_pubkey, h) return bytes([0x51, 0x20]) + output_pubkey [[File:bip-0341/tree.png|frame|This diagram shows the hashing structure to obtain the tweak from an internal key ''P'' and a Merkle tree consisting of 5 script leaves. ''A'', ''B'', ''C'' and ''E'' are ''TapLeaf'' hashes similar to ''D'' and ''AB'' is a ''TapBranch'' hash. Note that when ''CDE'' is computed ''E'' is hashed first because ''E'' is less than ''CD''.]] To spend this output using script ''D'', the control block would contain the following data in this order: The TapTweak would then be computed as described [[bip-0341.mediawiki#script-validation-rules|above]] like so: D = tagged_hash("TapLeaf", bytes([leaf_version]) + ser_script(script)) CD = tagged_hash("TapBranch", C + D) CDE = tagged_hash("TapBranch", E + CD) ABCDE = tagged_hash("TapBranch", AB + CDE) TapTweak = tagged_hash("TapTweak", p + ABCDE) '''Spending using the key path''' A Taproot output can be spent with the secret key corresponding to the internal_pubkey. To do so, a witness stack consists of a single element: a [[bip-0340.mediawiki|BIP340]] signature on the signature hash as defined above, with the secret key tweaked by the same h as in the above snippet. See the code below: def taproot_sign_key(script_tree, internal_seckey, hash_type, bip340_aux_rand): if script_tree is None: h = bytes() else: _, h = taproot_tree_helper(script_tree) output_seckey = taproot_tweak_seckey(internal_seckey, h) sig = schnorr_sign(sighash(hash_type), output_seckey, bip340_aux_rand) if hash_type != 0: sig += bytes([hash_type]) return [sig] This function returns the witness stack necessary and a sighash function to compute the signature hash as defined above (for simplicity, the snippet above ignores passing information like the transaction, the input position, ... to the sighashing code). '''Spending using one of the scripts''' A Taproot output can be spent by satisfying any of the scripts used in its construction. To do so, a witness stack consisting of the script's inputs, plus the script itself and the control block are necessary. See the code below: def taproot_sign_script(internal_pubkey, script_tree, script_num, inputs): info, h = taproot_tree_helper(script_tree) (leaf_version, script), path = info[script_num] output_pubkey_y_parity, _ = taproot_tweak_pubkey(internal_pubkey, h) pubkey_data = bytes([output_pubkey_y_parity + leaf_version]) + internal_pubkey return inputs + [script, pubkey_data + path] == Security == Taproot improves the privacy of Bitcoin because instead of revealing all possible conditions for spending an output, only the satisfied spending condition has to be published. Ideally, outputs are spent using the key path which prevents observers from learning the spending conditions of a coin. A key path spend could be a "normal" payment from a single- or multi-signature wallet or the cooperative settlement of hidden multiparty contract. A script path spend leaks that there is a script path and that the key path was not applicable - for example because the involved parties failed to reach agreement. Moreover, the depth of a script in the Merkle root leaks information including the minimum depth of the tree, which suggests specific wallet software that created the output and helps clustering. Therefore, the privacy of script spends can be improved by deviating from the optimal tree determined by the probability distribution over the leaves. Just like other existing output types, taproot outputs should never reuse keys, for privacy reasons. This does not only apply to the particular leaf that was used to spend an output but to all leaves committed to in the output. If leaves were reused, it could happen that spending a different output would reuse the same Merkle branches in the Merkle proof. Using fresh keys implies that taproot output construction does not need to take special measures to randomizing leaf positions because they are already randomized due to the branch-sorting Merkle tree construction used in taproot. This does not avoid leaking information through the leaf depth and therefore only applies to balanced (sub-) trees. In addition, every leaf should have a set of keys distinct from every other leaf. The reason for this is to increase leaf entropy and prevent an observer from learning an undisclosed script using brute-force search. == Test vectors == Test vectors for wallet operation (scriptPubKey computation, key path spending, control block construction) can be found [[bip-0341/wallet-test-vectors.json|here]]. It consists of two sets of vectors. * The first "scriptPubKey" tests concern computing the scriptPubKey and (mainnet) BIP350 address given an internal public key, and a script tree. The script tree is encoded as null to represent no scripts, a JSON object to represent a leaf node, or a 2-element array to represent an inner node. The control blocks needed for script path spending are also provided for each of the script leaves. * The second "keyPathSpending" tests consists of a list of test cases, each of which provides an unsigned transaction and the UTXOs it spends. For each of its BIP341 inputs, the internal private key and the Merkle root it was derived from is given, as well as the expected witness to spend it. All signatures are created with an all-zero (0x0000...0000) BIP340 auxiliary randomness array. * In all cases, hexadecimal values represent byte arrays, not numbers. In particular, that means that provided hash values have the hex digits corresponding to the first bytes first. This differs from the convention used for txids and block hashes, where the hex strings represent numbers, resulting in a reversed order. Validation test vectors used in the [https://github.com/bitcoin/bitcoin/blob/3820090bd619ac85ab35eff376c03136fe4a9f04/src/test/script_tests.cpp#L1718 Bitcoin Core unit test framework] can be found [https://github.com/bitcoin-core/qa-assets/blob/main/unit_test_data/script_assets_test.json?raw=true here]. == Rationale == == Deployment == This BIP is deployed concurrently with [[bip-0342.mediawiki|BIP342]]. For Bitcoin signet, these BIPs are always active. For Bitcoin mainnet and testnet3, these BIPs are deployed by "version bits" with the name "taproot" and bit 2, using [[bip-0009.mediawiki|BIP9]] modified to use a lower threshold, with an additional ''min_activation_height'' parameter and replacing the state transition logic for the DEFINED, STARTED and LOCKED_IN states as follows: case DEFINED: if (GetMedianTimePast(block.parent) >= starttime) { return STARTED; } return DEFINED; case STARTED: int count = 0; walk = block; for (i = 0; i < 2016; i++) { walk = walk.parent; if ((walk.nVersion & 0xE0000000) == 0x20000000 && ((walk.nVersion >> bit) & 1) == 1) { count++; } } if (count >= threshold) { return LOCKED_IN; } else if (GetMedianTimePast(block.parent) >= timeout) { return FAILED; } return STARTED; case LOCKED_IN: if (block.nHeight < min_activation_height) { return LOCKED_IN; } return ACTIVE; For Bitcoin mainnet, the starttime is epoch timestamp 1619222400 (midnight 24 April 2021 UTC), timeout is epoch timestamp 1628640000 (midnight 11 August 2021 UTC), the threshold is 1815 blocks (90%) instead of 1916 blocks (95%), and the min_activation_height is block 709632. The deployment did activate at height 709632 on Bitcoin mainnet. For Bitcoin testnet3, the starttime is epoch timestamp 1619222400 (midnight 24 April 2021 UTC), timeout is epoch timestamp 1628640000 (midnight 11 August 2021 UTC), the threshold is 1512 blocks (75%), and the min_activation_height is block 0. The deployment did activate at height 2011968 on Bitcoin testnet3. == Backwards compatibility == As a soft fork, older software will continue to operate without modification. Non-upgraded nodes, however, will consider all SegWit version 1 witness programs as anyone-can-spend scripts. They are strongly encouraged to upgrade in order to fully validate the new programs. Non-upgraded wallets can receive and send bitcoin from non-upgraded and upgraded wallets using SegWit version 0 programs, traditional pay-to-pubkey-hash, etc. Depending on the implementation non-upgraded wallets may be able to send to Segwit version 1 programs if they support sending to [[bip-0350.mediawiki|BIP350]] Bech32m addresses. == Acknowledgements == This document is the result of discussions around script and signature improvements with many people, and had direct contributions from Greg Maxwell and others. It further builds on top of earlier published proposals such as Taproot by Greg Maxwell, and Merkle branch constructions by Russell O'Connor, Johnson Lau, and Mark Friedenbach. The authors wish the thank Arik Sosman for suggesting to sort Merkle node children before hashes, removing the need to transfer the position in the tree, as well as all those who provided valuable feedback and reviews, including the participants of the [https://github.com/ajtowns/taproot-review structured reviews]. ================================================ FILE: bip-0342.mediawiki ================================================
  BIP: 342
  Layer: Consensus (soft fork)
  Title: Validation of Taproot Scripts
  Authors: Pieter Wuille 
           Jonas Nick 
           Anthony Towns 
  Status: Deployed
  Type: Specification
  Assigned: 2020-01-19
  License: BSD-3-Clause
  Discussion: 2019-05-06: https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2019-May/016914.html [bitcoin-dev] Taproot proposal
  Requires: 340, 341
==Introduction== ===Abstract=== This document specifies the semantics of the initial scripting system under [[bip-0341.mediawiki|BIP341]]. ===Copyright=== This document is licensed under the 3-clause BSD license. ===Motivation=== [[bip-0341.mediawiki|BIP341]] proposes improvements to just the script structure, but some of its goals are incompatible with the semantics of certain opcodes within the scripting language itself. While it is possible to deal with these in separate optional improvements, their impact is not guaranteed unless they are addressed simultaneously with [[bip-0341.mediawiki|BIP341]] itself. Specifically, the goal is making '''Schnorr signatures''', '''batch validation''', and '''signature hash''' improvements available to spends that use the script system as well. ==Design== In order to achieve these goals, signature opcodes OP_CHECKSIG and OP_CHECKSIGVERIFY are modified to verify Schnorr signatures as specified in [[bip-0340.mediawiki|BIP340]] and to use a signature message algorithm based on the common message calculation in [[bip-0341.mediawiki|BIP341]]. The tapscript signature message also simplifies OP_CODESEPARATOR handling and makes it more efficient. The inefficient OP_CHECKMULTISIG and OP_CHECKMULTISIGVERIFY opcodes are disabled. Instead, a new opcode OP_CHECKSIGADD is introduced to allow creating the same multisignature policies in a batch-verifiable way. Tapscript uses a new, simpler signature opcode limit fixing complicated interactions with transaction weight. Furthermore, a potential malleability vector is eliminated by requiring MINIMALIF. Tapscript can be upgraded through soft forks by defining unknown key types, for example to add new hash_types or signature algorithms. Additionally, the new tapscript OP_SUCCESS opcodes allow introducing new opcodes more cleanly than through OP_NOP. ==Specification== The rules below only apply when validating a transaction input for which all of the conditions below are true: * The transaction input is a '''segregated witness spend''' (i.e., the scriptPubKey contains a witness program as defined in [[bip-0141.mediawiki|BIP141]]). * It is a '''taproot spend''' as defined in [[bip-0341.mediawiki#design|BIP341]] (i.e., the witness version is 1, the witness program is 32 bytes, and it is not P2SH wrapped). * It is a '''script path spend''' as defined in [[bip-0341.mediawiki#design|BIP341]] (i.e., after removing the optional annex from the witness stack, two or more stack elements remain). * The leaf version is ''0xc0'' (i.e. the first byte of the last witness element after removing the optional annex is ''0xc0'' or ''0xc1''), marking it as a '''tapscript spend'''. Validation of such inputs must be equivalent to performing the following steps in the specified order. # If the input is invalid due to BIP141 or BIP341, fail. # The script as defined in BIP341 (i.e., the penultimate witness stack element after removing the optional annex) is called the '''tapscript''' and is decoded into opcodes, one by one: ## If any opcode numbered ''80, 98, 126-129, 131-134, 137-138, 141-142, 149-153, 187-254'' is encountered, validation succeeds (none of the rules below apply). This is true even if later bytes in the tapscript would fail to decode otherwise. These opcodes are renamed to OP_SUCCESS80, ..., OP_SUCCESS254, and collectively known as OP_SUCCESSx'''OP_SUCCESSx''' OP_SUCCESSx is a mechanism to upgrade the Script system. Using an OP_SUCCESSx before its meaning is defined by a softfork is insecure and leads to fund loss. The inclusion of OP_SUCCESSx in a script will pass it unconditionally. It precedes any script execution rules to avoid the difficulties in specifying various edge cases, for example: OP_SUCCESSx in a script with an input stack larger than 1000 elements, OP_SUCCESSx after too many signature opcodes, or even scripts with conditionals lacking OP_ENDIF. The mere existence of an OP_SUCCESSx anywhere in the script will guarantee a pass for all such cases. OP_SUCCESSx are similar to the OP_RETURN in very early bitcoin versions (v0.1 up to and including v0.3.5). The original OP_RETURN terminates script execution immediately, and return pass or fail based on the top stack element at the moment of termination. This was one of a major design flaws in the original bitcoin protocol as it permitted unconditional third party theft by placing an OP_RETURN in scriptSig. This is not a concern in the present proposal since it is not possible for a third party to inject an OP_SUCCESSx to the validation process, as the OP_SUCCESSx is part of the script (and thus committed to by the taproot output), implying the consent of the coin owner. OP_SUCCESSx can be used for a variety of upgrade possibilities: * An OP_SUCCESSx could be turned into a functional opcode through a softfork. Unlike OP_NOPx-derived opcodes which only have read-only access to the stack, OP_SUCCESSx may also write to the stack. Any rule changes to an OP_SUCCESSx-containing script may only turn a valid script into an invalid one, and this is always achievable with softforks. * Since OP_SUCCESSx precedes size check of initial stack and push opcodes, an OP_SUCCESSx-derived opcode requiring stack elements bigger than 520 bytes may uplift the limit in a softfork. * OP_SUCCESSx may also redefine the behavior of existing opcodes so they could work together with the new opcode. For example, if an OP_SUCCESSx-derived opcode works with 64-bit integers, it may also allow the existing arithmetic opcodes in the ''same script'' to do the same. * Given that OP_SUCCESSx even causes potentially unparseable scripts to pass, it can be used to introduce multi-byte opcodes, or even a completely new scripting language when prefixed with a specific OP_SUCCESSx opcode.. ## If any push opcode fails to decode because it would extend past the end of the tapscript, fail. # If the '''initial stack''' as defined in BIP341 (i.e., the witness stack after removing both the optional annex and the two last stack elements after that) violates any resource limits (stack size, and size of the elements in the stack; see "Resource Limits" below), fail. Note that this check can be bypassed using OP_SUCCESSx. # The tapscript is executed according to the rules in the following section, with the initial stack as input. ## If execution fails for any reason, fail. ## If the execution results in anything but exactly one element on the stack which evaluates to true with CastToBool(), fail. # If this step is reached without encountering a failure, validation succeeds. ===Script execution=== The execution rules for tapscript are based on those for P2WSH according to BIP141, including the OP_CHECKLOCKTIMEVERIFY and OP_CHECKSEQUENCEVERIFY opcodes defined in [[bip-0065.mediawiki|BIP65]] and [[bip-0112.mediawiki|BIP112]], but with the following modifications: * '''Disabled script opcodes''' The following script opcodes are disabled in tapscript: OP_CHECKMULTISIG and OP_CHECKMULTISIGVERIFY'''Why are OP_CHECKMULTISIG and OP_CHECKMULTISIGVERIFY disabled, and not turned into OP_SUCCESSx?''' This is a precaution to make sure people who accidentally keep using OP_CHECKMULTISIG in Tapscript notice a problem immediately. It also avoids the complication of script disassemblers needing to become context-dependent.. The disabled opcodes behave in the same way as OP_RETURN, by failing and terminating the script immediately when executed, and being ignored when found in unexecuted branch of the script. * '''Consensus-enforced MINIMALIF''' The MINIMALIF rules, which are only a standardness rule in P2WSH, are consensus enforced in tapscript. This means that the input argument to the OP_IF and OP_NOTIF opcodes must be either exactly 0 (the empty vector) or exactly 1 (the one-byte vector with value 1)'''Why make MINIMALIF consensus?''' This makes it considerably easier to write non-malleable scripts that take branch information from the stack.. * '''OP_SUCCESSx opcodes''' As listed above, some opcodes are renamed to OP_SUCCESSx, and make the script unconditionally valid. * '''Signature opcodes'''. The OP_CHECKSIG and OP_CHECKSIGVERIFY are modified to operate on Schnorr public keys and signatures (see [[bip-0340.mediawiki|BIP340]]) instead of ECDSA, and a new opcode OP_CHECKSIGADD is added. ** The opcode 186 (0xba) is named as OP_CHECKSIGADD. '''OP_CHECKSIGADD''' This opcode is added to compensate for the loss of OP_CHECKMULTISIG-like opcodes, which are incompatible with batch verification. OP_CHECKSIGADD is functionally equivalent to OP_ROT OP_SWAP OP_CHECKSIG OP_ADD, but only takes 1 byte. All CScriptNum-related behaviours of OP_ADD are also applicable to OP_CHECKSIGADD.'''Alternatives to CHECKMULTISIG''' There are multiple ways of implementing a threshold ''k''-of-''n'' policy using Taproot and Tapscript: * '''Using a single OP_CHECKSIGADD-based script''' A CHECKMULTISIG script m ... n CHECKMULTISIG with witness 0 ... can be rewritten as script CHECKSIG CHECKSIGADD ... CHECKSIGADD m NUMEQUAL with witness ... . Every witness element w_i is either a signature corresponding to pubkey_i or an empty vector. A similar CHECKMULTISIGVERIFY script can be translated to BIP342 by replacing NUMEQUAL with NUMEQUALVERIFY. This approach has very similar characteristics to the existing OP_CHECKMULTISIG-based scripts. * '''Using a ''k''-of-''k'' script for every combination''' A ''k''-of-''n'' policy can be implemented by splitting the script into several leaves of the Merkle tree, each implementing a ''k''-of-''k'' policy using CHECKSIGVERIFY ... CHECKSIGVERIFY CHECKSIG. This may be preferable for privacy reasons over the previous approach, as it only exposes the participating public keys, but it is only more cost effective for small values of ''k'' (1-of-''n'' for any ''n'', 2-of-''n'' for ''n ≥ 6'', 3-of-''n'' for ''n ≥ 9'', ...). Furthermore, the signatures here commit to the branch used, which means signers need to be aware of which other signers will be participating, or produce signatures for each of the tree leaves. * '''Using an aggregated public key for every combination''' Instead of building a tree where every leaf consists of ''k'' public keys, it is possible instead build a tree where every leaf contains a single ''aggregate'' of those ''k'' keys using [https://eprint.iacr.org/2018/068 MuSig]. This approach is far more efficient, but does require a 3-round interactive signing protocol to jointly produce the (single) signature. * '''Native Schnorr threshold signatures''' Multisig policies can also be realized with [http://cacr.uwaterloo.ca/techreports/2001/corr2001-13.ps threshold signatures] using verifiable secret sharing. This results in outputs and inputs that are indistinguishable from single-key payments, but at the cost of needing an interactive protocol (and associated backup procedures) before determining the address to send to. ===Rules for signature opcodes=== The following rules apply to OP_CHECKSIG, OP_CHECKSIGVERIFY, and OP_CHECKSIGADD. * For OP_CHECKSIGVERIFY and OP_CHECKSIG, the public key (top element) and a signature (second to top element) are popped from the stack. ** If fewer than 2 elements are on the stack, the script MUST fail and terminate immediately. * For OP_CHECKSIGADD, the public key (top element), a CScriptNum n (second to top element), and a signature (third to top element) are popped from the stack. ** If fewer than 3 elements are on the stack, the script MUST fail and terminate immediately. ** If n is larger than 4 bytes, the script MUST fail and terminate immediately. * If the public key size is zero, the script MUST fail and terminate immediately. * If the public key size is 32 bytes, it is considered to be a public key as described in BIP340: ** If the signature is not the empty vector, the signature is validated against the public key (see the next subsection). Validation failure in this case immediately terminates script execution with failure. * If the public key size is not zero and not 32 bytes, the public key is of an ''unknown public key type'''''Unknown public key types''' allow adding new signature validation rules through softforks. A softfork could add actual signature validation which either passes or makes the script fail and terminate immediately. This way, new SIGHASH modes can be added, as well as [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2018-December/016549.html NOINPUT-tagged public keys] and a public key constant which is replaced by the taproot internal key for signature validation. and no actual signature verification is applied. During script execution of signature opcodes they behave exactly as known public key types except that signature validation is considered to be successful. * If the script did not fail and terminate before this step, regardless of the public key type: ** If the signature is the empty vector: *** For OP_CHECKSIGVERIFY, the script MUST fail and terminate immediately. *** For OP_CHECKSIG, an empty vector is pushed onto the stack, and execution continues with the next opcode. *** For OP_CHECKSIGADD, a CScriptNum with value n is pushed onto the stack, and execution continues with the next opcode. ** If the signature is not the empty vector, the opcode is counted towards the sigops budget (see further). *** For OP_CHECKSIGVERIFY, execution continues without any further changes to the stack. *** For OP_CHECKSIG, a 1-byte value 0x01 is pushed onto the stack. *** For OP_CHECKSIGADD, a CScriptNum with value of n + 1 is pushed onto the stack. ===Common Signature Message Extension=== We define the tapscript message extension ''ext'' to [[bip-0341.mediawiki#common-signature-message|BIP341 Common Signature Message]], indicated by ''ext_flag = 1'': * ''tapleaf_hash'' (32): the tapleaf hash as defined in [[bip-0341.mediawiki#design|BIP341]] * ''key_version'' (1): a constant value ''0x00'' representing the current version of public keys in the tapscript signature opcode execution. * ''codesep_pos'' (4): the opcode position of the last executed OP_CODESEPARATOR before the currently executed signature opcode, with the value in little endian (or ''0xffffffff'' if none executed). The first opcode in a script has a position of 0. A multi-byte push opcode is counted as one opcode, regardless of the size of data being pushed. Opcodes in parsed but unexecuted branches count towards this value as well. ===Signature validation=== To validate a signature ''sig'' with public key ''p'': * Compute the tapscript message extension ''ext'' described above. * If the ''sig'' is 64 bytes long, return ''Verify(p, hashTapSighash(0x00 || SigMsg(0x00, 1) || ext), sig)'', where ''Verify'' is defined in [[bip-0340.mediawiki#design|BIP340]]. * If the ''sig'' is 65 bytes long, return ''sig[64] ≠ 0x00 and Verify(p, hashTapSighash(0x00 || SigMsg(sig[64], 1) || ext), sig[0:64])''. * Otherwise, fail. In summary, the semantics of signature validation is identical to BIP340, except the following: # The signature message includes the tapscript-specific data ''key_version''.'''Why does the signature message commit to the ''key_version''?''' This is for future extensions that define unknown public key types, making sure signatures can't be moved from one key type to another. # The signature message commits to the executed script through the ''tapleaf_hash'' which includes the leaf version and script instead of ''scriptCode''. This implies that this commitment is unaffected by OP_CODESEPARATOR. # The signature message includes the opcode position of the last executed OP_CODESEPARATOR.'''Why does the signature message include the position of the last executed OP_CODESEPARATOR?''' This allows continuing to use OP_CODESEPARATOR to sign the executed path of the script. Because the codeseparator_position is the last input to the hash, the SHA256 midstate can be efficiently cached for multiple OP_CODESEPARATORs in a single script. In contrast, the BIP143 handling of OP_CODESEPARATOR is to commit to the executed script only from the last executed OP_CODESEPARATOR onwards which requires unnecessary rehashing of the script. It should be noted that the one known OP_CODESEPARATOR use case of saving a second public key push in a script by sharing the first one between two code branches can be most likely expressed even cheaper by moving each branch into a separate taproot leaf. ===Resource limits=== In addition to changing the semantics of a number of opcodes, there are also some changes to the resource limitations: * '''Script size limit''' The maximum script size of 10000 bytes does not apply. Their size is only implicitly bounded by the block weight limit.'''Why is a limit on script size no longer needed?''' Since there is no scriptCode directly included in the signature hash (only indirectly through a precomputable tapleaf hash), the CPU time spent on a signature check is no longer proportional to the size of the script being executed. * '''Non-push opcodes limit''' The maximum non-push opcodes limit of 201 per script does not apply.'''Why is a limit on the number of opcodes no longer needed?''' An opcode limit only helps to the extent that it can prevent data structures from growing unboundedly during execution (both because of memory usage, and because of time that may grow in proportion to the size of those structures). The size of stack and altstack is already independently limited. By using O(1) logic for OP_IF, OP_NOTIF, OP_ELSE, and OP_ENDIF as suggested [https://bitslog.com/2017/04/17/new-quadratic-delays-in-bitcoin-scripts/ here] and implemented [https://github.com/bitcoin/bitcoin/pull/16902 here], the only other instance can be avoided as well. * '''Sigops limit''' The sigops in tapscripts do not count towards the block-wide limit of 80000 (weighted). Instead, there is a per-script sigops ''budget''. The budget equals 50 + the total serialized size in bytes of the transaction input's witness (including the CompactSize prefix). Executing a signature opcode (OP_CHECKSIG, OP_CHECKSIGVERIFY, or OP_CHECKSIGADD) with a non-empty signature decrements the budget by 50. If that brings the budget below zero, the script fails immediately. Signature opcodes with unknown public key type and non-empty signature are also counted.'''The tapscript sigop limit''' The signature opcode limit protects against scripts which are slow to verify due to excessively many signature operations. In tapscript the number of signature opcodes does not count towards the BIP141 or legacy sigop limit. The old sigop limit makes transaction selection in block construction unnecessarily difficult because it is a second constraint in addition to weight. Instead, the number of tapscript signature opcodes is limited by witness weight. Additionally, the limit applies to the transaction input instead of the block and only actually executed signature opcodes are counted. Tapscript execution allows one signature opcode per 50 witness weight units plus one free signature opcode.'''Parameter choice of the sigop limit''' Regular witnesses are unaffected by the limit as their weight is composed of public key and (SIGHASH_ALL) signature pairs with ''33 + 65'' weight units each (which includes a 1 weight unit CompactSize tag). This is also the case if public keys are reused in the script because a signature's weight alone is 65 or 66 weight units. However, the limit increases the fees of abnormal scripts with duplicate signatures (and public keys) by requiring additional weight. The weight per sigop factor 50 corresponds to the ratio of BIP141 block limits: 4 mega weight units divided by 80,000 sigops. The "free" signature opcode permitted by the limit exists to account for the weight of the non-witness parts of the transaction input.'''Why are only signature opcodes counted toward the budget, and not for example hashing opcodes or other expensive operations?''' It turns out that the CPU cost per witness byte for verification of a script consisting of the maximum density of signature checking opcodes (taking the 50 WU/sigop limit into account) is already very close to that of scripts packed with other opcodes, including hashing opcodes (taking the 520 byte stack element limit into account) and OP_ROLL (taking the 1000 stack element limit into account). That said, the construction is very flexible, and allows adding new signature opcodes like CHECKSIGFROMSTACK to count towards the limit through a soft fork. Even if in the future new opcodes are introduced which change normal script cost there is no need to stuff the witness with meaningless data. Instead, the taproot annex can be used to add weight to the witness without increasing the actual witness size.. * '''Stack + altstack element count limit''' The existing limit of 1000 elements in the stack and altstack together after every executed opcode remains. It is extended to also apply to the size of initial stack. * '''Stack element size limit''' The existing limit of maximum 520 bytes per stack element remains, both in the initial stack and in push opcodes. ==Rationale== ==Deployment== This proposal is deployed identically to Taproot ([[bip-0341.mediawiki|BIP341]]). ==Examples== The Taproot ([[bip-0341.mediawiki|BIP341]]) test vectors also contain examples for Tapscript execution. ==Acknowledgements== This document is the result of many discussions and contains contributions by a number of people. The authors wish to thank all those who provided valuable feedback and reviews, including the participants of the [https://github.com/ajtowns/taproot-review structured reviews]. ================================================ FILE: bip-0343.mediawiki ================================================
  BIP: 343
  Layer: Consensus (soft fork)
  Title: Mandatory activation of taproot deployment
  Authors: Shinobius 
           Michael Folkson 
  Status: Deployed
  Type: Specification
  Assigned: 2021-04-25
  License: BSD-3-Clause OR CC0-1.0
==Abstract== This document specifies a BIP8 (LOT=true) deployment to activate taproot. ==Motivation== The Taproot soft fork upgrade has been assessed to have overwhelming community consensus and hence should attempt to be activated. Lessons have been learned from the BIP148 and BIP91 deployments in 2017 with regards to giving many months of advance warning before the mandatory signaling is attempted. The mandatory signaling is only required if miners have failed to meet the signaling threshold during the BIP8 deployment. It is important that mandatory signaling is included as without it miners would effectively have the ability to indefinitely block the activation of a soft fork with overwhelming consensus. ==Specification== This BIP will begin an activation signaling period using bit 2 at blockheight 681408 with a minimum activation height of 709632 and an activation threshold of 90%. The signaling period will timeout at blockheight 760032 with a latest activation height of 762048. Lockinontimeout (LOT) is set to true so mandatory signaling will be enforced in the last signaling period before the timeout height. Blocks without the signaling bit 2 set run the risk of being rejected during this period if taproot is not locked in prior. This BIP will cease to be active when taproot is locked in. ==Reference implementation== *[[https://github.com/BitcoinActivation/bitcoin]] ==Backward Compatibility== As a soft fork, older software will continue to operate without modification. Non-upgraded nodes, however, will consider all SegWit version 1 witness programs as anyone-can-spend scripts. They are strongly encouraged to upgrade in order to fully validate the new programs. ==Compatibility with later alternative activations== The activation mechanism “Speedy Trial” as proposed by Russell O’Connor and outlined in this bitcoin-dev mailing list [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2021-March/018583.html post] by David Harding was released in Bitcoin Core. It is effectively a BIP8 activation mechanism with one exception: start height and timeout height were defined using median time past (MTP) rather than block heights. It uses signaling bit 2, was deployed between midnight April 24th 2021 and midnight August 11th 2021, has a minimum activation height of 709632 and intends to activate BIPs 340, 341, and 342. The BIP8(LOT=true) deployment is compatible with the “Speedy Trial” deployment in Bitcoin Core as there was not a discrepancy between MTP and block height for the defined start heights. The BIP8 (LOT=true) deployment has also been deliberately designed to be compatible with a future BIP8(LOT=false) or BIP8(LOT=true) deployment in Bitcoin Core assuming Bitcoin Core releases one of these activation mechanisms in the event of the Speedy Trial deployment failing to activate. ==Rationale== The deployment of BIP148 demonstrated that multiple implementations with different activation mechanisms can incentivize the necessary actors to act so that the different deployments activate in sync. A BIP8 LOT=true deployment can run in parallel with other BIP8 activation mechanisms that have eventual mandatory signaling or no mandatory signaling. Eventual mandatory signaling ensures that miners cannot prevent the activation of a desired feature with community consensus indefinitely. ==Acknowledgements== Thanks to Shaolin Fry and Luke Dashjr for their work on BIP148 and BIP8 which were important prerequisites for this proposal. ==References== *[[bip-0008.mediawiki|BIP8 Version bits with lock-in by height]] *[[bip-0148.mediawiki|BIP148 Mandatory activation of segwit deployment]] *[[bip-0340.mediawiki|BIP340 Schnorr Signatures for secp256k1]] *[[bip-0341.mediawiki|BIP341 Taproot: SegWit version 1 spending rules]] *[[bip-0342.mediawiki|BIP342 Validation of Taproot Scripts]] *[https://taproot.works/taproot-faq/ Taproot benefits] ==Copyright== This document is dual licensed as BSD 3-clause, and Creative Commons CC0 1.0 Universal. ================================================ FILE: bip-0345/vaults.drawio ================================================ ================================================ FILE: bip-0345.mediawiki ================================================
  BIP: 345
  Layer: Consensus (soft fork)
  Title: OP_VAULT
  Authors: James O'Beirne 
           Greg Sanders 
  Status: Closed
  Type: Specification
  Assigned: 2023-02-03
  License: BSD-3-Clause
  Discussion: 2023-01-09: https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2023-January/021318.html [bitcoin-dev] OP_VAULT announcement
              2023-03-01: https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2023-March/021510.html [bitcoin-dev] BIP for OP_VAULT
  Proposed-Replacement: 443
== Introduction == This BIP proposes two new tapscript opcodes that add consensus support for a specialized covenant: OP_VAULT and OP_VAULT_RECOVER. These opcodes, in conjunction with OP_CHECKTEMPLATEVERIFY ([https://github.com/bitcoin/bips/blob/master/bip-0119.mediawiki BIP-0119]), allow users to enforce a delay period before designated coins may be spent to an arbitrary destination, with the exception of a prespecified "recovery" path. At any time prior to final withdrawal, the coins can be spent to the recovery path. === Copyright === This document is licensed under the 3-clause BSD license. === Motivation === The hazard of custodying Bitcoin is well-known. Users of Bitcoin must go to significant effort to secure their private keys, and hope that once provisioned their custody system does not yield to any number of evolving and persistent threats. Users have little means to intervene once a compromise is detected. This proposal introduces a mechanism that significantly mitigates the worst-case outcome of key compromise: coin loss. Introducing a way to intervene during unexpected spends allows users to incorporate highly secure key storage methods or unusual fallback strategies that are only exercised in the worst case, and which may otherwise be operationally prohibitive. The goal of this proposal is to make this strategy usable for custodians of any size with minimal complication. ==== Example uses ==== A common configuration for an individual custodying Bitcoin is "single signature and passphrase" using a hardware wallet. A user with such a configuration might be concerned about the risk associated with relying on a single manufacturer for key management, as well as physical access to the hardware. This individual can use OP_VAULT to make use of a highly secure key as the unlikely recovery path, while using their existing signing procedure as the withdrawal trigger key with a configured spend delay of e.g. 1 day. The recovery path key can be of a highly secure nature that might otherwise make it impractical for daily use. For example, the key could be generated in some analog fashion, or on an old computer that is then destroyed, with the private key replicated only in paper form. Or the key could be a 2-of-3 multisig using devices from different manufacturers. Perhaps the key is geographically or socially distributed. Since it can be any Bitcoin script policy, the recovery key can include a number of spending conditions, e.g. a time-delayed fallback to an "easier" recovery method, in case the highly secure key winds up being ''too'' highly secure. The user can run software on their mobile device that monitors the blockchain for spends of the vault outpoints. If the vaulted coins move in an unexpected way, the user can immediately sweep them to the recovery path, but spending the coins on a daily basis works in the same way it did prior to vaulting (aside from the spend delay). Institutional custodians of Bitcoin may use vaults in similar fashion. ===== Provable timelocks ===== This proposal provides a mitigation to the [https://web.archive.org/web/20230210123933/https://xkcd.com/538/ "$5 wrench attack."] By setting the spend delay to, say, a week, and using as the recovery path a script that enforces a longer relative timelock, the owner of the vault can prove that he is unable to access its value immediately. To the author's knowledge, this is the only way to configure this defense without rolling timelocked coins for perpetuity or relying on a trusted third party. == Goals == [[File:bip-0345/vaults-Basic.png|frame|center]] Vaults in Bitcoin have been discussed formally since 2016 ([https://crypto.news/app/uploads/2016/08/MES16.pdf MES16]) and informally since [https://web.archive.org/web/20160220215151/https://bitcointalk.org/index.php?topic=511881.0 2014]. The value of having a configurable delay period with recovery capability in light of an unexpected spend has been widely recognized. The only way to implement vaults given the existing consensus rules, aside from [https://github.com/revault emulating vaults with large multisig configurations], is to use presigned transactions created with a one-time-use key. This approach was first demonstrated [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2020-April/017755.html in 2020]. Unfortunately, this approach has a number of practical shortcomings: * generating and securely deleting ephemeral keys, which are used to emulate the vault covenant, is required, * amounts and withdrawal patterns must be precommitted to, * there is a necessity to precommit to an address that the funds must pass through on their way to the final withdrawal target, which is likely only known at unvault time, * the particular fee management technique or wallet must be decided upon vault creation, * coin loss follows if a vault address is reused, * the transaction data that represents the "bearer asset" of the vault must be stored for perpetuity, otherwise value is lost, and * the vault creation ceremony must be performed each time a new balance is to be deposited. The deployment of a "precomputed" covenant mechanism like [https://github.com/bitcoin/bips/blob/master/bip-0119.mediawiki OP_CHECKTEMPLATEVERIFY] or [https://github.com/bitcoin/bips/blob/master/bip-0118.mediawiki SIGHASH_ANYPREVOUT] would both remove the necessity to use an ephemeral key, since the covenant is enforced on-chain, and lessen the burden of sensitive data storage, since the necessary transactions can be generated from a set of compact parameters. This approach was demonstrated [https://github.com/jamesob/simple-ctv-vault in 2022]. However, the limitations of precomputation still apply: amounts, destinations, and fee management are all fixed. Funds must flow through a fixed intermediary to their final destination. Batch operations, which may be vital for successful recovery during fee spikes or short spend delay, are not possible. [[File:bip-0345/withdrawal-comparison.drawio.png|frame|center]] Having a "general" covenant mechanism that can encode arbitrary transactional state machines would allow us to solve these issues, but at the cost of complex and large scripts that would probably be duplicated many times over in the blockchain. The particular design and deployment timeline of such a general framework is also uncertain. This approach was demonstrated [https://blog.blockstream.com/en-covenants-in-elements-alpha/ in 2016]. This proposal intends to address the problems outlined above by providing a delay period/recovery path use with minimal transactional and operational overhead using a specialized covenant. The design goals of the proposal are: * '''efficient reuse of an existing vault configuration.''''''Why does this support address reuse?''' The proposal doesn't rely on or encourage address reuse, but certain uses are unsafe if address reuse cannot be handled - for example, if a custodian gives its users a vault address to deposit to, it cannot enforce that those users make a single deposit for each address. A single vault configuration, whether the same literal scriptPubKey or not, should be able to “receive” multiple deposits. * '''batched operations''' for recovery and withdrawal to allow managing multiple vault coins efficiently. * '''unbounded partial withdrawals''', which allows users to withdraw partial vault balances without having to perform the setup ceremony for a new vault. * '''dynamic unvault targets''', which allow the proposed withdrawal target for a vault to be specified at withdrawal time rather than when the vault is first created. This would remove the need for a prespecified, intermediate wallet that only exists to route unvaulted funds to their desired destination. * '''dynamic fee management''' that, like dynamic targets, defers the specification of fee rates and source to unvault time rather than vault creation time. These goals are accompanied by basic safety considerations (e.g. not being vulnerable to mempool pinning) and a desire for concision, both in terms of the number of outputs created as well as script sizes. This proposal is designed to be compatible with any future sighash modes (e.g. SIGHASH_GROUP) or fee management strategies (e.g. [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2020-September/018168.html transaction sponsors]) that may be introduced. Use of these opcodes will benefit from, but do not strictly rely on, [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2022-September/020937.html v3 transaction relay] and [https://github.com/instagibbs/bips/blob/527b007dbf5b9a89895017030183370e05468ae6/bip-ephemeralanchors.mediawiki ephemeral anchors]. == Design == In typical usage, a vault is created by encumbering coins under a taptree [https://github.com/bitcoin/bips/blob/master/bip-0341.mediawiki (BIP-341)] containing at least two leaves: one with an OP_VAULT-containing script that facilitates the expected withdrawal process, and another leaf with OP_VAULT_RECOVER which ensures the coins can be recovered at any time prior to withdrawal finalization. The rules of OP_VAULT ensure the timelocked, interruptible withdrawal by allowing a spending transaction to replace the OP_VAULT tapleaf with a prespecified script template, allowing for some parameters to be set at spend (trigger) time. All other leaves in the taptree must be unchanged in the destination output, which preserves the recovery path as well as any other spending conditions originally included in the vault. This is similar to the TAPLEAF_UPDATE_VERIFY design that was proposed [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2021-September/019419.html in 2021]. These tapleaf replacement rules, described more precisely below, ensure a timelocked withdrawal, where the timelock is fixed by the original OP_VAULT parameters, to a fixed set of outputs (via OP_CHECKTEMPLATEVERIFY'''Why is OP_CHECKTEMPLATEVERIFY (BIP-119) relied upon for this proposal?''' During the withdrawal process, the proposed final destination for value being withdrawn must be committed to. OP_CTV is the simplest, safest way to commit the spend of some coins to a particular set of outputs. An earlier version of this proposal attempted to use a simpler, but similar method, of locking the spend of coins to a set of outputs, but this method introduced txid malleability.
Note that if some other method of locking spends to a particular set of outputs should be deployed, that method can be used in the OP_VAULT with no changes.
) which is chosen when the withdrawal process is triggered. While OP_CHECKTEMPLATEVERIFY is used in this proposal as the preferred method to bind the proposed withdrawal to a particular set of final outputs, OP_VAULT is composable with other (and future) opcodes to facilitate other kinds of withdrawal processes. [[File:bip-0345/opvault.drawio.png|frame|center]] === Transaction types === The vault has a number of stages, some of them optional: * '''vault transaction''': encumbers some coins into a Taproot structure that includes at least one OP_VAULT leaf and one OP_VAULT_RECOVER leaf. * '''trigger transaction''': spends one or more OP_VAULT-tapleaf inputs into an output which is encumbered by a timelocked withdrawal to a fixed set of outputs, chosen at trigger time. This publicly broadcasts the intent to withdraw to some specific set of outputs.

The trigger transaction may have an additional output which allocates some of the vault balance into a partial "revault," which simply encumbers the revaulted portion of the value into the same scriptPubKey as the OP_VAULT-containing input(s) being spent. * '''withdrawal transaction''': spends the timelocked, destination-locked trigger inputs into a compatible set of final withdrawal outputs (per, e.g., a CHECKTEMPLATEVERIFY hash), after the trigger inputs have matured per the spend delay. Timelocked CTV transactions are the motivating usage of OP_VAULT, but any script template can be specified during the creation of the vault. * '''recovery transaction''': spends one or more vault inputs via OP_VAULT_RECOVER tapleaf to the prespecified recovery path, which can be done at any point before the withdrawal transaction confirms. Each input can optionally require a witness satisfying a specified ''recovery authorization'' script, an optional script prefixing the OP_VAULT_RECOVER fragment. The use of recovery authorization has certain trade-offs discussed later. === Fee management === A primary consideration of this proposal is how fee management is handled. Providing dynamic fee management is critical to the operation of a vault, since * precalculated fees are prone to making transactions unconfirmable in high fee environments, and * a fee wallet that is prespecified might be compromised or lost before use. But dynamic fee management can introduce [https://bitcoinops.org/en/topics/transaction-pinning/ pinning vectors]. Care has been taken to avoid unnecessarily introducing these vectors when using the new destination-based spending policies that this proposal introduces. Originally, this proposal had a hard dependency on reformed transaction nVersion=3 policies, including ephemeral anchors, but it has since been revised to simply benefit from these changes in policy as well as other potential fee management mechanisms. == Specification == The tapscript opcodes OP_SUCCESS187 (0xbb) and OP_SUCCESS188 (0xbc) are constrained with new rules to implement OP_VAULT and OP_VAULT_RECOVER, respectively. === OP_VAULT evaluation === When evaluating OP_VAULT (OP_SUCCESS187, 0xbb), the expected format of the stack, shown top to bottom, is: [ leaf-update script data items ... ] where * is a minimally-encoded data push of a serialized script. In conjunction with the leaf-update data items, it dictates the tapleaf script in the output taptree that will replace the one currently executing. ** Otherwise, script execution MUST fail and terminate immediately. * is an up to 4-byte minimally encoded CScriptNum indicating how many leaf-update script items should be popped off the stack. '''Why only prefix with data pushes?''' Prefixing the leaf-update-script-body with opcodes opens up the door to prefix OP_SUCCESSX opcodes, to name a single issue only, side-stepping the validation that was meant to be run by the committed script. ** If this value does not decode to a valid CScriptNum, script execution MUST fail and terminate immediately. ** If this value is less than 0, script execution MUST fail and terminate immediately. ** If there are fewer than 3 items following the items on the stack, script execution MUST fail and terminate immediately. In other words, after popping , there must be at least 3 + items remaining on the stack. * The following stack items are popped off the stack and prefixed as minimally-encoded push-data arguments to the to construct the expected tapleaf replacement script. * is an up to 4-byte minimally encoded CScriptNum indicating the index of the output which, in conjunction with an optional revault output, carries forward the value of this input, and has an identical taptree aside from the currently executing leaf. ** If this value does not decode to a valid CScriptNum, script execution MUST fail and terminate immediately. ** If this value is less than 0 or is greater than or equal to the number of outputs, script execution MUST fail and terminate immediately. * is an up to 4-byte minimally encoded CScriptNum optionally indicating the index of an output which, in conjunction with the trigger output, carries forward the value of this input, and has an identical scriptPubKey to the current input. ** If this value does not decode to a valid CScriptNum, script execution MUST fail and terminate immediately. ** If this value is greater than or equal to the number of outputs, script execution MUST fail and terminate immediately. ** If this value is negative and not equal to -1, script execution MUST fail and terminate immediately.'''Why is -1 the only allowable negative value for revault-vout-idx?''' A negative revault index indicates that no revault output exists; if this value were allowed to be any negative number, the witness could be malleated (and bloated) while a transaction is waiting for confirmation. * is an up to 7-byte minimally encoded CScriptNum indicating the number of satoshis being revaulted. ** If this value does not decode to a valid CScriptNum, script execution MUST fail and terminate immediately. ** If this value is not greater than or equal to 0, script execution MUST fail and terminate immediately. ** If this value is non-zero but is negative, script execution MUST fail and terminate immediately. ** If this value is zero but is not -1, script execution MUST fail and terminate immediately. After the stack is parsed, the following validation checks are performed: * Decrement the per-script sigops budget (see [https://github.com/bitcoin/bips/blob/master/bip-0342.mediawiki#user-content-Resource_limits BIP-0342]) by 60'''Why is the sigops cost for OP_VAULT set to 60?''' To determine the validity of a trigger output, OP_VAULT must perform an EC multiplication and hashing proportional to the length of the control block in order to generate the output's expected TapTweak. This has been measured to have a cost in the worst case (max length control block) of roughly twice a Schnorr verification. Because the hashing cost could be mitigated by caching midstate, the cost is 60 and not 100.; if the budget is brought below zero, script execution MUST fail and terminate immediately. * Let the output designated by be called ''triggerOut''. * If the scriptPubKey of ''triggerOut'' is not a version 1 witness program, script execution MUST fail and terminate immediately. * Let the script constructed by taking the and prefixing it with minimally-encoded data pushes of the leaf-update script data items be called the ''leaf-update-script''. * If the scriptPubKey of ''triggerOut'' does not match that of a taptree that is identical to that of the currently evaluated input, but with the leaf script substituted for ''leaf-update-script'', script execution MUST fail and terminate immediately. ** Note: the parity bit of the resulting taproot output is allowed to vary, so both values for the new output must be checked. * Let the output designated by (if the index value is non-negative) be called ''revaultOut''. * If the scriptPubKey of ''revaultOut'' is not equal to the scriptPubKey of the input being spent, script execution MUST fail and terminate immediately. * Implementation recommendation: if the sum of the amounts of ''triggerOut'' and ''revaultOut'' (if any) are not greater than or equal to the value of this input, script execution SHOULD fail and terminate immediately. This ensures that (at a minimum) the vaulted value for this input is carried through. ** Amount checks are ultimately done with deferred checks, but this check can help short-circuit obviously invalid spends. * Queue a deferred check'''What is a deferred check and why does this proposal require them for correct script evaluation?''' A deferred check is a validation check that is executed only after all input scripts have been validated, and is based on aggregate information collected during each input's EvalScript run.

Currently, the validity of each input is (usually) checked concurrently across all inputs in a transaction. Because this proposal allows batching the spend of multiple vault inputs into a single recovery or withdrawal output, we need a mechanism to ensure that all expected values per output can be summed and then checked. This necessitates the introduction of an "aggregating" set of checks which can only be executed after each input's script is evaluated. Note that similar functionality would be required for batch input validation or cross-input signature aggregation.
that ensures the satoshis for this input's nValue minus are included within the output nValue found at . * Queue a deferred check that ensures satoshis, if non-zero, are included within the output's nValue found at . ** These deferred checks could be characterized in terms of the pseudocode below (in ''Deferred checks'') as
TriggerCheck(input_amount, , , ). If none of the conditions fail, a single true value (0x01) is left on the stack. === OP_VAULT_RECOVER evaluation === When evaluating OP_VAULT_RECOVER (OP_SUCCESS188, 0xbc), the expected format of the stack, shown top to bottom, is: where * is a 32-byte data push. ** If this is not 32 bytes in length, script execution MUST fail and terminate immediately. * is an up to 4-byte minimally encoded CScriptNum indicating the index of the recovery output. ** If this value does not decode to a valid CScriptNum, script execution MUST fail and terminate immediately. ** If this value is less than 0 or is greater than or equal to the number of outputs, script execution MUST fail and terminate immediately. After the stack is parsed, the following validation checks are performed: * Let the output at index be called ''recoveryOut''. * Compute the scriptPubKey tagged hash for ''recoveryOut'' as output-sPK-hash = tagged_hash("VaultRecoverySPK", CompactSize(len(recoveryOut.scriptPubKey)) || recoveryOut.scriptPubKey), where tagged_hash() is from the [https://github.com/bitcoin/bips/blob/master/bip-0340/reference.py BIP-0340 reference code]. * If the ''recoveryOut'' output-sPK-hash is not equal to , script execution MUST fail and terminate immediately. ** Implementation recommendation: if ''recoveryOut'' does not have an nValue greater than or equal to this input's amount, the script SHOULD fail and terminate immediately. * Queue a deferred check that ensures the nValue of ''recoveryOut'' contains the entire nValue of this input.'''How do recovery transactions pay for fees?''' If the recovery is unauthorized, fees are attached either via CPFP with an ephemeral anchor or as inputs which are solely spent to fees (i.e. no change output). If the recovery is authorized, fees can be attached in any manner, e.g. unrelated inputs and outputs or CPFP via anchor. ** This deferred check could be characterized in terms of the pseudocode below as RecoveryCheck(, input_amount). If none of the conditions fail, a single true value (0x01) is left on the stack. === Deferred check evaluation === Once all inputs for a transaction are validated per the rules above, any deferred checks queued MUST be evaluated. The Python pseudocode for this is as follows: class TriggerCheck: """Queued by evaluation of OP_VAULT (withdrawal trigger).""" input_amount: int revault_amount: int trigger_vout_idx: int revault_vout_idx: int class RecoveryCheck: """Queued by evaluation of OP_VAULT_RECOVER.""" input_amount: int vout_idx: int def validate_deferred_checks(checks: [DeferredCheck], tx: Transaction) -> bool: """ Ensure that all value from vault inputs being triggered or recovered is preserved in suitable output nValues. """ # Map to hold expected output values. out_map: Dict[int, int] = defaultdict(lambda: 0) for c in checks: if isinstance(c, TriggerCheck): out_map[c.trigger_vout_idx] += (c.input_amount - c.revault_amount) if c.revault_amount > 0: out_map[c.revault_vout_idx] += c.revault_amount elif isinstance(c, RecoveryCheck): out_map[c.vout_idx] += c.input_amount for (vout_idx, amount_sats) in out_map.items(): # Trigger/recovery value can be greater than the constituent vault input # amounts. if tx.vout[vout_idx].nValue < amount_sats: return False return True If the above procedure, or an equivalent, returns false, script execution MUST fail and terminate immediately. This ensures that all compatible vault inputs can be batched into shared corresponding trigger or recovery outputs while preserving their entire input value. == Policy changes == In order to prevent possible pinning attacks, recovery transactions must be replaceable. * When validating an OP_VAULT_RECOVER input being spent, the script MUST fail (by policy, not consensus) and terminate immediately if both'''Why are recovery transactions required to be replaceable?''' In the case of unauthorized recoveries, an attacker may attempt to pin recovery transactions by broadcasting a "rebundled" version with a low fee rate. Vault owners must be able to overcome this with replacement. In the case of authorized recovery, if an attacker steals the recovery authorization key, the attacker may try to pin the recovery transaction during theft. Requiring replaceability ensures that the owner can always raise the fee rate of the recovery transaction, even if they are RBF rule #3 griefed in the process. *# the input is not marked as opt-in replaceable by having an nSequence number less than 0xffffffff - 1, per [https://github.com/bitcoin/bips/blob/master/bip-0125.mediawiki BIP-0125], and *# the version of the recovery transaction has an nVersion other than 3. If the script containing OP_VAULT_RECOVER is 34 bytes or less34 bytes is the length of a recovery script that consists solely of OP_VAULT_RECOVER., let it be called "unauthorized," because there is no script guarding the recovery process. In order to prevent pinning attacks in the case of unauthorized recovery - since the spend of the input (and the structure of the transaction) is not authorized by a signed signature message - the output structure of unauthorized recovery transaction is limited. * If the recovery is unauthorized, the recovery transaction MUST (by policy) abide by the following constraints: ** If the spending transaction has more than two outputs, the script MUST fail and terminate immediately. ** If the spending transaction has two outputs, and the output which is not ''recoveryOut'' is not an [https://github.com/instagibbs/bips/blob/527b007dbf5b9a89895017030183370e05468ae6/bip-ephemeralanchors.mediawiki ephemeral anchor], the script MUST fail and terminate immediately.'''Why can unauthorized recoveries only process a single recovery path?''' Because there is no signature required for unauthorized recoveries, if additional outputs were allowed, someone observing a recovery in the mempool would be able to rebundle and broadcast the recovery with a lower fee rate. == Implementation == A sample implementation is available on bitcoin-inquisition [https://github.com/jamesob/bitcoin/tree/2023-02-opvault-inq here], with an associated [https://github.com/bitcoin-inquisition/bitcoin/pull/21 pull request]. == Applications == The specification above, perhaps surprisingly, does not specifically cover how a relative timelocked withdrawal process with a fixed target is implemented. The tapleaf update semantics specified in OP_VAULT as well as the output-based authorization enabled by OP_VAULT_RECOVER can be used to implement a vault, but they are incomplete without two other pieces: * a way to enforce relative timelocks, like OP_CHECKSEQUENCEVERIFY, and * a way to enforce that proposed withdrawals are ultimately being spent to a precise set of outputs, like OP_CHECKTEMPLATEVERIFY. These two pieces are combined with the tapleaf update capabilities of OP_VAULT to create a vault, described below. === Creating a vault === In order to vault coins, they can be spent into a witness v1 scriptPubKey that contains a taptree of the form tr(, leaves = { recover: OP_VAULT_RECOVER, trigger: OP_CHECKSIGVERIFY (i) 2 $leaf-update-script-body OP_VAULT, (ii) ... [ possibly other leaves ] } ) where * $leaf-update-script-body is, for example, OP_CHECKSEQUENCEVERIFY OP_DROP OP_CHECKTEMPLATEVERIFY. ** This is one example of a trigger script, but ''any'' script fragment can be used, allowing the creation of different types of vaults. For example, you could use OP_CHECKSEQUENCEVERIFY OP_DROP OP_CHECKSIG to do a time-delayed transfer of the coins to another key. This also future-proofs OP_VAULT for future scripting capabilities. * The script fragment in (i) is called the "trigger authorization," because it gates triggering the withdrawal. This can be done in whatever manner the wallet designer would like. * The script fragment in (ii) is the incomplete OP_VAULT invocation - it will be completed once the rest of the parameters (the CTV target hash, trigger vout index, and revault vout index) are provided by the trigger transaction witness. Typically, the internal key for the vault taproot output will be specified so that it is controlled by the same descriptor as the recovery path, which facilitates another (though probably unused) means of recovering the vault output to the recovery path. This has the potential advantage of recovering the coin without ever revealing it was a vault. Otherwise, the internal key can be chosen to be an unspendable NUMS point to force execution of the taptree contents. === Triggering a withdrawal === To make use of the vault, and spend it towards some output, we construct a spend of the above tr() output that simply replaces the "trigger" leaf with the full leaf-update script (in this case, a timelocked CTV script): Witness stack: - - (-1 if none) - - - - [ "trigger" leaf script contents ] - [ taproot control block prompting a script-path spend to "trigger" leaf ] Output scripts: [ tr(, leaves = { recover: OP_VAULT_RECOVER, <-- unchanged trigger: OP_CHECKSEQUENCEVERIFY OP_DROP OP_CHECKTEMPLATEVERIFY <-- changed per the leaf-update rules of OP_VAULT ... [ possibly other leaves ] } ), [ optional revault output with the same sPK as the original vault output ], ] OP_VAULT has allowed the taptree to be transformed so that the trigger leaf becomes a timelocked CTV script, which is what actually facilitates the announced withdrawal. The withdrawal is interruptible by the recovery path because the "recover" leaf is preserved exactly from the original taptree. Note that the CTV hash is specified at spend time using the witness stack, and "locked in" via the OP_VAULT spend rules which assert its existence in the output. The vault funds can be recovered at any time prior to the spend of the timelocked CTV script by way of a script-path spend using the "recover" leaf. === Recovery authorization === When configuring a vault, the user must decide if they want to have the recovery process gated by a script fragment prefixing the OP_VAULT_RECOVER instruction in the "recover" leaf. Its use entails trade-offs. ==== Unauthorized recovery ==== Unauthorized recovery simplifies vault use in that recovery never requires additional information aside from the location of the vault outpoints and the recovery path - the "authorization" is simply the reveal of the recovery path, i.e. the preimage of . But because this reveal is the only authorization necessary to spend the vault coins to recovery, the user must expect to recover all such vaults at once, since an observer can replay this recovery (provided they know the outpoints). Additionally, unauthorized recovery across multiple distinct recovery paths cannot be done in the same transaction, and fee control is more constrained: because the output structure is limited for unauthorized recovery, fee management relies either on inputs which are completely spent to fees or the use of the optional ephemeral anchor and package relay. These limitations are to avoid pinning attacks. ==== Authorized recovery ==== With authorized recovery, the user must keep track of an additional piece of information: how to solve the recovery authorization script fragment when recovery is required. If this key is lost, the user will be unable to initiate the recovery process for their coins. If an attacker obtains the recovery key, they may grief the user during the recovery process by constructing a low fee rate recovery transaction and broadcasting it (though they will not be able to pin because of the replaceability requirement on recovery transactions). However, authorized recovery configurations have significant benefits. Batched recoveries are possible for vaults with otherwise incompatible recovery parameters. Fee management is much more flexible, since authorized recovery transactions are "free form" and unrelated inputs and outputs can be added, potentially to handle fees. ==== Recommendation: use a simple, offline recovery authorization key seed ==== The benefits of batching and fee management that authorized recovery provides are significant. If the recovery authorization key falls into the hands of an attacker, the outcome is not catastrophic, whereas if the user loses their recovery authorization key as well as their trigger key, the result is likely coin loss. Consequently, the author's recommendation is to use a simple seed for the recovery authorization key that can be written down offline and replicated. Note that the recovery authorization key '''is not''' the recovery path key, and this is '''much different''' than any recommendation on how to generate the recovery path key itself. === Address reuse and recovery === When creating a vault, four factors affect the resulting P2TR address: # The internal pubkey (likely belonging to the recovery wallet) # The recovery leaf # The trigger leaf # Any other leaves that exist in the taptree The end user has the option of varying certain contents along descriptors in order to avoid reusing vault addresses without affecting key management, e.g. the trigger authorization pubkeys. Note that when using unauthorized recovery, the reveal of the recovery scriptPubKey will allow any observer to initiate the recovery process for any vault with matching recovery params, provided they are able to locate the vault outpoints. As a result, it is recommended to expect that '''all outputs sharing an identical unauthorized should be recovered together'''. This situation can be avoided with a comparable key management model by varying the generation of each vault's recovery scriptPubKey along a single descriptor, but note that this will prevent recovering multiple separate vaults into a single recovery output. Varying the internal pubkey will prevent batching the trigger of multiple vault inputs into a single trigger output; consequently it is recommended that users instead vary some component of the trigger leaf script if address reuse is undesirable. Users could vary the trigger pubkey along a descriptor, keeping the recovery path and internal-pubkey the same, which both avoids reusing addresses and allows batched trigger and recovery operations. ==== Recommendation: generate new recovery addresses for new trigger keys ==== If using unauthorized recovery, it is recommended that you do not share recovery scriptPubKeys across separate trigger keys. If one trigger key is compromised, that will necessitate the (unauthorized) recovery of all vaults with that trigger key, which will reveal the recovery path preimage. This means that an observer might be able to initiate recovery for vaults controlled by an uncompromised trigger key. ==== Fee management ==== Fees can be managed in a variety of ways, but it's worth noting that both trigger and recovery transactions must preserve the total value of vault inputs, so vaulted values cannot be repurposed to pay for fees. This does not apply to the withdrawal transaction, which can allocate value arbitrarily. In the case of vaults that use recovery authorization, all transactions can "bring their own fees" in the form of unrelated inputs and outputs. These transactions are also free to specify ephemeral anchors, once the related relay policies are deployed. This means that vaults using recovery authorization have no dependence on the deploy of v3 relay policy. For vaults using unauthorized recovery, the recovery transaction relies on the use of either fully-spent fee inputs or an ephemeral anchor output. This means that vaults which do not use recovery authorization are essentially dependent on v3 transaction relay policy being deployed. === Batching === ==== During trigger ==== OP_VAULT outputs with the same taptree, aside from slightly different trigger leaves, can be batched together in the same withdrawal process. Two "trigger" leaves are compatible if they have the same OP_VAULT arguments. Note that this allows the trigger authorization -- the script prefixing the OP_VAULT invocation -- to differ while still allowing batching. Trigger transactions can act on multiple incompatible OP_VAULT input sets, provided each set has a suitable associated ''triggerOut'' output. Since SIGHASH_DEFAULT can be used to sign the trigger authorization, unrelated inputs and outputs can be included, possibly to facilitate fee management or the batch withdrawal of incompatible vaults. ==== During withdrawal ==== During final withdrawal, multiple trigger outputs can be used towards the same withdrawal transaction provided that they share identical parameters. This facilitates batched withdrawals. ==== During recovery ==== OP_VAULT_RECOVER outputs with the same can be recovered into the same output. Recovery-incompatible vaults which have authorized recovery can be recovered in the same transaction, so long as each set (grouped by ) has an associated ''recoveryOut''. This allows unrelated recoveries to share common fee management. === Watchtowers === The value of vaults is contingent upon having monitoring in place that will alert the owner when unexpected spends are taking place. This can be done in a variety of ways, with varying degrees of automation and trust in the watchtower. In the maximum-trust case, the watchtower can be fully aware of all vaulted coins and has the means to initiate the recovery process if spends are not pre-reported to the watchtower. In the minimum-trust case, the user can supply a probabilistic filter of which coins they wish to monitor; the watchtower would then alert the user if any coins matching the filter move, and the user would be responsible for ignoring false positives and handling recovery initiation. === Output descriptors === Output descriptors for vault-related outputs will be covered in a subsequent BIP. == Deployment == Activation mechanism is to be determined. This BIP should be deployed concurrently with BIP-0119 to enable full use of vaults. == Backwards compatibility == OP_VAULT and OP_VAULT_RECOVER replace, respectively, the witness v1-only opcodes OP_SUCCESS187 and OP_SUCCESS188 with stricter verification semantics. Consequently, scripts using those opcodes which previously were valid will cease to be valid with this change. Stricter verification semantics for an OP_SUCCESSx opcode are a soft fork, so existing software will be fully functional without upgrade except for mining and block validation. Backwards compatibility considerations are very comparable to previous deployments for OP_CHECKSEQUENCEVERIFY and OP_CHECKLOCKTIMEVERIFY (see [https://github.com/bitcoin/bips/blob/master/bip-0065.mediawiki BIP-0065] and [https://github.com/bitcoin/bips/blob/master/bip-0112.mediawiki BIP-0112]). == Rationale == == References == * [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2016-February/012470.html [bitcoin-dev] Bitcoin Vaults (2016)] * [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2018-February/015793.html [bitcoin-dev] Simple lock/unlock mechanism (2018)] * [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2020-April/017755.html [bitcoin-dev] On-chain vaults prototype (2020)] * [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2021-September/019419.html [bitcoin-dev] TAPLEAF_UPDATE_VERIFY covenant opcode (2021)] * [https://arxiv.org/abs/2005.11776 Custody Protocols Using Bitcoin Vaults (2020)] * [https://jameso.be/vaults.pdf Vaults and Covenants (2023)] == Acknowledgements == The author would like to thank * AJ Towns and Greg Sanders for discussion, numerous suggestions that improved the proposal, and advice. * Jeremy Rubin for inspiration, advice, and mentorship. * BL for discussion and insight. * John Moffett for early feedback and a test case demonstrating a recursive script evaluation attack. * Johan Halseth for providing conceptual review and pointing out a pinning attack. * Pieter Wuille for implementation advice. ================================================ FILE: bip-0346/ref-impl/Cargo.toml ================================================ [package] name = "txhash-ref" version = "0.0.0" edition = "2021" [dependencies] bitcoin = { version = "=0.32.8", features = [ "serde" ] } serde_json = "1" ================================================ FILE: bip-0346/ref-impl/src/main.rs ================================================ use bitcoin::{Transaction, TxOut}; use bitcoin::consensus::encode::Encodable; use bitcoin::hashes::{sha256, Hash, HashEngine}; pub const TXFS_VERSION: u8 = 1 << 0; pub const TXFS_LOCKTIME: u8 = 1 << 1; pub const TXFS_CURRENT_INPUT_IDX: u8 = 1 << 2; pub const TXFS_CURRENT_INPUT_CONTROL_BLOCK: u8 = 1 << 3; pub const TXFS_CURRENT_INPUT_SPENTSCRIPT: u8 = 1 << 4; pub const TXFS_CURRENT_INPUT_LAST_CODESEPARATOR_POS: u8 = 1 << 5; pub const TXFS_CURRENT_INPUT_TAPROOT_ANNEX: u8 = 1 << 6; pub const TXFS_CONTROL: u8 = 1 << 7; pub const TXFS_INPUTS_PREVOUTS: u8 = 1 << 0; pub const TXFS_INPUTS_SEQUENCES: u8 = 1 << 1; pub const TXFS_INPUTS_SCRIPTSIGS: u8 = 1 << 2; pub const TXFS_INPUTS_PREV_SCRIPTPUBKEYS: u8 = 1 << 3; pub const TXFS_INPUTS_PREV_VALUES: u8 = 1 << 4; pub const TXFS_INPUTS_TAPROOT_ANNEXES: u8 = 1 << 5; pub const TXFS_OUTPUTS_SCRIPTPUBKEYS: u8 = 1 << 6; pub const TXFS_OUTPUTS_VALUES: u8 = 1 << 7; pub const TXFS_INPUTS_ALL: u8 = TXFS_INPUTS_PREVOUTS | TXFS_INPUTS_SEQUENCES | TXFS_INPUTS_SCRIPTSIGS | TXFS_INPUTS_PREV_SCRIPTPUBKEYS | TXFS_INPUTS_PREV_VALUES | TXFS_INPUTS_TAPROOT_ANNEXES; pub const TXFS_OUTPUTS_ALL: u8 = TXFS_OUTPUTS_SCRIPTPUBKEYS | TXFS_OUTPUTS_VALUES; pub const TXFS_INOUT_NUMBER: u8 = 1 << 7; pub const TXFS_INOUT_SELECTION_NONE: u8 = 0x00; pub const TXFS_INOUT_SELECTION_CURRENT: u8 = 0x40; pub const TXFS_INOUT_SELECTION_ALL: u8 = 0x3f; pub const TXFS_INOUT_SELECTION_MODE: u8 = 1 << 6; pub const TXFS_INOUT_LEADING_SIZE: u8 = 1 << 5; pub const TXFS_INOUT_INDIVIDUAL_MODE: u8 = 1 << 5; pub const TXFS_INOUT_SELECTION_MASK: u8 = 0xff ^ (1 << 7) ^ (1 << 6) ^ (1 << 5); pub const TXFS_SPECIAL_TEMPLATE: [u8; 4] = [ TXFS_VERSION | TXFS_LOCKTIME | TXFS_CURRENT_INPUT_IDX, TXFS_INPUTS_SEQUENCES | TXFS_INPUTS_SCRIPTSIGS | TXFS_OUTPUTS_ALL, TXFS_INOUT_NUMBER | TXFS_INOUT_SELECTION_ALL, TXFS_INOUT_NUMBER | TXFS_INOUT_SELECTION_ALL, ]; const SHA256_EMPTY: sha256::Hash = sha256::Hash::const_hash(&[]); /// Interpret the bits of the input byte as a signed 7-bit integer and return the /// value as an i8. fn read_i7(input: u8) -> i8 { let masked = input & 0x7f; if (masked & 0x40) == 0 { masked as i8 } else { 0i8 - ((!(masked-1)) & 0x7f) as i8 } } /// Interpret the bits of the input bytes as a signed 15-bit integer and return the /// value as an i16. fn read_i15(input: u16) -> i16 { let masked = input & 0x7fff; if (masked & 0x4000) == 0 { masked as i16 } else { 0i16 - ((!(masked-1)) & 0x7fff) as i16 } } fn convert_short_txfs(txfs: u8) -> Result<[u8; 4], &'static str> { let mut base = TXFS_VERSION | TXFS_LOCKTIME | TXFS_CONTROL | TXFS_CURRENT_INPUT_TAPROOT_ANNEX; let mut inout_fields = TXFS_OUTPUTS_ALL | TXFS_INPUTS_SEQUENCES | TXFS_INPUTS_SCRIPTSIGS; let input_selection = match txfs & 0b00000011 { 0b00000000 => TXFS_INOUT_SELECTION_NONE, 0b00000001 => TXFS_INOUT_SELECTION_CURRENT, 0b00000011 => TXFS_INOUT_SELECTION_ALL, _ => return Err("0b10 is not a valid input selection"), }; let output_selection = match txfs & 0b00001100 { 0b00000000 => TXFS_INOUT_SELECTION_NONE, 0b00000100 => TXFS_INOUT_SELECTION_CURRENT, 0b00001100 => TXFS_INOUT_SELECTION_ALL, _ => return Err("0b10 is not a valid output selection"), }; if txfs & 0b00010000 != 0 { inout_fields = inout_fields | TXFS_INPUTS_PREVOUTS; } if txfs & 0b00100000 != 0 { inout_fields = inout_fields | TXFS_INPUTS_PREV_SCRIPTPUBKEYS | TXFS_INPUTS_PREV_VALUES; } if txfs & 0b01000000 != 0 { base = base | TXFS_CURRENT_INPUT_CONTROL_BLOCK | TXFS_CURRENT_INPUT_SPENTSCRIPT | TXFS_CURRENT_INPUT_LAST_CODESEPARATOR_POS; } if txfs & 0b10000000 != 0 { base = base | TXFS_CURRENT_INPUT_IDX; } Ok([base, inout_fields, input_selection, output_selection]) } /// Parse an input or output selection from the TxFieldSelector bytes. /// /// Returns the selected indices and a flag whether to commit the number of items. fn parse_inout_selection( first_byte: u8, bytes: &mut impl Iterator, nb_items: usize, current_input_idx: u32, ) -> Result<(Vec, bool), &'static str> { let commit_number = (first_byte & TXFS_INOUT_NUMBER) != 0; let selection = first_byte & (0xff ^ TXFS_INOUT_NUMBER); let selected = if selection == TXFS_INOUT_SELECTION_NONE { vec![] } else if selection == TXFS_INOUT_SELECTION_ALL { (0..nb_items).collect() } else if selection == TXFS_INOUT_SELECTION_CURRENT { if current_input_idx as usize >= nb_items { // NB can only happen for outputs return Err("current input index exceeds number of outputs and current output selected"); } vec![current_input_idx as usize] } else if (selection & TXFS_INOUT_SELECTION_MODE) == 0 { // leading mode let count = if (selection & TXFS_INOUT_LEADING_SIZE) == 0 { (selection & TXFS_INOUT_SELECTION_MASK) as usize } else { let next_byte = bytes.next().ok_or("second leading selection byte missing")?; (((selection & TXFS_INOUT_SELECTION_MASK) as usize) << 8) + next_byte as usize }; assert_ne!(count, 0, "this should be interpreted as NONE above"); if count > nb_items { return Err("selected number of leading in/outputs out of bounds"); } (0..count).collect() } else { // individual mode let absolute = (selection & TXFS_INOUT_INDIVIDUAL_MODE) == 0; let count = (selection & TXFS_INOUT_SELECTION_MASK) as usize; let mut selected = Vec::with_capacity(count as usize); for _ in 0..count { let first = bytes.next().ok_or("expected an index byte")?; let single_byte = (first & (1 << 7)) == 0; let number = if single_byte { first as usize } else { let next_byte = bytes.next().ok_or("expected another index byte")?; (((first & (1 << 7)) as usize) << 8) + next_byte as usize }; let idx = if absolute { number } else { let rel = if single_byte { read_i7(number as u8) as isize } else { read_i15(number as u16) as isize }; if rel.is_negative() && rel.abs() > current_input_idx as isize { return Err("relative index out of bounds"); } (current_input_idx as isize + rel) as usize }; if idx > nb_items { return Err("selected index out of bounds"); } if let Some(last) = selected.last() { if idx <= *last { return Err("selected indices not in increasing order") } } selected.push(idx); } selected }; Ok((selected, commit_number)) } /// /// /// Assumes that TxFieldSelector is valid. pub fn calculate_txhash( txfs: &[u8], tx: &Transaction, prevouts: &[TxOut], current_input_idx: u32, current_input_last_codeseparator_pos: Option, ) -> Result { assert_eq!(tx.input.len(), prevouts.len()); let txfs = if txfs.is_empty() { TXFS_SPECIAL_TEMPLATE.to_vec() } else if txfs.len() == 1 { convert_short_txfs(txfs[0])?.to_vec() } else { txfs.to_vec() }; let txfs = &txfs; let mut engine = sha256::Hash::engine(); if (txfs[0] & TXFS_CONTROL) != 0 { engine.input(txfs); } let mut bytes = txfs.iter().copied().peekable(); let global = bytes.next().unwrap(); if (global & TXFS_VERSION) != 0 { tx.version.consensus_encode(&mut engine).unwrap(); } if (global & TXFS_LOCKTIME) != 0 { tx.lock_time.consensus_encode(&mut engine).unwrap(); } if (global & TXFS_CURRENT_INPUT_IDX) != 0 { (current_input_idx as u32).consensus_encode(&mut engine).unwrap(); } let current_prevout = &prevouts[current_input_idx as usize]; let current_input = &tx.input[current_input_idx as usize]; if (global & TXFS_CURRENT_INPUT_CONTROL_BLOCK) != 0 { assert!(current_prevout.script_pubkey.is_p2tr(), "only active in taproot context"); if let Some(cb) = current_input.witness.taproot_control_block() { engine.input(&sha256::Hash::hash(&cb)[..]); } else { // keyspend engine.input(&SHA256_EMPTY[..]); } } if (global & TXFS_CURRENT_INPUT_SPENTSCRIPT) != 0 { assert!(current_prevout.script_pubkey.is_p2tr(), "only active in taproot context"); if let Some(script) = current_input.witness.taproot_leaf_script() { let mut eng = sha256::Hash::engine(); script.version.to_consensus().consensus_encode(&mut eng).unwrap(); script.script.consensus_encode(&mut eng).unwrap(); engine.input(&sha256::Hash::from_engine(eng)[..]); } else { engine.input(&SHA256_EMPTY[..]); } } if (global & TXFS_CURRENT_INPUT_LAST_CODESEPARATOR_POS) != 0 { let pos = current_input_last_codeseparator_pos.unwrap_or(u32::MAX); (pos as u32).consensus_encode(&mut engine).unwrap(); } if (global & TXFS_CURRENT_INPUT_TAPROOT_ANNEX) != 0 { if let Some(annex) = current_input.witness.taproot_annex() { engine.input(&sha256::Hash::hash(annex)[..]); } else { engine.input(&SHA256_EMPTY[..]); } } let inout_fields = bytes.next().unwrap_or(0x00); // Inputs let (input_selection, commit_number_inputs) = if let Some(first_byte) = bytes.next() { parse_inout_selection(first_byte, &mut bytes, tx.input.len(), current_input_idx)? } else { (vec![], false) }; if commit_number_inputs { (tx.input.len() as u32).consensus_encode(&mut engine).unwrap(); } if !input_selection.is_empty() && (inout_fields & TXFS_INPUTS_PREVOUTS) != 0 { let hash = { let mut engine = sha256::Hash::engine(); for i in &input_selection { tx.input[*i].previous_output.consensus_encode(&mut engine).unwrap(); } sha256::Hash::from_engine(engine) }; engine.input(&hash[..]); } if !input_selection.is_empty() && (inout_fields & TXFS_INPUTS_SEQUENCES) != 0 { let hash = { let mut engine = sha256::Hash::engine(); for i in &input_selection { tx.input[*i].sequence.consensus_encode(&mut engine).unwrap(); } sha256::Hash::from_engine(engine) }; engine.input(&hash[..]); } if !input_selection.is_empty() && (inout_fields & TXFS_INPUTS_SCRIPTSIGS) != 0 { let hash = { let mut engine = sha256::Hash::engine(); for i in &input_selection { engine.input(&sha256::Hash::hash(&tx.input[*i].script_sig.as_bytes())[..]); } sha256::Hash::from_engine(engine) }; engine.input(&hash[..]); } if !input_selection.is_empty() && (inout_fields & TXFS_INPUTS_PREV_SCRIPTPUBKEYS) != 0 { let hash = { let mut engine = sha256::Hash::engine(); for i in &input_selection { engine.input(&sha256::Hash::hash(&prevouts[*i].script_pubkey.as_bytes())[..]); } sha256::Hash::from_engine(engine) }; engine.input(&hash[..]); } if !input_selection.is_empty() && (inout_fields & TXFS_INPUTS_PREV_VALUES) != 0 { let hash = { let mut engine = sha256::Hash::engine(); for i in &input_selection { prevouts[*i].value.consensus_encode(&mut engine).unwrap(); } sha256::Hash::from_engine(engine) }; engine.input(&hash[..]); } if !input_selection.is_empty() && (inout_fields & TXFS_INPUTS_TAPROOT_ANNEXES) != 0 { let hash = { let mut engine = sha256::Hash::engine(); for i in &input_selection { if prevouts[*i].script_pubkey.is_p2tr() { if let Some(annex) = tx.input[*i].witness.taproot_annex() { engine.input(&sha256::Hash::hash(annex)[..]); } else { engine.input(&SHA256_EMPTY[..]); } } else { engine.input(&SHA256_EMPTY[..]); } } sha256::Hash::from_engine(engine) }; engine.input(&hash[..]); } // Outputs let (output_selection, commit_number_outputs) = if let Some(first_byte) = bytes.next() { parse_inout_selection(first_byte, &mut bytes, tx.output.len(), current_input_idx)? } else { (vec![], false) }; if commit_number_outputs { (tx.output.len() as u32).consensus_encode(&mut engine).unwrap(); } if !output_selection.is_empty() && (inout_fields & TXFS_OUTPUTS_SCRIPTPUBKEYS) != 0 { let hash = { let mut engine = sha256::Hash::engine(); for i in &output_selection { engine.input(&sha256::Hash::hash(&tx.output[*i].script_pubkey.as_bytes())[..]); } sha256::Hash::from_engine(engine) }; hash.consensus_encode(&mut engine).unwrap(); } if !output_selection.is_empty() && (inout_fields & TXFS_OUTPUTS_VALUES) != 0 { let hash = { let mut engine = sha256::Hash::engine(); for i in &output_selection { tx.output[*i].value.consensus_encode(&mut engine).unwrap(); } sha256::Hash::from_engine(engine) }; hash.consensus_encode(&mut engine).unwrap(); } if bytes.next().is_some() { return Err("unexpected additional txfs bytes"); } Ok(sha256::Hash::from_engine(engine)) } mod test_vectors { use super::*; use std::any::Any; use std::ops::{self, RangeBounds}; use bitcoin::hex::DisplayHex; use bitcoin::{Amount, ScriptBuf, Sequence, Witness}; use bitcoin::blockdata::transaction::{self, TxIn}; use bitcoin::opcodes::all::*; fn test_vector_tx() -> (Transaction, Vec) { let tx = Transaction { version: transaction::Version::TWO, lock_time: bitcoin::absolute::LockTime::from_consensus(42), input: vec![ TxIn { previous_output: "3333333333333333333333333333333333333333333333333333333333333333:3".parse().unwrap(), script_sig: ScriptBuf::new(), sequence: Sequence::from_consensus(2), witness: { let mut buf = Witness::new(); buf.push(vec![0x12]); buf }, }, TxIn { previous_output: "4444444444444444444444444444444444444444444444444444444444444444:4".parse().unwrap(), script_sig: ScriptBuf::new(), sequence: Sequence::from_consensus(3), witness: { let mut buf = Witness::new(); buf.push(vec![0x13]); buf.push(vec![0x14]); buf.push(vec![0x50, 0x42]); // annex buf }, }, TxIn { previous_output: "1111111111111111111111111111111111111111111111111111111111111111:1".parse().unwrap(), script_sig: vec![0x23].into(), sequence: Sequence::from_consensus(1), witness: Witness::new(), }, TxIn { previous_output: "2222222222222222222222222222222222222222222222222222222222222222:2".parse().unwrap(), script_sig: ScriptBuf::new(), sequence: Sequence::from_consensus(3), witness: { // p2wsh annex-like stack element let mut buf = Witness::new(); buf.push(vec![0x13]); buf.push(vec![0x14]); buf.push(vec![0x50, 0x42]); // annex buf }, }, ], output: vec![ TxOut { script_pubkey: vec![OP_PUSHNUM_6.to_u8()].into(), value: Amount::from_sat(350), }, TxOut { script_pubkey: vec![OP_PUSHNUM_7.to_u8()].into(), value: Amount::from_sat(351), }, TxOut { script_pubkey: vec![OP_PUSHNUM_8.to_u8()].into(), value: Amount::from_sat(353), }, ], }; let prevs = vec![ TxOut { script_pubkey: vec![ // p2tr 0x51, 0x20, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, ].into(), value: Amount::from_sat(361), }, TxOut { script_pubkey: vec![ // p2tr 0x51, 0x20, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, ].into(), value: Amount::from_sat(362), }, TxOut { script_pubkey: vec![OP_PUSHNUM_16.to_u8()].into(), value: Amount::from_sat(360), }, TxOut { script_pubkey: vec![ // p2wsh 0x00, 0x20, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, ].into(), value: Amount::from_sat(361), }, ]; (tx, prevs) } #[derive(Debug)] struct TestCase { tx: Transaction, prevs: Vec, vectors: Vec } #[derive(Debug)] struct TestVector { txfs: Vec, input: usize, codeseparator: Option, txhash: sha256::Hash, } fn generate_vectors() -> Vec { let all = 0xff; let allio = TXFS_INPUTS_ALL | TXFS_OUTPUTS_ALL; let selnone = TXFS_INOUT_SELECTION_NONE; // 0x00 let selcur = TXFS_INOUT_SELECTION_CURRENT; let selall = TXFS_INOUT_SELECTION_ALL; let number = TXFS_INOUT_NUMBER; let leading = 0; let individual = TXFS_INOUT_SELECTION_MODE; let absolute = 0; let relative = TXFS_INOUT_INDIVIDUAL_MODE; fn r + 'static>(t: T) -> Option> { Some(Box::new(t)) } // txfs and range of inputs to run it on let selectors: &[(&[u8], Option>)] = &[ // global (&[1 << 0, 0], None), (&[1 << 1, 0], None), (&[1 << 2, 0], None), (&[1 << 3, 0], None), (&[1 << 4, 0], None), (&[1 << 5, 0], None), (&[1 << 6, 0], None), (&[1 << 7, 0], None), // outputs (&[all, 0, 0, number | selnone], None), (&[all, TXFS_OUTPUTS_SCRIPTPUBKEYS, 0, selcur], None), (&[all, TXFS_OUTPUTS_VALUES, 0, selcur], None), (&[all, TXFS_OUTPUTS_ALL, 0, selcur], None), (&[all, TXFS_OUTPUTS_SCRIPTPUBKEYS, 0, selall], None), (&[all, TXFS_OUTPUTS_VALUES, 0, selall], None), (&[all, TXFS_OUTPUTS_ALL, 0, selall], None), (&[all, TXFS_OUTPUTS_SCRIPTPUBKEYS, 0, number | selcur], None), (&[all, TXFS_OUTPUTS_VALUES, 0, number | selcur], None), (&[all, TXFS_OUTPUTS_ALL, 0, number | selcur], None), (&[all, TXFS_OUTPUTS_SCRIPTPUBKEYS, 0, number | selall], None), (&[all, TXFS_OUTPUTS_VALUES, 0, number | selall], None), (&[all, TXFS_OUTPUTS_ALL, 0, number | selall], None), // inputs (&[all, 0, number | selnone], None), (&[all, TXFS_INPUTS_PREVOUTS, selcur], None), (&[all, TXFS_INPUTS_SEQUENCES, selcur], None), (&[all, TXFS_INPUTS_SCRIPTSIGS, selcur], None), (&[all, TXFS_INPUTS_PREV_SCRIPTPUBKEYS, selcur], None), (&[all, TXFS_INPUTS_PREV_VALUES, selcur], None), (&[all, TXFS_INPUTS_TAPROOT_ANNEXES, selcur], None), (&[all, TXFS_INPUTS_ALL, selcur], None), (&[all, TXFS_INPUTS_PREVOUTS, selall], None), (&[all, TXFS_INPUTS_SEQUENCES, selall], None), (&[all, TXFS_INPUTS_SCRIPTSIGS, selall], None), (&[all, TXFS_INPUTS_PREV_SCRIPTPUBKEYS, selall], None), (&[all, TXFS_INPUTS_PREV_VALUES, selall], None), (&[all, TXFS_INPUTS_TAPROOT_ANNEXES, selall], None), (&[all, TXFS_INPUTS_ALL, selall], None), (&[all, TXFS_INPUTS_PREVOUTS, number | selcur], None), (&[all, TXFS_INPUTS_SEQUENCES, number | selcur], None), (&[all, TXFS_INPUTS_SCRIPTSIGS, number | selcur], None), (&[all, TXFS_INPUTS_PREV_SCRIPTPUBKEYS, number | selcur], None), (&[all, TXFS_INPUTS_PREV_VALUES, number | selcur], None), (&[all, TXFS_INPUTS_TAPROOT_ANNEXES, number | selcur], None), (&[all, TXFS_INPUTS_ALL, number | selcur], None), (&[all, TXFS_INPUTS_PREVOUTS, number | selall], None), (&[all, TXFS_INPUTS_SEQUENCES, number | selall], None), (&[all, TXFS_INPUTS_SCRIPTSIGS, number | selall], None), (&[all, TXFS_INPUTS_PREV_SCRIPTPUBKEYS, number | selall], None), (&[all, TXFS_INPUTS_PREV_VALUES, number | selall], None), (&[all, TXFS_INPUTS_TAPROOT_ANNEXES, number | selall], None), (&[all, TXFS_INPUTS_ALL, number | selall], None), // both (&[all, allio, selall, selall], None), (&[all, allio, selcur, selcur], None), (&[all, 0, number | selnone, number | selnone], None), (&[all, allio, number | selall, number | selall], None), (&[all, allio, number | selcur, number | selcur], None), (&[all, allio, selcur, selall], None), (&[all, allio, selall, selcur], None), // leading (&[all, allio, leading | 0x01, number | leading | 0x02], None), (&[all, allio, number | selcur, leading | 0x02], None), // individual absolute (&[all, allio, individual | absolute | 0x01, 0x01, individual | absolute | 0x02, 0x00, 0x02], None), (&[all, allio, number | individual | absolute | 0x01, 0x01, number | individual | absolute | 0x02, 0x00, 0x02], None), // individual relative (&[all, allio, individual | relative | 0x01, (-1i8 as u8) >> 1, individual | relative | 0x02, (-1i8 as u8) >> 1, 0], r(1..2)), (&[all, allio, number | individual | relative | 0x01, (-1i8 as u8) >> 1, number | individual | relative | 0x02, (-1i8 as u8) >> 1, 0], r(1..2)), //TODO(stevenroose) test index size, but for that we need > 32 in/outputs // special case template (&[], None), // shorthand txfs, sighash examples (&[0b11111111], None), (&[0b11110111], None), (&[0b11110011], None), (&[0b11111101], None), (&[0b11110101], None), (&[0b11110001], None), (&[0b11101101], None), (&[0b11100101], None), (&[0b11100001], None), (&[0b11001101], None), (&[0b11000101], None), (&[0b11000001], None), ]; let cases = vec![ test_vector_tx(), ]; fn check_range(r: &Box, idx: usize) -> bool { if let Some(ref range) = r.downcast_ref::() { return range.contains(&idx); } if let Some(ref range) = r.downcast_ref::>() { return range.contains(&idx); } if let Some(ref range) = r.downcast_ref::>() { return range.contains(&idx); } if let Some(ref range) = r.downcast_ref::>() { return range.contains(&idx); } unreachable!("invalid range type used: {:?}", r.type_id()); } cases.into_iter().enumerate().map(|(cidx, (tx, prevs))| { let mut vectors = Vec::new(); for (_sidx, (txfs, idx_range)) in selectors.iter().enumerate() { for i in 0..tx.input.len() { let default = r(..2); // only 2 fist inputs are taproot let range = idx_range.as_ref().unwrap_or(default.as_ref().unwrap()); if !check_range(range, i) { continue; } // println!("{} >> #{} ({}) >> {}", cidx, _sidx, txfs.as_hex(), i); match calculate_txhash(txfs, &tx, &prevs, i as u32, None) { Ok(txhash) => vectors.push(TestVector { txfs: txfs.to_vec(), input: i, codeseparator: None, txhash: txhash, }), Err(e) => panic!("Error in vector #{} for selector {}: {}", cidx, txfs.as_hex(), e, ), } } } TestCase { tx, prevs, vectors } }).collect() } pub fn write_vector_file(path: impl AsRef) { use bitcoin::consensus::encode::serialize_hex; let ret = generate_vectors().into_iter().enumerate().map(|(i_tx, c)| serde_json::json!({ "tx": serialize_hex(&c.tx), "prevs": c.prevs.iter().map(|p| serialize_hex(p)).collect::>(), "vectors": c.vectors.into_iter().enumerate().map(|(i_v, v)| serde_json::json!({ "id": format!("{}:{} ({} #{})", i_tx, i_v, v.txfs.as_hex(), v.input), "txfs": v.txfs.as_hex().to_string(), "input": v.input, "codeseparator": v.codeseparator, "txhash": v.txhash, })).collect::>(), })).collect::>(); let mut file = std::fs::File::create(path).unwrap(); serde_json::to_writer_pretty(&mut file, &ret).unwrap(); } } fn main() { test_vectors::write_vector_file("./txhash_vectors.json"); } ================================================ FILE: bip-0346/ref-impl/txhash_vectors.json ================================================ [ { "prevs": [ "69010000000000002251200100000000000000000000000000000000000000000000000000000000000000", "6a010000000000002251200200000000000000000000000000000000000000000000000000000000000000", "68010000000000000160", "69010000000000002200200100000000000000000000000000000000000000000000000000000000000000" ], "tx": "02000000000104333333333333333333333333333333333333333333333333333333333333333303000000000200000044444444444444444444444444444444444444444444444444444444444444440400000000030000001111111111111111111111111111111111111111111111111111111111111111010000000123010000002222222222222222222222222222222222222222222222222222222222222222020000000003000000035e0100000000000001565f0100000000000001576101000000000000015801011203011301140250420003011301140250422a000000", "vectors": [ { "codeseparator": null, "id": "0:0 (0100 #0)", "input": 0, "txfs": "0100", "txhash": "26b25d457597a7b0463f9620f666dd10aa2c4373a505967c7c8d70922a2d6ece" }, { "codeseparator": null, "id": "0:1 (0100 #1)", "input": 1, "txfs": "0100", "txhash": "26b25d457597a7b0463f9620f666dd10aa2c4373a505967c7c8d70922a2d6ece" }, { "codeseparator": null, "id": "0:2 (0200 #0)", "input": 0, "txfs": "0200", "txhash": "e8a4b2ee7ede79a3afb332b5b6cc3d952a65fd8cffb897f5d18016577c33d7cc" }, { "codeseparator": null, "id": "0:3 (0200 #1)", "input": 1, "txfs": "0200", "txhash": "e8a4b2ee7ede79a3afb332b5b6cc3d952a65fd8cffb897f5d18016577c33d7cc" }, { "codeseparator": null, "id": "0:4 (0400 #0)", "input": 0, "txfs": "0400", "txhash": "df3f619804a92fdb4057192dc43dd748ea778adc52bc498ce80524c014b81119" }, { "codeseparator": null, "id": "0:5 (0400 #1)", "input": 1, "txfs": "0400", "txhash": "67abdd721024f0ff4e0b3f4c2fc13bc5bad42d0b7851d456d88d203d15aaa450" }, { "codeseparator": null, "id": "0:6 (0800 #0)", "input": 0, "txfs": "0800", "txhash": "5df6e0e2761359d30a8275058e299fcc0381534545f55cf43e41983f5d4c9456" }, { "codeseparator": null, "id": "0:7 (0800 #1)", "input": 1, "txfs": "0800", "txhash": "d703d3da6a87bd8e0b453f3b6c41edcc9bf331b2b88ef26eb39dc7abee4e00a3" }, { "codeseparator": null, "id": "0:8 (1000 #0)", "input": 0, "txfs": "1000", "txhash": "5df6e0e2761359d30a8275058e299fcc0381534545f55cf43e41983f5d4c9456" }, { "codeseparator": null, "id": "0:9 (1000 #1)", "input": 1, "txfs": "1000", "txhash": "5df6e0e2761359d30a8275058e299fcc0381534545f55cf43e41983f5d4c9456" }, { "codeseparator": null, "id": "0:10 (2000 #0)", "input": 0, "txfs": "2000", "txhash": "ad95131bc0b799c0b1af477fb14fcf26a6a9f76079e48bf090acb7e8367bfd0e" }, { "codeseparator": null, "id": "0:11 (2000 #1)", "input": 1, "txfs": "2000", "txhash": "ad95131bc0b799c0b1af477fb14fcf26a6a9f76079e48bf090acb7e8367bfd0e" }, { "codeseparator": null, "id": "0:12 (4000 #0)", "input": 0, "txfs": "4000", "txhash": "5df6e0e2761359d30a8275058e299fcc0381534545f55cf43e41983f5d4c9456" }, { "codeseparator": null, "id": "0:13 (4000 #1)", "input": 1, "txfs": "4000", "txhash": "227747766d19539b54f018e7ccfde16bd7c38ebbf5649357ecf67bdfb9755b5c" }, { "codeseparator": null, "id": "0:14 (8000 #0)", "input": 0, "txfs": "8000", "txhash": "8509b81230019d2ad970d970f791dfbdc8caf54f5c594fcd327cef9feed206c1" }, { "codeseparator": null, "id": "0:15 (8000 #1)", "input": 1, "txfs": "8000", "txhash": "8509b81230019d2ad970d970f791dfbdc8caf54f5c594fcd327cef9feed206c1" }, { "codeseparator": null, "id": "0:16 (ff000080 #0)", "input": 0, "txfs": "ff000080", "txhash": "6286469e7f9ac95ff97d41ab1cf8a1d8a3872e45f5bac80a1acf8fd9d4397c18" }, { "codeseparator": null, "id": "0:17 (ff000080 #1)", "input": 1, "txfs": "ff000080", "txhash": "74256c5211c8209c1be86fa0d7b92993a03d5e19647b5d1f83fdc65ebee51b86" }, { "codeseparator": null, "id": "0:18 (ff400040 #0)", "input": 0, "txfs": "ff400040", "txhash": "66c3a2d99e0eccce1e769d61b879f6003252912982a9efc138b24365d6c68879" }, { "codeseparator": null, "id": "0:19 (ff400040 #1)", "input": 1, "txfs": "ff400040", "txhash": "f1dfe060222dfa92e1f91d5afd5790ac9de5b1ff5db777282c85e0a968c25d0e" }, { "codeseparator": null, "id": "0:20 (ff800040 #0)", "input": 0, "txfs": "ff800040", "txhash": "52bc63b1b02c3d375d13236938b25d5249df08fb4d891686a70e5702ea12c0e4" }, { "codeseparator": null, "id": "0:21 (ff800040 #1)", "input": 1, "txfs": "ff800040", "txhash": "40351ff507344dd2493e80df868843bac4cff20c456e2ca28cfa39b2a0cf0557" }, { "codeseparator": null, "id": "0:22 (ffc00040 #0)", "input": 0, "txfs": "ffc00040", "txhash": "75ae3a008d82c09aa7afd34abd46f03afe940758d33763b188d1fa2bd068cd80" }, { "codeseparator": null, "id": "0:23 (ffc00040 #1)", "input": 1, "txfs": "ffc00040", "txhash": "6c3adf154dec8e01f323c0ac20ee5731bfbc5af4259a9a87c8ad0c77dd9c4417" }, { "codeseparator": null, "id": "0:24 (ff40003f #0)", "input": 0, "txfs": "ff40003f", "txhash": "8dea16353d8dbb04764bc5a21fa36236aa3f736761cbb9be809a0a870fa6a366" }, { "codeseparator": null, "id": "0:25 (ff40003f #1)", "input": 1, "txfs": "ff40003f", "txhash": "f3d00fee00e8841e38f465e211ede292fde56e1223c0f211786bc1d357593545" }, { "codeseparator": null, "id": "0:26 (ff80003f #0)", "input": 0, "txfs": "ff80003f", "txhash": "d0b05b4c01125da54d473da6d5f21bef264cfa236e9dde70ff140027cef94931" }, { "codeseparator": null, "id": "0:27 (ff80003f #1)", "input": 1, "txfs": "ff80003f", "txhash": "5eb3c700160c0b8b185babc8d2f2be4370f666c660ddb2113a187aacbfbf2b59" }, { "codeseparator": null, "id": "0:28 (ffc0003f #0)", "input": 0, "txfs": "ffc0003f", "txhash": "a28ff0cd1109352b4dcbf74a0d2a6c73732235b532bb8284ad388b8e49838ea5" }, { "codeseparator": null, "id": "0:29 (ffc0003f #1)", "input": 1, "txfs": "ffc0003f", "txhash": "ec672278f9ab6f4a21e9406721c27173e7887b75ab82cdee81988692324b3e47" }, { "codeseparator": null, "id": "0:30 (ff4000c0 #0)", "input": 0, "txfs": "ff4000c0", "txhash": "af6e1adf1ff16c7bae08e4127b30dab4fedee683277c8b65e27897e9013d63cf" }, { "codeseparator": null, "id": "0:31 (ff4000c0 #1)", "input": 1, "txfs": "ff4000c0", "txhash": "a0f1b5db81c1bba78772f6306107809c29c2f01d41e5d74e39fcf3463e666a91" }, { "codeseparator": null, "id": "0:32 (ff8000c0 #0)", "input": 0, "txfs": "ff8000c0", "txhash": "8ce6884e8b3a11d81f69b9642981770cf2f7ed59cd7748e66f443e10cb16094d" }, { "codeseparator": null, "id": "0:33 (ff8000c0 #1)", "input": 1, "txfs": "ff8000c0", "txhash": "d62d70495e26ba054e60328d35595ea3caf74d8faec2a34e08fb0da8ac6e4514" }, { "codeseparator": null, "id": "0:34 (ffc000c0 #0)", "input": 0, "txfs": "ffc000c0", "txhash": "29c5f8ace77d67bc684be308d8bba076ddbccb7db86890f1affde88243111d66" }, { "codeseparator": null, "id": "0:35 (ffc000c0 #1)", "input": 1, "txfs": "ffc000c0", "txhash": "9d7f7313cf89e95b4984f6864fe6103e26fe02d8e930221d1bdf47b8222b5d8d" }, { "codeseparator": null, "id": "0:36 (ff4000bf #0)", "input": 0, "txfs": "ff4000bf", "txhash": "a111bf0e5c46831243ec5d8095ffdb959b316c00e00296dfce12b5dc817f1d29" }, { "codeseparator": null, "id": "0:37 (ff4000bf #1)", "input": 1, "txfs": "ff4000bf", "txhash": "1ac5b588e154bbf4cf1a462eb83718bcd72c1b544867300004950afa15a416a0" }, { "codeseparator": null, "id": "0:38 (ff8000bf #0)", "input": 0, "txfs": "ff8000bf", "txhash": "2ecd12402dd1443629037d5864d5464d9c8812bd44449bfc25b16b0c76bfff79" }, { "codeseparator": null, "id": "0:39 (ff8000bf #1)", "input": 1, "txfs": "ff8000bf", "txhash": "c5a5ac672a574311029e25b4d381f844745aad80e23040119aa9df76570d9ae2" }, { "codeseparator": null, "id": "0:40 (ffc000bf #0)", "input": 0, "txfs": "ffc000bf", "txhash": "6b7d5990b3435e42a4212c88967eb0f9c8b3c3738ecc2fc79d4b48bb386f178c" }, { "codeseparator": null, "id": "0:41 (ffc000bf #1)", "input": 1, "txfs": "ffc000bf", "txhash": "ba92bbf9b3151efaaa0582c5db076066fdc842037daf5c8d51ee425130cd2181" }, { "codeseparator": null, "id": "0:42 (ff0080 #0)", "input": 0, "txfs": "ff0080", "txhash": "3a23df77318fd630a1b004bd49ee23e2f6ffb588a3e38d50577a307401f67127" }, { "codeseparator": null, "id": "0:43 (ff0080 #1)", "input": 1, "txfs": "ff0080", "txhash": "c8c9cb44b4405c2efb77e6fd2a1258d4479042d6dc1fb51bf8aa0448f6514635" }, { "codeseparator": null, "id": "0:44 (ff0140 #0)", "input": 0, "txfs": "ff0140", "txhash": "e2fcdd4957e7891edac19f58776806218069192b0e94d1d77260a555342d06ac" }, { "codeseparator": null, "id": "0:45 (ff0140 #1)", "input": 1, "txfs": "ff0140", "txhash": "3f87e78b8be3e4b28b29c255bd5ed7c10ab69b02963b02b9394aee1b5f788434" }, { "codeseparator": null, "id": "0:46 (ff0240 #0)", "input": 0, "txfs": "ff0240", "txhash": "2589b0924c45f17484e681c5df41fa136833c44b985ef3fbf17974ca46d7ecd4" }, { "codeseparator": null, "id": "0:47 (ff0240 #1)", "input": 1, "txfs": "ff0240", "txhash": "871bc1ff067094336c1860b01a38673cedce057568f036202e7a3e2410847e44" }, { "codeseparator": null, "id": "0:48 (ff0440 #0)", "input": 0, "txfs": "ff0440", "txhash": "91509f1fd4fb675a936c5cf9c79528ea6441750f41ca8851125c1d78f1880a6c" }, { "codeseparator": null, "id": "0:49 (ff0440 #1)", "input": 1, "txfs": "ff0440", "txhash": "6e18b0171ce7aee2307a4e9ecc1e8d625d07116063e52604a85bc6d1064cfc32" }, { "codeseparator": null, "id": "0:50 (ff0840 #0)", "input": 0, "txfs": "ff0840", "txhash": "d9f97f4e62518332b2bd5d0bad604973d5dfef0945a95685d258ce9743d079ec" }, { "codeseparator": null, "id": "0:51 (ff0840 #1)", "input": 1, "txfs": "ff0840", "txhash": "0575703690b0c557080ff3bef27cfe517abacbe420aa9ddaf53cfe3c733ec077" }, { "codeseparator": null, "id": "0:52 (ff1040 #0)", "input": 0, "txfs": "ff1040", "txhash": "eb53fa90d5e2617ec342007a1bf7ac62dbe66c5147ba60a294a7db1704620f75" }, { "codeseparator": null, "id": "0:53 (ff1040 #1)", "input": 1, "txfs": "ff1040", "txhash": "6dc2f01a3b22b761df91d9a6ba9b58d85f26d881585bd252fcf75eed4ab74e94" }, { "codeseparator": null, "id": "0:54 (ff2040 #0)", "input": 0, "txfs": "ff2040", "txhash": "1a7a2897721b14ebabac2dd83964323864d6f54610a21c255b7a61be4042f269" }, { "codeseparator": null, "id": "0:55 (ff2040 #1)", "input": 1, "txfs": "ff2040", "txhash": "953b14f68d47206c29b780c13234a8e2017804367c4b67012626d19e2f21ceff" }, { "codeseparator": null, "id": "0:56 (ff3f40 #0)", "input": 0, "txfs": "ff3f40", "txhash": "e94869fa522e4acd229958b360dd6b9d87f9e59fcead016875b0f97f10c18595" }, { "codeseparator": null, "id": "0:57 (ff3f40 #1)", "input": 1, "txfs": "ff3f40", "txhash": "3262c8c9f7b2538e123f11e7b31aa7c7c5f6c7bf031ac89ead194991a9df74b1" }, { "codeseparator": null, "id": "0:58 (ff013f #0)", "input": 0, "txfs": "ff013f", "txhash": "3ab80fffdf1301f056762b0e2e09c11699a479adbaa1bea38a95a6ec49e94c0e" }, { "codeseparator": null, "id": "0:59 (ff013f #1)", "input": 1, "txfs": "ff013f", "txhash": "2ccab90e40aaab0304458362ba31ce910c41ed446ad14b15a15613a84be0a147" }, { "codeseparator": null, "id": "0:60 (ff023f #0)", "input": 0, "txfs": "ff023f", "txhash": "29ebfe25e2d5e33a416808b36e2d23538c7e94c77ada313fd78a3137471fb618" }, { "codeseparator": null, "id": "0:61 (ff023f #1)", "input": 1, "txfs": "ff023f", "txhash": "eddeb813dabe380be2f59cf04b4e0528a2033933ffea03bb49b45a262ca2d566" }, { "codeseparator": null, "id": "0:62 (ff043f #0)", "input": 0, "txfs": "ff043f", "txhash": "ebd4f5e2636391b007d0c1e68e0d088d6e5a638a3e40c00e322b0a9363b3e477" }, { "codeseparator": null, "id": "0:63 (ff043f #1)", "input": 1, "txfs": "ff043f", "txhash": "9f1cd389104b23b29d534b16d06ba3f0839d58d443f798ada9155bf2f4ebe4f6" }, { "codeseparator": null, "id": "0:64 (ff083f #0)", "input": 0, "txfs": "ff083f", "txhash": "4b596fbefb903426720ba9a3906306371253d2de874537e722a47de29c925647" }, { "codeseparator": null, "id": "0:65 (ff083f #1)", "input": 1, "txfs": "ff083f", "txhash": "ef50137ead871d0dd9c1b4c6cb0c57ea00f7650d111897d0bcd0441622e9375d" }, { "codeseparator": null, "id": "0:66 (ff103f #0)", "input": 0, "txfs": "ff103f", "txhash": "874afe3e5a88a2cc3afc3239ea78e6d0cd91c83ae384880830f0daf1096838d1" }, { "codeseparator": null, "id": "0:67 (ff103f #1)", "input": 1, "txfs": "ff103f", "txhash": "7002a2f133407c98c08f17caac86fdeac6e5f2ae86c059567028a9e2f2718929" }, { "codeseparator": null, "id": "0:68 (ff203f #0)", "input": 0, "txfs": "ff203f", "txhash": "589f39f55732242d97de0fdb8aa8a3736b197d4f319885c32651cd565021da6b" }, { "codeseparator": null, "id": "0:69 (ff203f #1)", "input": 1, "txfs": "ff203f", "txhash": "46fc739044047fc00053ec7532ceee2ea53fe75029a2d65c90d5da2738937b8e" }, { "codeseparator": null, "id": "0:70 (ff3f3f #0)", "input": 0, "txfs": "ff3f3f", "txhash": "ece064b4f1551cfbcff6792e32842bb08335fb2cb5ee430f7707a00d15f89c41" }, { "codeseparator": null, "id": "0:71 (ff3f3f #1)", "input": 1, "txfs": "ff3f3f", "txhash": "e41fd96f9d8f48c6ac04ce5039d850535b668c3b8b83f3913e2a131edfe5b4df" }, { "codeseparator": null, "id": "0:72 (ff01c0 #0)", "input": 0, "txfs": "ff01c0", "txhash": "35aa24440a7e833ed0f6503688a7a7009ebc1999cebd58c10724a2d321d41174" }, { "codeseparator": null, "id": "0:73 (ff01c0 #1)", "input": 1, "txfs": "ff01c0", "txhash": "d3bbb1e58851725a94a5538189b5dad23c9c7cec53549f959e6f498dce737828" }, { "codeseparator": null, "id": "0:74 (ff02c0 #0)", "input": 0, "txfs": "ff02c0", "txhash": "79ee870774e05726bbf47780154ff33e9ded3c67bae7ec02a12663106adbcc68" }, { "codeseparator": null, "id": "0:75 (ff02c0 #1)", "input": 1, "txfs": "ff02c0", "txhash": "01bf86cb8dd28adf6807c505b4c538a2490c213be8b1224b55c7e4b5ab523d97" }, { "codeseparator": null, "id": "0:76 (ff04c0 #0)", "input": 0, "txfs": "ff04c0", "txhash": "8dbd343cd6dd7f92c0c9e0c278d6189f8ae08400e7ffbe0e932fb4675bc0d4f1" }, { "codeseparator": null, "id": "0:77 (ff04c0 #1)", "input": 1, "txfs": "ff04c0", "txhash": "8b566825b9c36b5e0b6916827ad7573cfe74f8a903c1ff06a06329aaa28b9c1d" }, { "codeseparator": null, "id": "0:78 (ff08c0 #0)", "input": 0, "txfs": "ff08c0", "txhash": "98d344d199bb540a91c6a9d70e3daa3ead46c30a377470ffbe1199d12a606aec" }, { "codeseparator": null, "id": "0:79 (ff08c0 #1)", "input": 1, "txfs": "ff08c0", "txhash": "b68c12f03396664d494b2af4363efc89667f76d9bf962e52c2a52fcb0ed877b9" }, { "codeseparator": null, "id": "0:80 (ff10c0 #0)", "input": 0, "txfs": "ff10c0", "txhash": "2fb64ddf05090b11ec14848963af6aac97ea2394623e66d8f9237eb712b5bbe8" }, { "codeseparator": null, "id": "0:81 (ff10c0 #1)", "input": 1, "txfs": "ff10c0", "txhash": "8eaa22ece3e6e61340a013c607ca487270b14143fdb666d021879f5c84fbf661" }, { "codeseparator": null, "id": "0:82 (ff20c0 #0)", "input": 0, "txfs": "ff20c0", "txhash": "70bf9abee31014fc3e454049535e115948ea16022323d58eda379801763b00c5" }, { "codeseparator": null, "id": "0:83 (ff20c0 #1)", "input": 1, "txfs": "ff20c0", "txhash": "5abbe67209f513d56380f45578dc5479ab76e3ed9121f4d100dca09793da2584" }, { "codeseparator": null, "id": "0:84 (ff3fc0 #0)", "input": 0, "txfs": "ff3fc0", "txhash": "791a302cbb5e2a711ef54911a62b9968223bfda2d6c1f91f72ad8680883b4568" }, { "codeseparator": null, "id": "0:85 (ff3fc0 #1)", "input": 1, "txfs": "ff3fc0", "txhash": "5449e0e4fd52db193c70b0804fafd53093753b936cbf6582c33e375ca0c55ed2" }, { "codeseparator": null, "id": "0:86 (ff01bf #0)", "input": 0, "txfs": "ff01bf", "txhash": "0c86d8789f7a98e7aed70940dd78a1ea6b42d3a4adf16fe343d6ddac78c5fdc3" }, { "codeseparator": null, "id": "0:87 (ff01bf #1)", "input": 1, "txfs": "ff01bf", "txhash": "770c254d1a603e09243bd0d193ec89aaaee20958abe3c2249c57565cfb3ebc90" }, { "codeseparator": null, "id": "0:88 (ff02bf #0)", "input": 0, "txfs": "ff02bf", "txhash": "b2f3145c3caaddb1344fd170e62eadd93b34adb5a8262c8e1c2d542f8ce0e045" }, { "codeseparator": null, "id": "0:89 (ff02bf #1)", "input": 1, "txfs": "ff02bf", "txhash": "fbf7a5bec0037e3ed35f0fe243688f6e0fe3583adce9ca221af02bed1cced8cb" }, { "codeseparator": null, "id": "0:90 (ff04bf #0)", "input": 0, "txfs": "ff04bf", "txhash": "d08f2c883d8bc078ee42aa2647307d455a53caeeda3a2d1ce1bcaaaf223b2dc8" }, { "codeseparator": null, "id": "0:91 (ff04bf #1)", "input": 1, "txfs": "ff04bf", "txhash": "0db8760a71982cf0c354be8b286e1a202695aac3c18a952ec0af6c79247a50bd" }, { "codeseparator": null, "id": "0:92 (ff08bf #0)", "input": 0, "txfs": "ff08bf", "txhash": "acb8c88af64ecd6c65931c7549e6e913c7eb8a6305f5abdea1c21ada1c57c1fb" }, { "codeseparator": null, "id": "0:93 (ff08bf #1)", "input": 1, "txfs": "ff08bf", "txhash": "528f4d8c24cc929b21b2bf2306c12225b4a58119a57b46905a4748117a1f671e" }, { "codeseparator": null, "id": "0:94 (ff10bf #0)", "input": 0, "txfs": "ff10bf", "txhash": "dfc30a7df4cd7f105274ce5913b56e1fdb15f842d16259cac5e2142b8e328b72" }, { "codeseparator": null, "id": "0:95 (ff10bf #1)", "input": 1, "txfs": "ff10bf", "txhash": "fc7eb663ecafee91eaeb327be8ce4141eba15be928411b13b1145e825a25c7a5" }, { "codeseparator": null, "id": "0:96 (ff20bf #0)", "input": 0, "txfs": "ff20bf", "txhash": "68ddc75edee9e075116b3a92da91934b873bc5319b7d843964a1bdbbcc98a3fc" }, { "codeseparator": null, "id": "0:97 (ff20bf #1)", "input": 1, "txfs": "ff20bf", "txhash": "70b258975fd720f72300eb935e9ad1d6cb627201535d205ea2547f6379290f2c" }, { "codeseparator": null, "id": "0:98 (ff3fbf #0)", "input": 0, "txfs": "ff3fbf", "txhash": "af99fb1bb1d843814f205517718b70ff2729c3cc0169e97863d4de1b5f97d102" }, { "codeseparator": null, "id": "0:99 (ff3fbf #1)", "input": 1, "txfs": "ff3fbf", "txhash": "d51e4053eae324623ac8b45e6c756f54dc4f674c9024b1739976e481b58e4c29" }, { "codeseparator": null, "id": "0:100 (ffff3f3f #0)", "input": 0, "txfs": "ffff3f3f", "txhash": "2b8b2247712581368099f351dc3c3fea0ee5a46158c2ab8ea023dfd02483656e" }, { "codeseparator": null, "id": "0:101 (ffff3f3f #1)", "input": 1, "txfs": "ffff3f3f", "txhash": "efc150fc72f4d9ade4c88c6bf507c85abcac3c09e6ffb6e57e2b372460a9b58b" }, { "codeseparator": null, "id": "0:102 (ffff4040 #0)", "input": 0, "txfs": "ffff4040", "txhash": "bbc351d3a61ff0531c48883202c347ba6e2e889d0dae526cc302a8978f54194f" }, { "codeseparator": null, "id": "0:103 (ffff4040 #1)", "input": 1, "txfs": "ffff4040", "txhash": "56789e76148add29a6e11a71f9eee1d587967f475a7b7adead3a38aad9753070" }, { "codeseparator": null, "id": "0:104 (ff008080 #0)", "input": 0, "txfs": "ff008080", "txhash": "fc87d178387418de163b5cf92d7ec20236bc4e64d8013926e8202d7ffd35eaff" }, { "codeseparator": null, "id": "0:105 (ff008080 #1)", "input": 1, "txfs": "ff008080", "txhash": "ef7074fa8f70e1c36b9c392afdca434320e9fd58a8e35a5b7722fb832f11cb15" }, { "codeseparator": null, "id": "0:106 (ffffbfbf #0)", "input": 0, "txfs": "ffffbfbf", "txhash": "d872d9eda08df40dc5a6761f90d886720c24b392307df90c00d1647902967ca7" }, { "codeseparator": null, "id": "0:107 (ffffbfbf #1)", "input": 1, "txfs": "ffffbfbf", "txhash": "b3d3393fd149ec4bb0ecf50119f36ba0621259b6d6288d9a2e8b8332bc75bcd7" }, { "codeseparator": null, "id": "0:108 (ffffc0c0 #0)", "input": 0, "txfs": "ffffc0c0", "txhash": "addc2bf0570b09cf5dae3b8535158261e3e7c91db0fb313133343763cd3958dd" }, { "codeseparator": null, "id": "0:109 (ffffc0c0 #1)", "input": 1, "txfs": "ffffc0c0", "txhash": "66e8cf6e41e1f2963d4dd1a78d3e19318b27f34abc5011ef6359ecf5151ab812" }, { "codeseparator": null, "id": "0:110 (ffff403f #0)", "input": 0, "txfs": "ffff403f", "txhash": "9413abd29279ea6ad5a0675d1007ccd3d6d61ef6633eb9415961282f271d6c31" }, { "codeseparator": null, "id": "0:111 (ffff403f #1)", "input": 1, "txfs": "ffff403f", "txhash": "8cd9e9133c585c31e207db07732fb5f6a3c392118c90b4d20e9e7dd470dc38ed" }, { "codeseparator": null, "id": "0:112 (ffff3f40 #0)", "input": 0, "txfs": "ffff3f40", "txhash": "404f72fe8f7365a27bc5b1c496dd11a689a2f7d0f3b7b3c9755a8f7bf11d7b89" }, { "codeseparator": null, "id": "0:113 (ffff3f40 #1)", "input": 1, "txfs": "ffff3f40", "txhash": "59628e1df03ce68564e9035f376ac9c76f7a11d5b1b0b71c5a593da5b4cf5c6d" }, { "codeseparator": null, "id": "0:114 (ffff0182 #0)", "input": 0, "txfs": "ffff0182", "txhash": "ab8c241a251a98288b1758710961c0924e1c27b0df974cd669b2e154101e36b5" }, { "codeseparator": null, "id": "0:115 (ffff0182 #1)", "input": 1, "txfs": "ffff0182", "txhash": "eb561e62a71274921a7e0025e66c51299d1904cfba98debb4a23cee2f49f9209" }, { "codeseparator": null, "id": "0:116 (ffffc002 #0)", "input": 0, "txfs": "ffffc002", "txhash": "d5c3e2f80a574f8f80c016c2ddd4bee2298f4e91a49d07fbf2ff96ee1ebdbbc2" }, { "codeseparator": null, "id": "0:117 (ffffc002 #1)", "input": 1, "txfs": "ffffc002", "txhash": "99efebafd498376dfced0515ae0d1949cb7673bff30bd73a693011edf1541db6" }, { "codeseparator": null, "id": "0:118 (ffff4101420002 #0)", "input": 0, "txfs": "ffff4101420002", "txhash": "72f86b1e8e4721e3aa8c4ddfc744e93e2f4628fe63116e1c592449608077d0ea" }, { "codeseparator": null, "id": "0:119 (ffff4101420002 #1)", "input": 1, "txfs": "ffff4101420002", "txhash": "6dfab74a32a90fd024f5faeab5935486de4c07b76ac788f3a80fb4e426e63dfc" }, { "codeseparator": null, "id": "0:120 (ffffc101c20002 #0)", "input": 0, "txfs": "ffffc101c20002", "txhash": "8bcbd63009fea26f96e1736f2f2b517c7274feef626b3d9524e2dce22b81ec97" }, { "codeseparator": null, "id": "0:121 (ffffc101c20002 #1)", "input": 1, "txfs": "ffffc101c20002", "txhash": "d801364c0d3d9468c17101f1906e89e84d0e325d904ce54a1305885296228055" }, { "codeseparator": null, "id": "0:122 (ffff617f627f00 #1)", "input": 1, "txfs": "ffff617f627f00", "txhash": "a6eab06ad0e6053b0221d50463c6fa5c87dd4926bdff88dfbaae60147fa91beb" }, { "codeseparator": null, "id": "0:123 (ffffe17fe27f00 #1)", "input": 1, "txfs": "ffffe17fe27f00", "txhash": "9f5dee0abdcbdfc6016e7186ad639b50728771eebbd7464e3ba0b5d8f3ef68ea" }, { "codeseparator": null, "id": "0:124 ( #0)", "input": 0, "txfs": "", "txhash": "a1601773a4ddd7a2a1117fffaa670bd67fb3b85f91e2793e25de8c4f848fe0d9" }, { "codeseparator": null, "id": "0:125 ( #1)", "input": 1, "txfs": "", "txhash": "6ae6fe854e08cbf0a25636b575d8bbe63c120ba496796dd30b4924b79f909fbd" }, { "codeseparator": null, "id": "0:126 (ff #0)", "input": 0, "txfs": "ff", "txhash": "45da8ae2f210c2d6985d5c3e1067817838273495da515941e18fa554dc5e740d" }, { "codeseparator": null, "id": "0:127 (ff #1)", "input": 1, "txfs": "ff", "txhash": "335bfdcf79f6ae2ccb7d4972e26106f043813de634ba9a752b4808192f5e8c38" }, { "codeseparator": null, "id": "0:128 (f7 #0)", "input": 0, "txfs": "f7", "txhash": "bba33c04d64d580f27ef181c3482ed7243212176a721613f522415234b194df6" }, { "codeseparator": null, "id": "0:129 (f7 #1)", "input": 1, "txfs": "f7", "txhash": "13b100680de28fd5d7ecd40389c49add2298ea464152c06b859150e7018ea9e6" }, { "codeseparator": null, "id": "0:130 (f3 #0)", "input": 0, "txfs": "f3", "txhash": "27163ce496cf96f4dd5a0dc275ed3aeb4f13fac742011ae657c64536b7523896" }, { "codeseparator": null, "id": "0:131 (f3 #1)", "input": 1, "txfs": "f3", "txhash": "4f45f4c2a2390634e6591cffba66bec810fa17c88734fedc6ce974f765533771" }, { "codeseparator": null, "id": "0:132 (fd #0)", "input": 0, "txfs": "fd", "txhash": "66b2523a0e8ccc2388b401043dcd08bcd9848ce07ba90309a3194a88cceefc58" }, { "codeseparator": null, "id": "0:133 (fd #1)", "input": 1, "txfs": "fd", "txhash": "bf51c6a7993a1abc7f62d92ceb1abaf03ce10df620cab77a9c68bc8b2d993768" }, { "codeseparator": null, "id": "0:134 (f5 #0)", "input": 0, "txfs": "f5", "txhash": "4ac1bd781328f1a24dc514d686b1c0ea78ca28bf4b37e60472f98e9b1c07568c" }, { "codeseparator": null, "id": "0:135 (f5 #1)", "input": 1, "txfs": "f5", "txhash": "be93ef8b84789a7e522f73bb3c0c00afe91075e3a02dc82fb766f31a5e2810db" }, { "codeseparator": null, "id": "0:136 (f1 #0)", "input": 0, "txfs": "f1", "txhash": "0d09ed34a6bf5fbb8d447549c88a9aba198498f8351ddc32c89450cb8e2be34a" }, { "codeseparator": null, "id": "0:137 (f1 #1)", "input": 1, "txfs": "f1", "txhash": "38d07d3216b3a2096ac879292cc4d2eca1eee87c3a8ed0d4e53b11adda28d7b6" }, { "codeseparator": null, "id": "0:138 (ed #0)", "input": 0, "txfs": "ed", "txhash": "4978bd282206c9ad2f781e0ca252e9a37e4a366ca619c09c0a1d37028c8f7f28" }, { "codeseparator": null, "id": "0:139 (ed #1)", "input": 1, "txfs": "ed", "txhash": "009af4edad039ac16da71104b4fdd715a8068a56bd5b27e08a7a5c1eedbfb4e4" }, { "codeseparator": null, "id": "0:140 (e5 #0)", "input": 0, "txfs": "e5", "txhash": "83dc16b7f5dc131be5b21057a9a411e24a773579e5777953598ccfeee3bebcaa" }, { "codeseparator": null, "id": "0:141 (e5 #1)", "input": 1, "txfs": "e5", "txhash": "a5a38488a0ac5600cb790ebc61200e92e4bd2421f0e9cb412e53634efdb4f014" }, { "codeseparator": null, "id": "0:142 (e1 #0)", "input": 0, "txfs": "e1", "txhash": "bcc69369370c5083a378d0c9d6501f30bf61bc9c2e53ca0703d4da81b629ea37" }, { "codeseparator": null, "id": "0:143 (e1 #1)", "input": 1, "txfs": "e1", "txhash": "8746f7789df6c561577f84965b6db3a12eb8f66f34af3006713fef6db9620455" }, { "codeseparator": null, "id": "0:144 (cd #0)", "input": 0, "txfs": "cd", "txhash": "4b75f5635bbceb991d5c3f9c0c2a3d367a9b6b12cb150b0db632e2a8d81e337c" }, { "codeseparator": null, "id": "0:145 (cd #1)", "input": 1, "txfs": "cd", "txhash": "e48d0a29d86078a17a9283f6f1c314499eab7343855f4b9f7140c68d4b346b9f" }, { "codeseparator": null, "id": "0:146 (c5 #0)", "input": 0, "txfs": "c5", "txhash": "6f774daf5b1b163f35b4ca367df2798aa8e66c2ff30b77ea9f2e98a5db2b0ec6" }, { "codeseparator": null, "id": "0:147 (c5 #1)", "input": 1, "txfs": "c5", "txhash": "b21e18937bbfadfb37ef10ebf9dacff13801503e475f2524e9c3bb620c0c1567" }, { "codeseparator": null, "id": "0:148 (c1 #0)", "input": 0, "txfs": "c1", "txhash": "4f3d9c36d74b027ce9487907e36a59076f6a6760c7c5902b4dccac1199379a05" }, { "codeseparator": null, "id": "0:149 (c1 #1)", "input": 1, "txfs": "c1", "txhash": "f6abfe1167fecd2809b28fb8d3b0fc98829c49a8f80f47492a0a910ff5799aa5" } ] } ] ================================================ FILE: bip-0346.md ================================================ ``` BIP: 346 Layer: Consensus (soft fork) Title: OP_TXHASH Authors: Steven Roose Brandon Black Status: Draft Type: Specification Assigned: 2024-04-24 License: BSD-3-Clause ``` # Abstract This BIP proposes a new opcode `OP_TXHASH`, to be activated as a change to the semantics of `OP_SUCCESS189` in tapscript contexts. This opcode provides a generalized method for introspecting certain details of the spending transaction, which enables non-interactive enforcement of certain properties of the transaction spending a certain UTXO. Together with an opcode like `OP_CHECKSIGFROMSTACK`, this opcode effectively provides a fully generalized signature hash construction, fully supporting all existing SIGHASH flags, the proposed sighash flags from [BIP-118](bip-0118.mediawiki) (`SIGHASH_ANYPREVOUT`) and many other new signature hash combinations. The constructions specified in this BIP also open up the way for other potential updates; see Motivation section for more details. # Specification ## OP_TXHASH `OP_TXHASH` redefines the `OP_SUCCESS189` tapscript opcode (`0xbd`) as a soft fork upgrade. This opcode is only active in tapscript contexts. Note that `OP_SUCCESS187` is used by [BIP-443](bip-0443.mediawiki) (`OP_CHECKCONTRACTVERIFY`) and `OP_SUCCESS188` was used by [BIP-345](bip-0345.mediawiki) (`OP_VAULT`) at the time of first draft of this BIP, making `OP_SUCCESS189` the next available opcode for this purpose. It has the following semantics: * There is at least one element on the stack, fail otherwise. * The element is interpreted as the TxFieldSelector and is popped off the stack. * The TxFieldSelector must be valid, fail otherwise. * The 32-byte TxHash of the transaction at the current input index, calculated using the given TxFieldSelector is pushed onto the stack. ## TxFieldSelector The TxFieldSelector has the following encoding. We will give a brief conceptual summary, followed by a reference implementation of the CalculateTxHash function. In the following specifications, the `|` operator is used for the bitwise OR operation. * There are two special cases for the TxFieldSelector: * the empty value, zero bytes long: it is set equal to `TXFS_SPECIAL_TEMPLATE`, the de-facto default value which means everything except the prevouts and the prevout scriptPubkeys and amounts. Special case `TXFS_SPECIAL_TEMPLATE` is 4 bytes long, as follows: * 1: `TXFS_VERSION | TXFS_LOCKTIME | TXFS_CURRENT_INPUT_IDX` * 2: `TXFS_INPUTS_SEQUENCES | TXFS_INPUTS_SCRIPTSIGS | TXFS_OUTPUTS_ALL` * 3: `TXFS_INOUT_NUMBER | TXFS_INOUT_SELECTION_ALL` * 4: `TXFS_INOUT_NUMBER | TXFS_INOUT_SELECTION_ALL` * If the TxFieldSelector has exactly 1 byte, we use a _short notation_. It has its 8 bits assigned as follows, from lowest to highest: * 2/1: Inputs * 00: `TXFS_INOUT_SELECTION_NONE` * 01: `TXFS_INOUT_SELECTION_CURRENT` * 11: `TXFS_INOUT_SELECTION_ALL` * 4/3: Outputs * 00: `TXFS_INOUT_SELECTION_NONE` * 01: `TXFS_INOUT_SELECTION_CURRENT` * 11: `TXFS_INOUT_SELECTION_ALL` * 5: `TXFS_INPUTS_PREVOUTS` * 6: `TXFS_INPUTS_PREV_SCRIPTPUBKEYS | TXFS_INPUTS_PREV_VALUES` * 7: `TXFS_CURRENT_INPUT_CONTROL_BLOCK | TXFS_CURRENT_INPUT_SPENTSCRIPT | TXFS_CURRENT_INPUT_LAST_CODESEPARATOR_POS` * 8: `TXFS_CURRENT_INPUT_IDX` Additionally, it includes `TXFS_VERSION | TXFS_LOCKTIME | TXFS_CONTROL | TXFS_CURRENT_INPUT_TAPROOT_ANNEX` as global fields and `TXFS_INPUTS_SEQUENCES | TXFS_INPUTS_SCRIPTSIGS | TXFS_OUTPUTS_ALL` as input and output fields. These 1-byte selections allow the TxFieldSelector to emulate current signature hashing modes and those defined in [BIP-118](bip-0118.mediawiki): | BIP-341/118 sighash type | 1-byte TxFieldSelector | | :--------------------------- | :--------------------- | | `ALL` | `0b11111111` | | `SINGLE` | `0b11110111` | | `NONE` | `0b11110011` | | `ALL\|ANYONECANPAY` | `0b11111101` | | `SINGLE\|ANYONECANPAY` | `0b11110101` | | `NONE\|ANYONECANPAY` | `0b11110001` | | `ALL\|ANYPREVOUT` | `0b11101101` | | `SINGLE\|ANYPREVOUT` | `0b11100101` | | `NONE\|ANYPREVOUT` | `0b11100001` | | `ALL\|ANYPREVOUTANYSCRIPT` | `0b11001101` | | `SINGLE\|ANYPREVOUTANYSCRIPT`| `0b11000101` | | `NONE\|ANYPREVOUTANYSCRIPT` | `0b11000001` | * If the TxFieldSelector is longer than one byte, the first byte of the TxFieldSelector has its 8 bits assigned as follows, from lowest to highest: * 1: version (`TXFS_VERSION`) * 2: locktime (`TXFS_LOCKTIME`) * 3: current input index (`TXFS_CURRENT_INPUT_IDX`) * 4: current input control block (`TXFS_CURRENT_INPUT_CONTROL_BLOCK`) * 5: current input spent script (`TXFS_CURRENT_INPUT_SPENTSCRIPT`) * 6: current script last `OP_CODESEPARATOR` position (or 0xffffffff) (`TXFS_CURRENT_INPUT_LAST_CODESEPARATOR_POS`) * 7: current input annex including prefix byte (or empty) (`TXFS_CURRENT_INPUT_TAPROOT_ANNEX`) * 8: `TXFS_CONTROL` (i.e. include TxFieldSelector into hash) * The highest bit of the first byte (`TXFS_CONTROL`), we will call the "control bit", and it can be used to control the behavior of the opcode. For `OP_TXHASH`, the control bit is used to determine whether the TxFieldSelector itself has to be included in the resulting hash. (For potential other uses of the TxFieldSelector (like a hypothetical `OP_TX`), this bit can be repurposed.) * The second byte will be used to indicate fields from the inputs and outputs. The 8 bits are assigned the following variables, from lowest to highest: * Specifying which fields of the inputs will be selected: * 1: prevouts (`TXFS_INPUTS_PREVOUTS`) * 2: sequences (`TXFS_INPUTS_SEQUENCES`) * 3: scriptSigs (`TXFS_INPUTS_SCRIPTSIGS`) * 4: prevout scriptPubkeys (`TXFS_INPUTS_PREV_SCRIPTPUBKEYS`) * 5: prevout values (`TXFS_INPUTS_PREV_VALUES`) * 6: taproot annexes (`TXFS_INPUTS_TAPROOT_ANNEXES`) * Specifying which fields of the outputs will be selected: * 7: scriptPubkeys (`TXFS_OUTPUTS_SCRIPTPUBKEYS`) * 8: values (`TXFS_OUTPUTS_VALUES`) * We define as follows: * `TXFS_ALL = TXFS_VERSION | TXFS_LOCKTIME | TXFS_CURRENT_INPUT_IDX | TXFS_CURRENT_INPUT_CONTROL_BLOCK | TXFS_CURRENT_INPUT_LAST_CODESEPARATOR_POS | TXFS_CONTROL` * `TXFS_INPUTS_ALL = TXFS_INPUTS_PREVOUTS | TXFS_INPUTS_SEQUENCES | TXFS_INPUTS_SCRIPTSIGS | TXFS_INPUTS_PREV_SCRIPTPUBKEYS | TXFS_INPUTS_PREV_VALUES | TXFS_INPUTS_TAPROOT_ANNEXES` * `TXFS_OUTPUTS_ALL = TXFS_OUTPUTS_SCRIPTPUBKEYS | TXFS_OUTPUTS_VALUES` * For both inputs and then outputs, expect an additional byte as follows: * The highest bit (`TXFS_INOUT_NUMBER`) indicates whether the "number of in-/outputs" should be committed to. * For the remaining bits, there are three exceptional values: * 0x00 (`TXFS_INOUT_SELECTION_NONE`) means "no in/outputs" (hence only the number of them as `0x80` (`TXFS_INOUT_NUMBER`)). * `0x40` (`TXFS_INOUT_SELECTION_CURRENT`) means "select only the in/output of the current input index" (it is invalid when current index exceeds number of outputs). * `0x3f` (`TXFS_INOUT_SELECTION_ALL`) means "select all in/outputs". * The second highest bit (`TXFS_INOUT_SELECTION_MODE`) is the "specification mode": * Set to 0 it means "leading mode". * Set to 1 it means "individual mode". * In "leading mode", the third highest bit (`TXFS_INOUT_LEADING_SIZE`) is used to indicate the "index size", i.e. the number of bytes will be used to represent the number of in/output. * With "index size" set to 0, the remaining lowest 5 bits of the first byte will be interpreted as the number of leading in/outputs to select. * With "index size" set to 1, the remaining lowest 5 bits of the first byte together with the 8 bits of the next byte will be interpreted as the number of leading in/outputs to select. * In "individual mode", the third highest bit (`TXFS_INOUT_INDIVIDUAL_MODE`) indicates whether we are passing absolute indices (0) or indices relative to the current input (1), the remaining lowest 5 bits will be interpreted as `n`, the number of individual in/outputs follow. * In absolute mode (second highest bit is 0), for each of the `n` indices, at least one extra byte is expected. * If that byte's highest bit is set to 0, the remaining 7 bits represent the absolute index to select. * If that byte's highest bit is set to 1, the remaining 7 bits, together with the next byte's 8 bits represent the absolute index to select. * In relative mode (second highest bit is 1), for each of the `n` indices, at least one extra byte is expected. * If that byte's highest bit is set to 0, the remaining 7 bits represent the relative index in two's complement. * If that byte's highest bit is set to 1, the remaining 7 bits, together with the next byte's 8 bits represent the relative index in two's complement. Effectively, this allows a user to select * all in/outputs * the current input index * the leading in/outputs up to 8,191 * up to 32 individually selected in/outputs ** using absolute indices up to 32,767 ** using indices relative to the current input index from -16382 to +16383. ### TxFieldSelector malleability It is possible to represent the same selected data using multiple different TxFieldSelectors. For this reason, users are advised to always set the `TXFS_CONTROL` field flag that commits to the TxFieldSelector that was used to get the hash. ### Visualization * first byte ``` 1 1 1 1 1 1 1 1 | | | | | | | ^ version | | | | | | ^ locktime | | | | | ^ current input index | | | | ^ current input control block | | | ^ current input spent script | | ^ current script last OP_CODESEPARATOR | ^ current input taproot annex ^ control bit (ie. include TXFS in hash) ``` * second byte ``` <-> outputs | | <---------> inputs 1 1 1 1 1 1 1 1 | | | | | | | ^ prevouts | | | | | | ^ sequences | | | | | ^ scriptSigs | | | | ^ prevout scriptPubkeys | | | ^ prevout values | | ^ taproot annexes | ^ scriptPubkeys ^ values ``` * in/output selector byte "leading 3 in/outputs" ``` 1 0 0 0 0 0 1 1 | | | <-------> integer 0b00011 == 3 | | ^ index size: single byte | ^ leading mode ^ commit the number of in/outputs ``` "leading 257 in/outputs" ``` 1 0 1 0 0 0 0 1 0 0 0 0 0 0 0 1 | | | <------------------------> integer 0b00001 00000001 == 257 | | ^ index size 1: two bytes | ^ leading mode ^ commit the number of in/outputs ``` "indices 1 and 3" ``` 0 1 0 0 0 0 1 0 0 0 0 0 0 0 0 1 0 0 0 0 0 0 1 1 | | | | <--------------> second idx: 3 | | | | <-------------> first idx: 1 | | | | <-----> selection count: 0b0010 == 2 indices | | | ^ index size: single byte per index | | ^ absolute index | ^ individual mode ^ don't commit the number of in/outputs ``` * total example ``` ff ff c2 01 03 83 | | ^ commit number of outputs + leading 3 outputs | | <------> commit number of inputs + inputs at indices 1 and 3 | ^ all input and output fields ^ all regular fields ``` ## Resource limits Using the same validation budget ("sigops budget") introduced in BIP-0342, each TransactionHash decreases the validation budget by 25. If this brings the budget below zero, the script fails immediately.
The following considerations should be made: * All fields that can be of arbitrary size are cacheable as TransactionHash always hashes their hashed values. * In "individual mode", a user can at most commit 32 inputs or outputs, which we don't consider excessive for potential repeated use. * In "leading mode", a caching strategy can be used where the SHA256 context is stored every N in/outputs so that multiple executions of the TransactionHash function can use the caches and only have to hash an additional N-1 items at most. # Motivation This BIP specifies a basic transaction introspection primitive that is useful to either reduce interactivity in multi-user protocols or to enforce some basic constraints on transactions. Additionally, the constructions specified in this BIP can lay the groundwork for some potential future upgrades: * The TxFieldSelector construction would work well with a hypothetical opcode `OP_TX` that allows for directly introspecting the transaction by putting the fields selected on the stack instead of hashing them together. * The TransactionHash obtained by `OP_TXHASH` can be combined with `OP_CHECKSIGFROMSTACK` (see [BIP-348](bip-0348.md)) to effectively create an incredibly flexible signature hash, which would enable constructions like `SIGHASH_ANYPREVOUT`. * The TransactionHash obtained by `OP_TXHASH` can be introduced as a native sighash calculation in a future segwit upgrade, so that signatures using the TransactionHash as their sighash can be used in keyspend context. ## Comparing with some alternative proposals * This proposal strictly generalizes BIP-119's `OP_CHECKTEMPLATEVERIFY`, as the default mode of our TxFieldSelector is semantically the same (though not byte-for-byte identical) as what `OP_CTV` accomplishes, without costing any additional bytes. Additionally, using `OP_TXHASH` allows for more flexibility which can help in the case for * enabling adding fees to a transaction without breaking a multi-tx protocol; * multi-user protocols where users are only concerned about their own inputs and outputs. * Constructions like `OP_IN_OUT_VALUE` used with `OP_EQUALVERIFY` can be emulated by two `OP_TXHASH` instances by using the TxFieldSelector to select a single input value first and a single output value second and enforcing equality on the hashes. Neither of these alternatives can be used to enforce small value differences without the availability of 64-bit arithmetic in Script. * Like mentioned above, `SIGHASH_ANYPREVOUT` can be emulated using `OP_TXHASH` when combined with `OP_CHECKSIGFROMSTACK`: ` OP_TXHASH OP_CHECKSIGFROMSTACK` effectively emulates `SIGHASH_ANYPREVOUT`. # Reference Implementation A reference implementation in Rust is provided attached as part of this BIP together with a JSON file of test vectors generated using the reference implementation. # Design Considerations This specification in in _Draft_ and there is definitely still room for feedback and improvements. Some considerations that were made but could be revisited: - The `0b10` in/output selector for the shorthand is unused. Could possibly be filled in with "current + next", "current + previous" or any other semantics. - The individual index selection semantics allow for absolute indices up to ~32k and relative ones up to +/- ~16k, which is probably excessive. When removing the second byte there would reduce that to just 256 and +/- 128 respectively. - Similar to `OP_TEMPLATEHASH` (BIP number to be assigned, [PR](https://github.com/bitcoin/bips/pull/1974)), we could not support `scriptSigs` anymore and remove `TXFS_INPUTS_SCRIPTSIGS`. This field could then possibly be repurposed. # Backwards Compatibility `OP_TXHASH` replaces `OP_SUCCESS189`. The `SUCCESS` opcodes were introduced in taproot (BIP-342) to support changing the semantics of opcodes in ways that do allow the new semantics to change the stack. For this reason, `OP_TXHASH` only works in tapscript context. Since it is overriding a `SUCCESS` opcode, any older version of the software will always accept any script that uses the opcode, while the new versions of the software will validate the scripts according to the semantics outlined in this BIP. As such, this is also a soft fork change. ## Interactions with other BIPs This proposal interacts with several other BIPs: * **[BIP-118](bip-0118.mediawiki) (SIGHASH_ANYPREVOUT)**: `OP_TXHASH` can be combined with `OP_CHECKSIGFROMSTACK` (BIP-348) to emulate `SIGHASH_ANYPREVOUT` and other signature hash modes defined in BIP-118. The 1-byte TxFieldSelector format explicitly supports these modes. * **[BIP-119](bip-0119.mediawiki) (OP_CHECKTEMPLATEVERIFY)**: `OP_TXHASH` with the empty TxFieldSelector produces a hash semantically equivalent to BIP-119's `OP_CHECKTEMPLATEVERIFY`, making this proposal a generalization of BIP-119. * **[BIP-347](bip-0347.mediawiki) (OP_CAT)**: When combined with `OP_CAT`, `OP_TXHASH` enables powerful transaction introspection capabilities. The bit encoding format is designed to be explicit about endianness to ensure correct interaction with concatenation operations. * **[BIP-348](bip-0348.md) (OP_CHECKSIGFROMSTACK)**: Together with `OP_CHECKSIGFROMSTACK`, `OP_TXHASH` provides a fully generalized signature hash construction, enabling flexible covenant designs and multi-user protocols. # Implementation A reference implementation is included as part of the BIP, see [here](./bip-0346/ref-impl/src/main.rs). This implementation focusses on clarity and correctness, not on efficiency. A rudimentary set of test vectors is also generated from this implementation and included [here](./bip-0346/ref-impl/txhash_vectors.json). Furthermore, following other implementation attempts exist: * A proposed implementation for Bitcoin Core is available here: https://github.com/bitcoin/bitcoin/pull/29050 * A proposed implementation for rust-bitcoin is available here: https://github.com/rust-bitcoin/rust-bitcoin/pull/2275 NOTE: These implementations are slightly outdated as they were made for an earlier version of this specification. Updates are in progress. Both of the above implementations perform effective caching to avoid potential denial-of-service attack vectors. # Deployment This BIP can be deployed using a BIP 9 VersionBits deployment. The specific strategy and bit assignment are left unspecified and can later be amended to the BIP depending on community preference. # Acknowledgement Credit for this proposal mostly goes to Jeremy Rubin for his work on BIP-119's `OP_CHECKTEMPLATEVERIFY` and to Russell O'Connor for the original idea of generalizing `OP_CHECKTEMPLATEVERIFY` into `OP_TXHASH`. Additional thanks to Andrew Poelstra, Greg Sanders, Rearden Code, Rusty Russell and others for their feedback on the specification. # Copyright This document is licensed under the 3-clause BSD license. ================================================ FILE: bip-0347.mediawiki ================================================
  BIP: 347
  Layer: Consensus (soft fork)
  Title: OP_CAT in Tapscript
  Authors: Ethan Heilman 
           Armin Sabouri 
  Status: Complete
  Type: Specification
  Assigned: 2023-12-11
  License: BSD-3-Clause
  Discussion: 2023-10-21: https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2023-October/022049.html [bitcoin-dev] Proposed BIP for OP_CAT
  Version: 1.0.0
  Requires: 340, 341, 342
==Abstract== This BIP introduces OP_CAT as a tapscript opcode which allows the concatenation of two values on the stack. OP_CAT would be activated via a soft fork by redefining the opcode OP_SUCCESS126 (126 in decimal and 0x7e in hexadecimal). This is the same opcode value used by the original OP_CAT. == Copyright == This document is licensed under the 3-clause BSD license. ==Specification== When evaluated, the OP_CAT instruction: # Pops the top two values off the stack, # concatenates the popped values together in stack order, # and then pushes the concatenated value on the top of the stack. Given the stack ''[x1, x2]'', where ''x2'' is at the top of the stack, OP_CAT will push ''x1 || x2'' onto the stack. By ''||'' we denote concatenation. OP_CAT fails if there are fewer than two values on the stack or if a concatenated value would have a combined size greater than the maximum script element size of 520 bytes. This opcode would be activated via a soft fork by redefining the tapscript opcode OP_SUCCESS126 (126 in decimal and 0x7e in hexadecimal) to OP_CAT. ==Motivation== Bitcoin Tapscript lacks a general purpose way of combining objects on the stack, restricting the expressiveness and power of Tapscript. This prevents, among many other things, the ability to construct and evaluate merkle trees and other hashed data structures in Tapscript. OP_CAT, by adding a general purpose way to concatenate stack values, would overcome this limitation and greatly increase the functionality of Tapscript. OP_CAT aims to expand the toolbox of the tapscript developer with a simple, modular, and useful opcode in the spirit of Unix R. Pike and B. Kernighan, "Program design in the UNIX environment", 1983, https://harmful.cat-v.org/cat-v/unix_prog_design.pdf. To demonstrate the usefulness of OP_CAT below we provide a non-exhaustive list of some usecases that OP_CAT would enable: * Bitstream, a protocol for the atomic swap (fair exchange) of bitcoins for decryption keys, that enables decentralized file hosting systems paid in Bitcoin. While such swaps are currently possible on Bitcoin without OP_CAT, they require the use of complex and computationally expensive Verifiable Computation cryptographic techniques. OP_CAT would remove this requirement on Verifiable Computation, making such protocols far more practical to build in Bitcoin. R. Linus, "BitStream: Decentralized File Hosting Incentivised via Bitcoin Payments", 2023, https://robinlinus.com/bitstream.pdf * Tree signatures provide a multisignature script whose size can be logarithmic in the number of public keys and can encode spend conditions beyond n-of-m. For instance a transaction less than 1KB in size could support tree signatures with up to 4,294,967,296 public keys. This also enables generalized logical spend conditions. P. Wuille, "Multisig on steroids using tree signatures", 2015, https://blog.blockstream.com/en-treesignatures/ * Post-Quantum Lamport signatures in Bitcoin transactions. Lamport signatures merely require the ability to hash and concatenate values on the stack. J. Rubin, "[bitcoin-dev] OP_CAT Makes Bitcoin Quantum Secure [was CheckSigFromStack for Arithmetic Values]", 2021, https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2021-July/019233.html It has been proposed that if ECDSA is broken or a powerful computer was on the horizon, there might be an effort to protect ownership of bitcoins by allowing people to mark their taproot outputs as "script-path only" and then move their coins into such outputs with a leaf in the script tree requiring a Lamport signature. It is an open question if a tapscript commitment would preserve the quantum resistance of Lamport signatures. Beyond this question, the use of Lamport Signatures in taproot outputs is unlikely to be quantum resistant even if the script spend-path is made quantum resistant. This is because taproot outputs can also be spent with a key. An attacker with a sufficiently powerful quantum computer could bypass the taproot script spend-path by finding the discrete log of the taproot output and thus spending the output using the key spend-path. The use of "Nothing Up My Sleeve" (NUMS) points as described in [[bip-0341.mediawiki|BIP341]] to disable the key spend-path does not disable the key spend-path against a quantum attacker as NUMS relies on the hardness of finding discrete logs. We are not aware of any mechanism which could disable the key spend-path in a taproot output without a softfork change to taproot. * Non-equivocation contracts T. Ruffing, A. Kate, D. Schröder, "Liar, Liar, Coins on Fire: Penalizing Equivocation by Loss of Bitcoins", 2015, https://web.archive.org/web/20221023121048/https://publications.cispa.saarland/565/1/penalizing.pdf in tapscript provide a mechanism to punish equivocation/double spending in Bitcoin payment channels. OP_CAT enables this by enforcing rules on the spending transaction's nonce. The capability is a useful building block for payment channels and other Bitcoin protocols. * Vaults M. Moser, I. Eyal, and E. G. Sirer, Bitcoin Covenants, https://web.archive.org/web/20220203124718/https://fc16.ifca.ai/bitcoin/papers/MES16.pdf which are a specialized covenant that allows a user to block a malicious party who has compromised the user's secret key from stealing the funds in that output. As shown in A. Poelstra, "CAT and Schnorr Tricks II", 2021, https://www.wpsoftware.net/andrew/blog/cat-and-schnorr-tricks-ii.html OP_CAT is sufficient to build vaults in Bitcoin. * Replicating CheckSigFromStack A. Poelstra, "CAT and Schnorr Tricks I", 2021, https://www.wpsoftware.net/andrew/blog/cat-and-schnorr-tricks-i.html which would allow the creation of simple covenants and other advanced contracts without having to presign spending transactions, possibly reducing complexity and the amount of data that needs to be stored. Originally shown to work with Schnorr signatures, this result has been extended to ECDSA signatures R. Linus, "Covenants with CAT and ECDSA", 2023, https://gist.github.com/RobinLinus/9a69f5552be94d13170ec79bf34d5e85#file-covenants_cat_ecdsa-md. * OP_CAT would allow tapscript to perform arbitrary computation on stack elements larger than 32-bits such as signatures and public keys. While Collider Script E. Heilman, V. I. Kolobov, A. M. Levy, A. Poelstra, "ColliderScript: Covenants in Bitcoin via 160-bit hash collisions", 2024, https://eprint.iacr.org/2024/1802 showed that even without OP_CAT tapscript can perform arbitrary computation on stack elements larger than 32-bits, this approach is extremely computationally expensive. In practice, today's tapscript can only perform arbitrary computation on 32-bit stack elements. OP_CAT was not designed with this usecase in mind and OP_CAT an inefficient way to perform this task. * BitVMR. Linus, L. Aumayr, A. Zamyatin, A. Pelosi, Z. Avarikioti, M. Maffei "BitVM2: Bridging Bitcoin to Second Layers", 2025, https://bitvm.org/bitvm_bridge.pdf improvements. OP_CAT would enable BitVM2 to eliminating the trusted setup from its proof system allow BitVM2 to reduce the size of transactions it uses. OP_CAT was available in early versions of Bitcoin. In 2010, a single commit disabled OP_CAT, along with another 15 opcodes. Folklore states that OP_CAT was removed in this commit because it enabled the construction of a script whose evaluation could have memory usage exponential in the size of the script. For example, a script that pushed a 1-byte value on the stack and then repeated the opcodes OP_DUP, OP_CAT 40 times would result in a stack element whose size was greater than 1 terabyte assuming no maximum stack element size. As Bitcoin at that time had a maximum stack element size of 5000 bytes, the effect of this expansion was limited to 5000 bytes. This is no longer an issue because tapscript enforces a maximum stack element size of 520 bytes. ==Rationale== Our decision to reenable OP_CAT by redefining a tapscript OP_SUCCESSx opcode to OP_CAT was motivated to leverage the tapscript softfork opcode upgrade path introduced in [[bip-0342.mediawiki|BIP342]]. We specifically choose to use OP_SUCCESS126 rather than another OP_SUCCESSx as OP_SUCCESS126 uses the same opcode value (126 in decimal and 0x7e in hexadecimal) that was used for OP_CAT prior to it being disabled in Bitcoin. This removes a potential source of confusion that would exist if we had a opcode value different from the one used in the original OP_CAT opcode. While the OP_SUCCESSx opcode upgrade path could enable us to increase the stack element size while reenabling OP_CAT, we wanted to separate the decision to change the stack element size limit from the decision to reenable OP_CAT. This BIP takes no position in favor or against increasing the stack element size limit. ==Backwards Compatibility== OP_CAT usage in a non-tapscript script will continue to trigger the SCRIPT_ERR_DISABLED_OPCODE. The only change would be to OP_CAT usage in tapscript. This change to tapscript would be activated as a soft fork that redefines an OP_SUCCESSx opcode (OP_SUCCESS126) to OP_CAT. ==Reference implementation==
case OP_CAT:
{
  if (stack.size() < 2)
    return set_error(serror, SCRIPT_ERR_INVALID_STACK_OPERATION);
  valtype& vch1 = stacktop(-2);
  valtype& vch2 = stacktop(-1);
  if (vch1.size() + vch2.size() > MAX_SCRIPT_ELEMENT_SIZE)
    return set_error(serror, SCRIPT_ERR_PUSH_SIZE);
  vch1.insert(vch1.end(), vch2.begin(), vch2.end());
  stack.pop_back();
}
break;
The value of MAX_SCRIPT_ELEMENT_SIZE is 520. This implementation is inspired by the original implementation of [https://github.com/bitcoin/bitcoin/blob/01cd2fdaf3ac6071304ceb80fb7436ac02b1059e/script.cpp#L381-L393 OP_CAT as it existed in the Bitcoin codebase] prior to the commit "misc changes" 4bd188cS. Nakamoto, "misc changes", Aug 25 2010, https://github.com/bitcoin/bitcoin/commit/4bd188c4383d6e614e18f79dc337fbabe8464c82#diff-27496895958ca30c47bbb873299a2ad7a7ea1003a9faa96b317250e3b7aa1fefR94 which disabled it:
case OP_CAT:
{
    // (x1 x2 -- out)
    if (stack.size() < 2)
        return false;
    valtype& vch1 = stacktop(-2);
    valtype& vch2 = stacktop(-1);
    vch1.insert(vch1.end(), vch2.begin(), vch2.end());
    stack.pop_back();
    if (stacktop(-1).size() > 5000)
        return false;
}
break;
An alternative implementation of OP_CAT can be found in Elements Roose S., Elements Project, "Re-enable several disabled opcodes", 2019, https://github.com/ElementsProject/elements/commit/13e1103abe3e328c5a4e2039b51a546f8be6c60a#diff-a0337ffd7259e8c7c9a7786d6dbd420c80abfa1afdb34ebae3261109d9ae3c19R740-R759. ==Test Vectors== The following test vectors use Bitcoin-core JSON script-test format.
[
    [
        "78a11a1260c1101260",
        "78a11a1260",
        "c1101260",
        "#SCRIPT# CAT EQUAL",
        "#CONTROLBLOCK#",
        0.00000001
    ],
    "",
    "0x51 0x20 #TAPROOTOUTPUT#",
    "P2SH,WITNESS,TAPROOT,OP_CAT",
    "OK",
    "TAPSCRIPT CATs 78a11a1260 and c1101260 together and checks it is EQUAL to stack element 78a11a1260c1101260"
],
[
    [
        "51",
        "bbbb",
        "01",
        "#SCRIPT# IF CAT ELSE DROP ENDIF",
        "#CONTROLBLOCK#",
        0.00000001
    ],
    "",
    "0x51 0x20 #TAPROOTOUTPUT#",
    "P2SH,WITNESS,TAPROOT,OP_CAT",
    "OK",
    "TAPSCRIPT Tests CAT inside of an IF ELSE conditional (true IF)"
],
[
    [
        "",
        "09ca7009ca7009ca7009ca7009ca70",
        "#SCRIPT# CAT",
        "#CONTROLBLOCK#",
        0.00000001
    ],
    "",
    "0x51 0x20 #TAPROOTOUTPUT#",
    "P2SH,WITNESS,TAPROOT,OP_CAT",
    "OK",
    "TAPSCRIPT (['', 09ca7009ca7009ca7009ca7009ca70], CAT) Tests CAT succeeds when one of the two values to concatenate is of size zero"
],
A full test suite with additional vectors can be found at the Bitcoin [https://github.com/bitcoin/bitcoin/pull/29247 OP_CAT PR]. ==References== ==Changelog== * __1.0.0__ (2026-03-01) - Marked as complete. * __0.3.1__ (2026-01-23) - Made compliant with BIP 003, use cases added. * __0.3.0__ (2024-05-06) - Merged to BIP repo * __0.2.0__ (2024-04-24) - Assigned BIP number * __0.1.0__ (2023-12-11) - Initial draft posted May 6, 2024 ==Acknowledgements== We wish to acknowledge Dan Gould for encouraging and helping review this effort. We also want to thank Madars Virza, Jeremy Rubin, Andrew Poelstra, Bob Summerwill, Tim Ruffing and Johan T. Halseth for their feedback, review and helpful comments. ================================================ FILE: bip-0348.md ================================================ ``` BIP: 348 Layer: Consensus (soft fork) Title: CHECKSIGFROMSTACK Authors: Brandon Black Jeremy Rubin Status: Draft Type: Specification Assigned: 2024-11-26 License: BSD-3-Clause ``` ## Abstract This BIP describes a new opcode for the purpose of checking cryptographic signatures in bitcoin scripts against data from the stack. ## Summary When verifying taproot script spends having leaf version 0xc0 (as defined in [BIP 342]), we propose `OP_CHECKSIGFROMSTACK` to replace `OP_SUCCESS204` (0xcc). `OP_CHECKSIGFROMSTACK` has semantics similar to `OP_CHECKSIG`, as specified below. Briefly, it pops 3 elements from the stack: a 32-byte public key, a message, and a signature. If the signature is valid for that public key and message, 1 is pushed to the stack. If the signature is the empty vector, 0 is pushed to the stack, and otherwise script execution fails. Only 32-byte keys are constrained. Similar to [BIP 342] unknown key types, for other key lengths no signature verification is performed and it is considered successful. ## Specification * If fewer than 3 elements are on the stack, the script MUST fail and terminate immediately. * The public key (top element), message (second to top element), and signature (third from top element) are read from the stack. * The top three elements are popped from the stack. * If the public key size is zero, the script MUST fail and terminate immediately. * If the public key size is 32 bytes, it is considered to be a public key as described in [BIP 340]: * If the signature is not the empty vector, the signature is validated against the public key and message according to [BIP 340]. Validation failure in this case immediately terminates script execution with failure. * If the public key size is not zero and not 32 bytes; the public key is of an unknown public key type. Signature verification for unknown public key types succeeds as if signature verification for a known public key type had succeeded. * If the script did not fail and terminate before this step, regardless of the public key type: * If the signature is the empty vector: An empty vector is pushed onto the stack, and execution continues with the next opcode. * If the signature is not the empty vector: * The opcode is counted towards the sigops budget as described in [BIP 342]. * A 1-byte value 0x01 is pushed onto the stack. ## Design Considerations 1. Message hashing: [BIP 340] is compatible with any size of message and does not require it to be a securely hashed input, so the message is not hashed prior to [BIP 340] verification. 2. Lack of verify semantics: Adding a single opcode for this purpose keeps the implementation and design simple. An earlier draft had a verify variant as a NOP upgrade, and if this functionality is later brought to legacy scripts, that would be a good time to add a verify variant. 3. Add/multisig: No concession is made to `OP_CHECKMULTISIG` or `OP_CHECKSIGADD` semantics with `OP_CHECKSIGFROMSTACK`. In Tapscript, add semantics can be implemented with 1 additional vByte per key (`OP_TOALTSTACK OP_CHECKSIGFROMSTACK OP_FROMALTSTACK OP_ADD`). 4. Splitting R/S on the stack: Implementing split/separate signatures is left as an exercise for other bitcoin upgrades, such as [BIP 347] (`OP_CAT`). 5. APO-style ([BIP 118]) Taproot internal key: Rather than introducing an additional key type in this change, we suggest implementing `OP_INTERNALKEY` ([BIP 349]) or separately introducing that key type for all Tapscript signature checking operations in a separate change. ## Resource Limits These opcodes are treated identically to other signature checking opcodes and count against the sigops and budget. ## Motivation ### LN Symmetry When combined with [BIP 119] (`OP_CHECKTEMPLATEVERIFY`/CTV), `OP_CHECKSIGFROMSTACK` (CSFS) can be used to implement Lightning Symmetry channels. The construction `OP_CHECKTEMPLATEVERIFY OP_CHECKSIGFROMSTACK` with a spend stack containing the CTV hash and a signature for it is logically equivalent to ` OP_CHECKSIG` and a signature over `SIGHASH_ALL|SIGHASH_ANYPREVOUTANYSCRIPT`. The `OP_CHECKSIGFROMSTACK` construction is 8 vBytes larger. Summary of alternatives: * CTV+CSFS is the minimal functionality needed for Lightning Symmetry but requires the use of an `OP_RETURN` for data availability * APO is the original design for Lightning Symmetry and uses the taproot annex for data availability. * LNHANCE (CTV+CSFS+IKEY+PC) is the most efficient and direct way currently designed to implement Lightning Symmetry. ### Delegation Using a script like: ` SWAP IF 2 PICK SWAP CSFS VERIFY ENDIF CHECKSIG` either direct verification or delegation can be achieved by the following unlock stacks: ` 0` or ` 1` ### Advanced delegation when combined with [OP_PAIRCOMMIT] or OP_CAT Using a script like: `CLTV OVER PAIRCOMMIT TOALT CHECKSIGVERIFY FROMALT CSFS` or: `CLTV SHA256 OVER CAT TOALT CHECKSIGVERIFY FROMALT CSFS` with the unlock stack: ` ` Delegates to a public key after a lock time, enabling delegation to various keys after various associated times. ## Reference Implementation A reference implementation is provided here: https://github.com/bitcoin/bitcoin/pull/29270 ## Backward Compatibility By constraining the behavior of an OP_SUCCESS opcode, deployment of the BIP can be done in a backwards compatible, soft-fork manner. If anyone were to rely on the OP_SUCCESS behavior of `OP_SUCCESS204`, `OP_CHECKSIGFROMSTACK` would invalidate their spend. ## Deployment TBD ## Credits Reference implementation was made with reference to the implementation in Elements and started by moonsettler. ## Copyright This document is licensed under the 3-clause BSD license. [BIP 119]: https://github.com/bitcoin/bips/blob/master/bip-0119.mediawiki [BIP 118]: https://github.com/bitcoin/bips/blob/master/bip-0118.mediawiki [BIP 340]: https://github.com/bitcoin/bips/blob/master/bip-0340.mediawiki [BIP 342]: https://github.com/bitcoin/bips/blob/master/bip-0342.mediawiki [BIP 349]: https://github.com/bitcoin/bips/blob/master/bip-0349.md [BIP 347]: https://github.com/bitcoin/bips/blob/master/bip-0347.mediawiki [OP_PAIRCOMMIT]: https://github.com/bitcoin/bips/pull/1699 [mailing list]: https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2021-July/019192.html ================================================ FILE: bip-0349.md ================================================ ``` BIP: 349 Layer: Consensus (soft fork) Title: OP_INTERNALKEY Authors: Brandon Black Jeremy Rubin Status: Draft Type: Specification Assigned: 2024-11-14 License: BSD-3-Clause ``` ## Abstract This BIP describes a new tapscript opcode (`OP_INTERNALKEY`) which pushes the _taproot internal key_ to the stack. ## Specification When verifying taproot script path spends having leaf version `0xc0` (as defined in [BIP 342]), `OP_INTERNALKEY` replaces `OP_SUCCESS203` (0xcb). `OP_INTERNALKEY` pushes the 32-byte x-only representation of the _taproot internal key_ (referred to as _p_), as defined in [BIP 341], to the stack. ## Motivation ### Key spend with additional conditions When building taproot outputs, especially those secured by an aggregate key representing more than one signer, the parties may wish to collaborate on signing with the _taproot internal key_, but only with additional script restrictions. In this case, `OP_INTERNALKEY` saves 8 vBytes. ### Mitigated control block overhead for scripts using hash locks In cases where key path spending is not desired, the internal key may be set to a NUMS point whose bytes would otherwise be required in a tapscript. This could be used with any hash locked transaction, for example, to save 8 vBytes. Note: The internal key must be the X coordinate of a point on the SECP256K1 curve, so any such hash must be checked and modified until it is such an X coordinate. This will typically take approximately 2 attempts. ### Re-Keying with Merkle Root Preservation Consider a program such `CTV CSFS CLTV`. Such fragments are useful for LN-Symmetry applications. Such a program would be embedded within a Taproot script path, such as `TR(X, {CTV CSFS CLTV})`. Were the internal key to be updated from `X` to `Y`, the resulting program would be: `TR(Y, {CTV CSFS CLTV})`. The key in the leaf and the key-path would be mismatched. Were `OP_INTERNALKEY` to be used, the leaf would automatically re-key. E.g., `TR(X, {CTV OP_INTERNALKEY CSFS CLTV})` is equivalent to `TR(X, {CTV CSFS CLTV})` and `TR(Y, {CTV OP_INTERNALKEY CSFS CLTV})` is equivalent to `TR(Y, {CTV CSFS CLTV})`. While this particular example is contrived, the general technique of using `OP_INTERNALKEY` as updatable across an entire script tree is a helpful covenant primitive when it is desirable to invalidate signatures from prior states. For example, the theoretical `OP_TAPLEAFUPDATEVERIFY` opcode modifies the internal key directly to remove or add a participant, and `OP_INTERNALKEY` would ensure that the tweaked key is used from all script paths where desired. ## Reference Implementation A reference implementation is provided here: https://github.com/bitcoin/bitcoin/pull/29269 ## Backward Compatibility By constraining the behavior of an OP_SUCCESS opcode, deployment of the BIP can be done in a backwards compatible, soft-fork manner. If anyone were to rely on the OP_SUCCESS behavior of `OP_SUCCESS203`, `OP_INTERNALKEY` would invalidate their spend. ## Deployment TBD ## Credits The concept for INTERNALKEY first arose in a [discussion](https://gnusha.org/bitcoin-wizards/2022-01-05.log) between Russell O'Connor and Jeremy Rubin in Bitcoin Wizards IRC, inspired by BIP-0118's key punning technique for the internal key. It was later drafted into this BIP by Brandon Black. ## Copyright This document is licensed under the 3-clause BSD license. [BIP 341]: https://github.com/bitcoin/bips/blob/master/bip-0341.mediawiki [BIP 342]: https://github.com/bitcoin/bips/blob/master/bip-0342.mediawiki ================================================ FILE: bip-0350.mediawiki ================================================
  BIP: 350
  Layer: Applications
  Title: Bech32m format for v1+ witness addresses
  Authors: Pieter Wuille 
  Status: Deployed
  Type: Specification
  Assigned: 2020-12-16
  License: BSD-2-Clause
  Discussion: 2021-01-05: https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2021-January/018338.html [bitcoin-dev] Bech32m BIP: new checksum, and usage for segwit address
  Replaces: 173
==Introduction== ===Abstract=== This document defines an improved variant of Bech32 called '''Bech32m''', and amends BIP173 to use Bech32m for native segregated witness outputs of version 1 and later. Bech32 remains in use for segregated witness outputs of version 0. ===Copyright=== This BIP is licensed under the 2-clause BSD license. ===Motivation=== [[bip-0173.mediawiki|BIP173]] defined a generic checksummed base 32 encoded format called Bech32. It is in use for segregated witness outputs of version 0 (P2WPKH and P2WSH, see [[bip-0141.mediawiki|BIP141]]), and other applications. Bech32 has an unexpected [https://github.com/sipa/bech32/issues/51 weakness]: whenever the final character is a 'p', inserting or deleting any number of 'q' characters immediately preceding it does not invalidate the checksum. This does not affect existing uses of witness version 0 BIP173 addresses due to their restriction to two specific lengths, but may affect future uses and/or other applications using the Bech32 encoding. This document addresses that by specifying Bech32m, a variant of Bech32 that mitigates this insertion weakness and related issues. ==Specification== We first specify the new checksum algorithm, and then document how it should be used for future Bitcoin addresses. ===Bech32m=== Bech32m modifies the checksum of the Bech32 specification, replacing the constant ''1'' that is xored into the checksum at the end with ''0x2bc830a3''. The resulting checksum verification and creation algorithm (in Python, cf. the code in [https://github.com/bitcoin/bips/blob/master/bip-0173.mediawiki#Bech32|BIP173 Bech32 section]):
BECH32M_CONST = 0x2bc830a3

def bech32m_polymod(values):
  GEN = [0x3b6a57b2, 0x26508e6d, 0x1ea119fa, 0x3d4233dd, 0x2a1462b3]
  chk = 1
  for v in values:
    b = (chk >> 25)
    chk = (chk & 0x1ffffff) << 5 ^ v
    for i in range(5):
      chk ^= GEN[i] if ((b >> i) & 1) else 0
  return chk

def bech32m_hrp_expand(s):
  return [ord(x) >> 5 for x in s] + [0] + [ord(x) & 31 for x in s]

def bech32m_verify_checksum(hrp, data):
  return bech32m_polymod(bech32m_hrp_expand(hrp) + data) == BECH32M_CONST

def bech32m_create_checksum(hrp, data):
  values = bech32m_hrp_expand(hrp) + data
  polymod = bech32m_polymod(values + [0,0,0,0,0,0]) ^ BECH32M_CONST
  return [(polymod >> 5 * (5 - i)) & 31 for i in range(6)]
All other aspects of Bech32 remain unchanged, including its human-readable parts (HRPs). A combined function to decode both Bech32 and Bech32m simultaneously could be written using:
class Encoding(Enum):
    BECH32 = 1
    BECH32M = 2

def bech32_bech32m_verify_checksum(hrp, data):
    check = bech32_polymod(bech32_hrp_expand(hrp) + data)
    if check == 1:
        return Encoding.BECH32
    elif check == BECH32M_CONST:
        return Encoding.BECH32M
    else:
        return None
which returns either None for failure, or one of the BECH32 / BECH32M enumeration values to indicate successful decoding according to the respective standard. ===Addresses for segregated witness outputs=== Version 0 outputs (specifically, P2WPKH and P2WSH addresses) continue to use Bech32'''Why not permit both Bech32 and Bech32m for v0 addresses?''' Permitting both encodings reduces the error detection capabilities (it makes it equivalent to only have 29 bits of checksum). as specified in BIP173. Addresses for segregated witness outputs version 1 through 16 use Bech32m. Again, all other aspects of the encoding remain the same, including the 'bc' HRP. To generate an address for a segregated witness output: * If its witness version is 0, encode it using Bech32. * If its witness version is 1 or higher, encode it using Bech32m. To decode an address, client software should either decode with both a Bech32 and a Bech32m decoder'''Can a single string simultaneously be valid as Bech32 and Bech32m?''' No, a valid Bech32 and Bech32m string will always differ by at least 3 characters if they are the same length., or use a decoder that supports both simultaneously. In both cases, the address decoder has to verify that the encoding matches what is expected for the decoded witness version (Bech32 for version 0, Bech32m for others). The following code demonstrates the checks that need to be performed. Refer to the Python code linked in the reference implementation section below for full details of the called functions.
def decode(hrp, addr):
    hrpgot, data, spec = bech32_decode(addr)
    if hrpgot != hrp:
        return (None, None)
    decoded = convertbits(data[1:], 5, 8, False)
    # Witness programs are between 2 and 40 bytes in length.
    if decoded is None or len(decoded) < 2 or len(decoded) > 40:
        return (None, None)
    # Witness versions are in range 0..16.
    if data[0] > 16:
        return (None, None)
    # Witness v0 programs must be exactly length 20 or 32.
    if data[0] == 0 and len(decoded) != 20 and len(decoded) != 32:
        return (None, None)
    # Witness v0 uses Bech32; v1 through v16 use Bech32m.
    if data[0] == 0 and spec != Encoding.BECH32 or data[0] != 0 and spec != Encoding.BECH32M:
        return (None, None)
    # Success.
    return (data[0], decoded)
'''Error locating''' Bech32m, like Bech32, does support locating'''What about error correction?''' As explained in BIP173, introducing error correction reduces the ability to detect errors. While it is technically possible to correct a small number of errors due to Bech32(m)'s nature as a BCH code, implementations should refrain from using this for more than indicating where an error may be present. the positions of a few substitution errors. To combine this functionality with the segregated witness addresses proposed by this document, simply try locating errors for both Bech32 and Bech32m. If only one finds error locations, report that one. If both do (which should be very rare), there are a number of options: * Report the one that needs fewer corrections (if they differ). * Eliminate the response(s) that are inconsistent. Any symbol that isn't on an error location can be checked. For example, if the witness version symbol is not an error location, and it doesn't correspond to the specification used (0 for Bech32, 1+ for Bech32m), that response can be eliminated. See the fancy Javascript decoder below for example of the above. ==Compatibility== This document introduces a new encoding for v1 segregated witness outputs and higher versions. There should not be any compatibility issues on the receiver side; no wallets are creating v1 segregated witness addresses yet, as the output type is not usable on mainnet. On the other hand, the Bech32m proposal breaks forward-compatibility for sending to v1 and higher version segregated witness addresses. This incompatibility is [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2020-October/018236.html intentional]. An alternative design was [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2019-November/017460.html considered] where Bech32 remained in use for certain subsets of future addresses, but ultimately [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2020-December/018293.html discarded]. By introducing a clean break, we protect not only new software but also existing senders from the mutation issue, as new addresses will be incompatible with the existing Bech32 address validation. [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2020-November/018268.html Experiments] by Taproot proponents had shown that hardly any wallets and services supported sending to higher segregated witness output versions, so little is lost by [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2020-December/018298.html breaking] forward-compatibility. Furthermore, those experiments identified cases in which segregated witness implementations would have caused wallets to burn funds when sending to version 1 addresses. In case it is still in use, the chosen approach will prevent such software from destroying funds when attempting to send to a Bech32m address. ==Reference implementations== * Reference encoder and decoder: ** [https://github.com/sipa/bech32/blob/master/ref/python Reference Python implementation] ** [https://github.com/sipa/bech32/blob/master/ref/c Reference C implementation] ** [https://github.com/sipa/bech32/blob/master/ref/c++ Reference C++ implementation] ** [https://github.com/bitcoin/bitcoin/pull/20861 Bitcoin Core C++ implementation] ** [https://github.com/sipa/bech32/blob/master/ref/javascript Reference Javascript implementation] * Fancy decoder that localizes errors: ** [https://github.com/sipa/bech32/blob/master/ecc/javascript For JavaScript] ([http://bitcoin.sipa.be/bech32/demo/demo.html demo website]) ==Test vectors== '''Implementation advice''' Experiments testing BIP173 implementations found that many wallets and services did not support sending to higher version segregated witness outputs. In anticipation of the proposed [https://github.com/bitcoin/bips/blob/master/bip-0341.mediawiki Taproot] soft fork introducing v1 segregated witness outputs on the network, we emphatically recommend employing the complete set of test vectors provided below as well as ensuring that your implementation supports sending to v1 '''and higher versions'''. All higher versions of native segregated witness outputs should be recognized as valid recipients. As higher versions are not defined on the network, no wallet should ever create them and no recipient should ever provide them to a sender. Nor should a recipient ever want to falsely provide them as the recipient would simply see a payment intended to themselves burned instead. However, by defining higher versions as valid recipients now, future soft forks introducing higher versions of native segwit outputs will be forward-compatible to all wallets correctly implementing the Bech32m specification. ===Test vectors for Bech32m=== The following strings are valid Bech32m: * A1LQFN3A * a1lqfn3a * an83characterlonghumanreadablepartthatcontainsthetheexcludedcharactersbioandnumber11sg7hg6 * abcdef1l7aum6echk45nj3s0wdvt2fg8x9yrzpqzd3ryx * 11llllllllllllllllllllllllllllllllllllllllllllllllllllllllllllllllllllllllllllllllllludsr8 * split1checkupstagehandshakeupstreamerranterredcaperredlc445v * ?1v759aa No string can be simultaneously valid Bech32 and Bech32m, so the above examples also serve as invalid test vectors for Bech32. The following string are not valid Bech32m (with reason for invalidity): * 0x20 + 1xj0phk: HRP character out of range * 0x7F + 1g6xzxy: HRP character out of range * 0x80 + 1vctc34: HRP character out of range * an84characterslonghumanreadablepartthatcontainsthetheexcludedcharactersbioandnumber11d6pts4: overall max length exceeded * qyrz8wqd2c9m: No separator character * 1qyrz8wqd2c9m: Empty HRP * y1b0jsk6g: Invalid data character * lt1igcx5c0: Invalid data character * in1muywd: Too short checksum * mm1crxm3i: Invalid character in checksum * au1s5cgom: Invalid character in checksum * M1VUXWEZ: checksum calculated with uppercase form of HRP * 16plkw9: empty HRP * 1p2gdwpf: empty HRP ===Test vectors for v0-v16 native segregated witness addresses=== The following list gives valid segwit addresses and the scriptPubKey that they translate to in hex. * BC1QW508D6QEJXTDG4Y5R3ZARVARY0C5XW7KV8F3T4: 0014751e76e8199196d454941c45d1b3a323f1433bd6 * tb1qrp33g0q5c5txsp9arysrx4k6zdkfs4nce4xj0gdcccefvpysxf3q0sl5k7: 00201863143c14c5166804bd19203356da136c985678cd4d27a1b8c6329604903262 * bc1pw508d6qejxtdg4y5r3zarvary0c5xw7kw508d6qejxtdg4y5r3zarvary0c5xw7kt5nd6y: 5128751e76e8199196d454941c45d1b3a323f1433bd6751e76e8199196d454941c45d1b3a323f1433bd6 * BC1SW50QGDZ25J: 6002751e * bc1zw508d6qejxtdg4y5r3zarvaryvaxxpcs: 5210751e76e8199196d454941c45d1b3a323 * tb1qqqqqp399et2xygdj5xreqhjjvcmzhxw4aywxecjdzew6hylgvsesrxh6hy: 0020000000c4a5cad46221b2a187905e5266362b99d5e91c6ce24d165dab93e86433 * tb1pqqqqp399et2xygdj5xreqhjjvcmzhxw4aywxecjdzew6hylgvsesf3hn0c: 5120000000c4a5cad46221b2a187905e5266362b99d5e91c6ce24d165dab93e86433 * bc1p0xlxvlhemja6c4dqv22uapctqupfhlxm9h8z3k2e72q4k9hcz7vqzk5jj0: 512079be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798 The following list gives invalid segwit addresses and the reason for their invalidity. * tc1p0xlxvlhemja6c4dqv22uapctqupfhlxm9h8z3k2e72q4k9hcz7vq5zuyut: Invalid human-readable part * bc1p0xlxvlhemja6c4dqv22uapctqupfhlxm9h8z3k2e72q4k9hcz7vqh2y7hd: Invalid checksum (Bech32 instead of Bech32m) * tb1z0xlxvlhemja6c4dqv22uapctqupfhlxm9h8z3k2e72q4k9hcz7vqglt7rf: Invalid checksum (Bech32 instead of Bech32m) * BC1S0XLXVLHEMJA6C4DQV22UAPCTQUPFHLXM9H8Z3K2E72Q4K9HCZ7VQ54WELL: Invalid checksum (Bech32 instead of Bech32m) * bc1qw508d6qejxtdg4y5r3zarvary0c5xw7kemeawh: Invalid checksum (Bech32m instead of Bech32) * tb1q0xlxvlhemja6c4dqv22uapctqupfhlxm9h8z3k2e72q4k9hcz7vq24jc47: Invalid checksum (Bech32m instead of Bech32) * bc1p38j9r5y49hruaue7wxjce0updqjuyyx0kh56v8s25huc6995vvpql3jow4: Invalid character in checksum * BC130XLXVLHEMJA6C4DQV22UAPCTQUPFHLXM9H8Z3K2E72Q4K9HCZ7VQ7ZWS8R: Invalid witness version * bc1pw5dgrnzv: Invalid program length (1 byte) * bc1p0xlxvlhemja6c4dqv22uapctqupfhlxm9h8z3k2e72q4k9hcz7v8n0nx0muaewav253zgeav: Invalid program length (41 bytes) * BC1QR508D6QEJXTDG4Y5R3ZARVARYV98GJ9P: Invalid program length for witness version 0 (per BIP141) * tb1p0xlxvlhemja6c4dqv22uapctqupfhlxm9h8z3k2e72q4k9hcz7vq47Zagq: Mixed case * bc1p0xlxvlhemja6c4dqv22uapctqupfhlxm9h8z3k2e72q4k9hcz7v07qwwzcrf: zero padding of more than 4 bits * tb1p0xlxvlhemja6c4dqv22uapctqupfhlxm9h8z3k2e72q4k9hcz7vpggkg4j: Non-zero padding in 8-to-5 conversion * bc1gmk9yu: Empty data section ==Appendix: checksum design & properties== Checksums are used to detect errors introduced into data during transfer. A hash function-based checksum such as Base58Check detects any type of error uniformly, but not all classes of errors are equally likely to occur in practice. Bech32 prioritizes detection of substitution errors, but improving detection of one error class inevitably worsens detection of other error classes. During the design of Bech32, it was assumed that other simple error patterns beside substitutions would have a similar detection rate as in a hash function-based design, and detection would only be worse for complex, impractical errors. The discovered insertion weakness shows that this is not the case. For Bech32m, we aim to retain Bech32's guarantees for substitution errors, but make sure that other common errors don't perform worse than a hash function-based checksum would. To make sure the new standard is easy to implement, we restrict the design space to only amending the final constant that is xored in, as it was [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2019-December/017521.html observed] that is sufficient to mitigate the 'q' insertion issue while retaining the intended substitution error detection. In what follows, we explain how the new constant ''0x2bc830a3'' was chosen. ===Error patterns & detection probability=== We define an error pattern as a sequence of first one or more deletions, then swaps of adjacent characters, followed by substitutions, insertions, and duplications, in that order, all in specific positions, applied to a string with valid checksum that is otherwise randomly chosen. For insertions and substitutions we assume a uniformly random new character. For example, "delete the 17th character, swap the 11th character with the 12th character, and insert a random character in the 24th position" is an error pattern. "Replace the 43rd through 48th character with 'aardvark'" is not a valid error pattern, because the new characters are not random and there is no reason why this particular string is more likely than any other to be substituted. A hash function-based checksum design with a 30-bit hash would have a probability of incorrectly accepting equal to ''2-30'', for every error pattern. Bech32 has a probability of 0 to incorrectly accept error patterns consisting of up to 4 substitutions—they are always detected. The 'q'-insertion issue shows that for Bech32 a simple error pattern ("insert a random character in the penultimate position") with probability ''2-10'' exists: it requires the final character to be 'p' (leaving only 1 in 32 strings), and requires the inserted character to be 'q' (permitting only 1 of 32 possible inserted characters). Note that the choice of ''what'' the error pattern is (which types of errors, and where) isn't part of our probabilities: we try to make sure that ''every'' pattern behaves well, not just randomly chosen ones, because presumably humans make some kinds of errors more than others, and we cannot easily model which ones. ===Detection properties of Bech32m=== The table below shows the error detection properties of Bech32m, and a comparison with Bech32. The code used for this analysis can be found [https://gist.github.com/sipa/14c248c288c3880a3b191f978a34508e#file-const_analysis-cpp here]. Every row specifies one error pattern via the constraints in the left four columns. The remaining columns report what percentage of those patterns have certain probabilities of not being detected. The columns are: * '''errors''' The maximum number of individual errors considered * '''of type''' What type of errors are considered (either "subst. only" for just substitutions, or "any" to also include deletions, swaps, insertions, and duplications) * '''window''' The maximum size of the window in which the errors have to occur'''What is an error pattern’s window size?''' The window size of an error pattern is the length of the smallest consecutive range of characters that contains all modified characters (on input or output; whichever is larger). For example, an error pattern that turns "abcdef" into "accdbef" has a window size of 4, as it is replacing "bcd" with "ccdb", a 4 character string. Window size is only meaningful when the pattern consists of two or more errors. * '''code/verifier''' Whether this line is about Bech32 or Bech32m encoded strings, and whether those are evaluated regarding their probability of being accepted by either a Bech32 or a Bech32m verifier.'''Why do we care about probability of accepting Bech32m strings in Bech32 verifiers?''' For applications where Bech32m replaces an existing use of Bech32 (such as segregated witness addresses), we want to make sure that a Bech32m string created by new software won’t be erroneously accepted by old software that assumes Bech32 - even when a small number of errors were introduced as well.'''Should we also take into account failures that occur due to taking a valid Bech32m string, and after errors it becoming acceptable to a Bech32 verifier?''' This situation may in theory occur for segregated witness addresses when errors occur that change the version number in a v1+ address to v0. Due to the specificity of this type of error, plus the additional constraints that apply for v0 addresses, this is both unlikely and hard to analyze. * '''error patterns with failure probability''' For each probability (''0'', ''2-30'', ''2-25'', ''2-20'', ''2-15'', and ''2-10'') this reports what percentage of error patterns restricted by the constraints in the previous columns have those probabilities of being incorrectly accepted. The properties are divided into two classes: those that hold over all strings when averaged over all possible HRPs (human readable parts), and those specific to the "bc1" HRP with the length restrictions imposed by segregated witness addresses'''What restrictions were taken into account for the "bc1"-specific analysis?''' The minimum length (due to witness programs being at least 2 bytes), the maximum length (due to witness programs being at most 40 bytes), and the fact that the witness programs are a multiple of 8 bits. The fact that the first data symbol cannot be over 16, or that the padding has to be 0, is not taken into account.. {| class="wikitable" ! rowspan="2" | errors ! rowspan="2" | of type ! rowspan="2" | window ! rowspan="2" | code/verifier ! colspan="6" | error patterns with failure probability |- ! ''0'' !! ''2-30'' !! ''2-25'' !! ''2-20'' !! ''2-15'' !! ''2-10'' |- ! colspan="10" | Properties averaged over all HRPs |- | ≤ 4 || only subst. || any || rowspan="6" | Bech32m/Bech32m || 100.00%|| colspan="5" | none(a) |- | any || any || ≤ 4 || 56.16%|| 43.84%|| colspan="4" | none(b) |- | ≤ 2 || any || ≤ 68 || 7.71%|| 92.28%|| colspan="4" | none(b) |- | ≤ 2 || any || any || 7.79%|| 92.20%|| 0.004%|| colspan="3" | none(b) |- | ≤ 3 || any || ≤ 69 || 7.73%|| 92.23%|| 0.033%(d) || colspan="3" | none(b) |- | ≤ 3 || any || any || 7.77%|| 92.19%|| 0.034%|| 0.000065% || colspan="2" | none(b) |- | ≤ 4 || only subst. || any || rowspan="6" | Bech32/Bech32 || 100.00%|| colspan="5" | none |- | any || any || ≤ 4 || 54.00%|| 43.84%|| 1.08%|| 0.90%|| 0.17%|| 0.0091% |- | ≤ 2 || any || ≤ 68 || 4.59%|| 92.29%|| 1.09%|| 1.01%|| 0.99%|| 0.039% |- | ≤ 2 || any || any || 4.58%|| 92.21%|| 1.11%|| 1.04%|| 1.02%|| 0.038% |- | ≤ 3 || any || ≤ 69 || 6.69%|| 92.23%|| 0.56%|| 0.48%|| 0.041%|| 0.00055% |- | ≤ 3 || any || any || 6.66%|| 92.19%|| 0.59%|| 0.52%|| 0.041%|| 0.00053% |- | 0 || - || - || rowspan="3" | Bech32m/Bech32 || 100.00%|| colspan="5" | none(a) |- | 1 || any || - || 46.53%|| 53.46%|| colspan="4" | none(b) |- | ≤ 2 || any || any || 22.18%|| 77.77%|| 0.048%|| colspan="3" | none(b) |- ! colspan="10" | Properties for segregated witness addresses with HRP "bc" |- | ≤ 4 || only subst. || any || rowspan="6" | Bech32m/Bech32m || 100.00%|| colspan="5" | none(a) |- | 1 || any || - || 24.34%|| 75.66%|| colspan="4" | none(c) |- | ≤ 2 || any || ≤ 28 || 16.85%|| 83.15%|| colspan="4" | none(c) |- | any || any || ≤ 4 || 74.74%|| 25.25%|| 0.0016%|| colspan="3" | none(c) |- | ≤ 2 || any || any || 15.72%|| 84.23%|| 0.039%|| 0.0053%|| colspan="2" | none(c) |- | ≤ 3 || any || any || 13.98%|| 85.94%|| 0.078%|| 0.00063%|| colspan="2" | none(c) |- | ≤ 4 || only subst. || any || rowspan="6" | Bech32/Bech32 || 100.00%|| colspan="5" | none |- | 1 || any || - || 14.63%|| 75.71%|| 2.43%|| 2.43%|| 2.43%|| 2.38% |- | ≤ 2 || any || ≤ 28 || 14.22%|| 83.15%|| 0.94%|| 0.84%|| 0.79%|| 0.054% |- | any || any || ≤ 4 || 73.23%|| 25.26%|| 0.76%|| 0.63%|| 0.12%|| 0.0064% |- | ≤ 2 || any || any || 12.79%|| 84.24%|| 1.06%|| 0.95%|| 0.92%|| 0.041% |- | ≤ 3 || any || any || 13.00%|| 85.94%|| 0.57%|| 0.45%|| 0.044%|| 0.00067% |- | ≤ 3 || only subst. || any || rowspan="3" | Bech32m/Bech32 || 100.00%|| colspan="5" | none(c) |- | 1 || any || - || 70.89%|| 29.11%|| colspan="4" | none(c) |- | ≤ 2 || any || any || 36.12%|| 63.79%|| 0.092%|| 0.00049%|| colspan="2" | none(c) |} The numbers in this table, as well as a comparison with the numbers for the ‘’1’’ constant and earlier proposed improved constants, can be found [https://gist.github.com/sipa/14c248c288c3880a3b191f978a34508e#file-results_final-txt here]. ===Selection process=== The details of the selection process can be found [https://gist.github.com/sipa/14c248c288c3880a3b191f978a34508e here], but in short: * Start with the set of all ''230-1'' constants different from Bech32's ''1''. All of these satisfy the properties marked (a) in the table above. * Through exhaustive analysis, reject all constants that do not exhibit the properties'''How were the properties to select for chosen?''' All these properties are as strong as they can be without rejecting every constant: rejecting constants with lower probabilities, or more errors, or wider windows all result in nothing left. marked (b) in the table above (e.g. all constants that permit any error pattern of 2 errors or less in a window of 68 characters or less with a detection probability ''≥ 2-20''). This selection leaves us with 12054 candidates. * Reject all constants that do not exhibit the (c) properties in the table above'''Why optimize for segregated witness addresses (with HRP "bc1") specifically?''' Our analysis for generic HRP has limitations (see the detailed description [https://gist.github.com/sipa/14c248c288c3880a3b191f978a34508e#file-bech32m_mail-txt here], under "Technical details"). We optimize for generic usage first, but optimize for segregated witness addresses as a tiebreaker.. This leaves us with 79 candidates. * Finally, select the candidate that minimizes the number of error classes matching (d) in the table above as a final tiebreaker. The result is the single constant ''0x2bc830a3''. ==Footnotes== ==Acknowledgements== Thanks to Greg Maxwell for doing most of the computation for code selection and analysis, and comments. Thanks to Mark Erhardt for help with writing and editing this document. Thanks to Rusty Russell and others on the bitcoin-dev list for the discussion around intentionally breaking compatibility with existing senders, which is used in this specification. ================================================ FILE: bip-0351.mediawiki ================================================
  BIP: 351
  Layer: Applications
  Title: Private Payments
  Authors: Alfred Hodler 
           Clark Moody 
  Status: Draft
  Type: Informational
  Assigned: 2022-07-10
  License: MIT
==Abstract== This BIP makes it possible for two parties to transact using addresses that only they can calculate. This is done using exclusively on-chain methods and in a manner that minimizes blockchain footprint. Receiving parties can share their payment codes publicly without a loss of privacy, as every sender will calculate a unique set of addresses for each payment code. ==Motivation== A recipient that wishes to receive funds privately has several options. Each has tradeoffs in terms of chain analysis potential, recoverability, and wallet complexity. '''Sharing a static address''' works well enough for one-time payments between two parties as long as the address is shared through a private channel. It does not work well for recurring payments because address reuse leads to a loss of privacy. Using this method for donations exacerbates the problem since the address will serve as a focal point for data collection and analysis. Wallets must not reissue the same address to multiple recipients. '''Sharing a BIP32 extended public key''' works for recurring payments between two parties only. The same key cannot be shared to any other party without leaking the chain of payments. Furthermore, an extended public key does not say anything about address types and makes it possible for a sender to send to a script that a recipient cannot spend from. Alternate [https://github.com/satoshilabs/slips/blob/master/slip-0132.md version bytes] have been proposed to specify address types, but wallet adoption is limited. '''Sharing a BIP380 descriptor containing an extended public key''' solves the address type issue from sharing a raw BIP32 extended key. The drawback is that descriptor support is not widespread, especially in mobile wallets. '''Using a payment server''' works in the case of recipients that have the resources to set up and maintain a payment server that will generate a fresh address for each payment. These are usually businesses and the method is usually out of reach for the average user. The centralized server is vulnerable to takedown remotely and physically. '''Sharing a BIP47 payment code''' addresses most of the above shortcomings. However, it introduces the following problems: * The BIP uses a notification mechanism that relies on publicly known per-recipient notification addresses. If Alice wants to send funds to Bob, she has to use the same notification address that everyone else uses to notify Bob. If Alice is not careful with coin selection, i.e. ensuring that her notification UTXO is not linked to her, she will publicly expose herself as someone who is trying to send funds to Bob and their relationship becomes permanently visible on the blockchain. * The BIP does not say anything about address types. Receiving wallets therefore have to watch all address types that can be created from a single public key. Even then, a sender could send to a script that a recipient cannot spend from. ==Method== When Alice wants to start paying Bob in private, she imports his payment code into a compatible wallet. Her wallet extracts Bob's public key from the payment code and sends a notification transaction. If Bob finds a notification transaction addressed to himself, he imports Alice's public key contained therein and stores it. Bob then performs ECDH using Alice's public key and his own private key in order to calculate a common set of addresses to watch. Alice calculates the same set of addresses on her end and uses them to send coins to Bob. If Alice engages in coin control, both the initial notification transaction and subsequent payment transactions cannot be attributed to either party. Even if Alice uses coins that are already associated with her, chain analysis will identify her as a sender but Bob's privacy will remain entirely preserved. ==Specification== ===Definitions=== * Alice: sender * Bob: recipient * Payment code: static string that Bob generates and shares with others so that he can receive payments * ''P'': public key contained in Bob's payment code * ''p'': private key associated with Bob's public key ''P'' * ''N'': extended public key used by Alice to derive child keys for each Bob she wants to transact with * ''n'': private key associated with Alice's public key ''N'' * ''x'': Alice's secret recipient index, unique for each Bob * ''Nx'': child public key derived from ''N'' at index ''x'' (non-hardened) * ''nx'': private key associated with ''Nx'' * ''c'': Alice's transaction count toward Bob * ''Pc'': Bob's public key at index ''c'' * ''pc'': Bob's private key at index ''c'' * ''Ac'': Bob's receive address at index ''c'' * ''H'': SHA256 hash function * ''*'': EC multiplication * ''+'': EC addition * ''|'': string concatenation * ''[a..b]'': string slicing (inclusive of ''a'', exclusive of ''b'') ===Public Key Derivation Path=== The derivation path for this BIP follows BIP44. The following BIP32 path levels are defined: m / purpose' / coin_type' / account' purpose is set to 351. ''(p, P)'' and ''(n, N)'' are keys associated with the above path, depending on which side is performing the calculation. ''Nx'' keys are the direct non-hardened children of ''N''. For instance, the path of ''N0'' from ''N'' is ''m / 0''. ===Payment Code Structure and Encoding=== * bytes [0..2]: address type flags (2 bytes) * bytes [2..35]: compressed public key P (33 bytes) Payment codes are encoded in bech32m and the human readable part is "pay" for mainnet and "payt" for testnet (all types), resulting in payment codes that look like "pay1cqqq8d29g0a7m8ghmycqk5yv24mfh3xg8ptzqcn8xz6d2tjl8ccdnfkpjl7p84". ===Address Types=== Address type flags determine which address types a payment code accepts. This is represented by big-endian ordered 16 bits. For instance, a hypothetical payment code that handles all address types will have all defined bits set to 1 (0xffff). Currently defined flags: {| class="wikitable" ! Address Type !! Flag !! Flag Value !! Ordinal Value |- | P2PKH || 1 << 0 || 0x0001 || 0 |- | P2WPKH || 1 << 1 || 0x0002 || 1 |- | P2TR || 1 << 2 || 0x0004 || 2 |} The remaining flags are reserved for future address types. While payment codes use 2-byte bitflag arrays, notifications use ordinal values in the form of a single byte. All keys are compressed. Using uncompressed keys at any point is illegal. ===Notifications=== Notifications are performed by publishing transactions that contain a 40-byte OP_RETURN output. The value of the OP_RETURN is constructed using the following formula: ''search_key | notification_code | Nx | address_type'' * ''search_key'' equals "PP" and is a static ASCII-encoded string (2 bytes) * ''notification_code'' is ''H(nx * P)[0..4]'' (4 bytes) * ''Nx'' is the unique public key a sender is using for a particular recipient (33 bytes) * ''address_type'' is the '''ordinal''' value of a single address type that a sender wants to send to (1 byte). This must be selected from the recipient's accepted address types. When Alice wants to notify Bob that he will receive future payments from her, she performs the following procedure: # Assigns an unused, unique index ''x'' to Bob (''0'' if Bob is the first party she is notifying). # Calculates a 4-byte notification code: ''notification_code = H(nx * P)[0..4]'' # Commits to one of Bob's accepted address types by choosing its ordinal value. Going forward Alice must not send to address types other than the one she committed to in the notification. # Constructs a notification payload by concatenating the above values according to the formula. # Selects any UTXO in her wallet, preferably not associated with her. # Sends a transaction including an OP_RETURN output whose value is set to the constructed payload. When Bob notices a 40-byte OP_RETURN starting with ''search key'', he performs the following procedure: # Breaks down the payload into its four constituent parts. # Discards the ''search_key'' (item #0). # Selects ''Nx'' (item #2) and performs ''H(Nx * p)'' (Bob does not know the value of ''x''). Bob takes the first four bytes of the calculated value. # If the four bytes match the notification value (item #1), Bob found a notification addressed to himself and stores ''Nx'' together with ''address_type''. # If this process fails for any reason, Bob assumes a spurious notification or one not addressed to himself and gives up. Since changing ''x'' yields a completely different sender identity, Alice can always re-notify Bob from a different index when she does not want to be associated with her previous identity. Alice can also re-notify Bob when she wants to start sending to a different address type. Bob must be able to update his watchlist in that case and he can stop watching addresses associated with the old address type. Out-of-band notifications between Alice and Bob are legal (in fact, they may not be prevented), but in that case Bob loses the ability to restore his wallet from OP_RETURN outputs embedded in the blockchain. In that case, Bob has the burden of keeping a valid backup of any out-of-band notifications. ===Allowing Notification Collisions=== Since ''notification_code'' is a 4-byte truncation of the full value, Bob has a 1 in ~4.3 billion chance of detecting a spurious notification. This is considered acceptable because the cost of doing so is adding a few more addresses to Bob's watchlist. The benefit of this approach is that is saves 28 bytes per notification. ===Scanning Requirement=== There is a scanning requirement on the recipient side in that the recipient must have access to full blocks in order to be able to search them for OP_RETURN outputs containing notifications. For more information on how light clients can get around this limitation and still use the standard, see Appendix B. Recipients that do not want to decode raw block data can quickly search for notifications in a block by looking for the following byte array: [106, 40, 80, 80]. The first two bytes represent ''OP_RETURN'' and ''OP_PUSHBYTES_40'', followed by the ASCII value of ''search_key''. ===Transacting=== Alice initializes counter ''c'' which is unique to Bob and increments with each transaction. ''c'' is a 64-bit integer and must be inputted into a hasher as a big-endian encoded array of 8 bytes. 1. Alice calculates a secret point (constant between Alice and Bob): ''S = nx * P'' 2. Alice calculates a shared secret: ''s = H(S | c)'' 3. Alice calculates Bob's ephemeral public key and its associated address where the funds will be sent: ''Pc = P + s*G'' 4. Alice constructs an address using the key ''Pc'', using one of the address types she committed to in the notification transaction. Bob constructs his watchlist by mirroring this process on his end, except that his method of calculating ''S'' is: ''S = Nx * p'' When Bob wants to spend from such addresses, he calculates his private keys in the following manner: ''pc = p + s'' ==Backward Compatibility== Private Payments is a new standard which is not compatible with any previous standard based on static payment codes, such as BIP47. While the standard does not support versioning, it reserves unused bits in the address type bitflag array which can be allocated to new address types once they are deemed ubiquitous. Older payment codes (i.e. those generated when fewer address types were available) are readable by software supporting new address types. The reverse is also supported since older software will ignore newer address type flags that are not understood. ==Appendix A: Test Vectors== ===Alice's Wallet=== '''BIP32 seed:''' 0xfe '''Master xprv:''' xprv9s21ZrQH143K2qVytoy3eZSSuc1gfzFrkV4bgoHzYTkgge4UoNP62eV8jkHYNqddaaefpnjwkz71P5m4EW6RuQBJeP9pdfa9WBnjP6XUivG '''n:''' xprv9zNFGn56Wm1s89ycTCg4hB615ehu6ZvNL4mxUEAL28pNhBAb6SZgLdsgmQd1ECgAiCjy6XxTTRyBdPAhH1oMfLhv2bSwfiCYhL9s9ahEehf '''N:''' xpub6DMbgHbzM8aALe45ZED54K2jdgYPW2eDhHhZGcZwaUMMZyVjdysvtSCAcfPYiqB5Zw41EyLWPxCXko6iEckwRdF5CD2ZKdTxUKigPXsnpaE '''x:''' 0 '''nx:''' be9518016ec15762877de7d2ce7367a2087cf5682e72bbffa89535d73bb42f40 '''Nx:''' 02e3217349724307eed5514b53b1f53f0802672a9913d9bbb76afecc86be23f464 ===Bob's Wallet=== '''BIP32 seed:''' 0xff '''Master xprv:''' xprv9s21ZrQH143K47bRNtc26e8Gb3wkUiJ4fH3ewYgJeiGABp7vQtTKsLBzHM2fsfiK7Er6uMrWbdDwwrdcVn5TDC1T1npTFFkdEVoMgTwfVuR '''p:''' 0x26c610e7d0ed4395be3f0664073d66b0a3442b49e1ec13faf2dd9b7d3c335441 '''P:''' 0x0302be8bff520f35fae3439f245c52afb9085a7bf62d099c1f5e9e1b15a7e2121a '''Accepted scripts:''' 0x03 (legacy + segwit) (0x01 | 0x02) '''Payment code:''' pay1qqpsxq4730l4yre4lt3588eyt3f2lwggtfalvtgfns04a8smzkn7yys6xv2gs8 ===Alice notifying Bob=== '''S:''' 0x02c0892d6ba30b5b1eafebd47172e46d358721f294698f9f59b4d96b781da09a62 '''Notification code:''' 0x49cb55bb '''Address type commitment:''' 1 (segwit) '''Notification output script:''' OP_RETURN OP_PUSHBYTES_40 505049cb55bb02e3217349724307eed5514b53b1f53f0802672a9913d9bbb76afecc86be23f46401 ===Alice sending to Bob=== '''c:''' 0 '''s:''' 0x5dbe5efee4a5b9df73708241858f2bf7ec65f141dbd229ea8e2f9f51804a18f2 '''s*G:''' 0x039362033c1bc3f05e081d4d7f76d5ffebde349b0f6a4d2e8ffc5c065c17233247 '''Pc:''' 0x03e669bd1705691a080840b07d76713d040934a37f2e8dde2fe02f5d3286a49219 '''Ac:''' bc1qw7ld5h9tj2ruwxqvetznjfq9g5jyp0gjhrs30w ===Bob spending=== '''c:''' 0 '''pc:''' 0x84846fe6b592fd7531af88a58ccc92a88faa1c8bbdbe3de5810d3acebc7d6d33 ==Appendix B: Potential OP_RETURN Services== Compact Block Filters, as formulated in BIP-0158, do not cover OP_RETURN data payloads. In support of light wallets, an external service could publish transaction proofs for all transactions that include the tagged notification payload. Light wallets would download all such transactions, filter for matches against their payment code, then verify the transaction proofs against the block headers obtained over the P2P network. ==Appendix C: Potential Notification Transaction Services== No specific instruction is given as to the details of the notification transaction beyond simply including the single OP_RETURN payload. Since no restriction exists for other inputs or outputs of this transaction, there is an opportunity for an external service to include this payload in a transaction completely unrelated to Alice's wallet. Such a service could charge a fee out-of-band to help cover fees. Another opportunity exists for an existing business to attach notification payloads to transactions sent during the normal course of operations. Large withdrawal transactions from mining pools or exchanges could include a marginal notification payload without affecting overall fees. ==Reference Implementation== Reference implementation is available at https://github.com/private-payments/rust-private-payments ==Reference== * [[bip-0032.mediawiki|BIP32 - Hierarchical Deterministic Wallets]] * [[bip-0043.mediawiki|BIP43 - Purpose Field for Deterministic Wallets]] * [[bip-0044.mediawiki|BIP44 - Multi-Account Hierarchy for Deterministic Wallets]] * [[bip-0047.mediawiki|BIP47 - Reusable Payment Codes for Hierarchical Deterministic Wallets]] * [[bip-0157.mediawiki|BIP157 - Client Side Block Filtering]] * [[bip-0158.mediawiki|BIP158 - Compact Block Filters for Light Clients]] * [https://gist.github.com/RubenSomsen/21c477c90c942acf45f8e8f5c1ad4fae BIP47 Prague Discussion (acknowledgements: @rubensomsen, @afilini, @kixunil]) ================================================ FILE: bip-0352/bech32m.py ================================================ # Copyright (c) 2017, 2020 Pieter Wuille # # Permission is hereby granted, free of charge, to any person obtaining a copy # of this software and associated documentation files (the "Software"), to deal # in the Software without restriction, including without limitation the rights # to use, copy, modify, merge, publish, distribute, sublicense, and/or sell # copies of the Software, and to permit persons to whom the Software is # furnished to do so, subject to the following conditions: # # The above copyright notice and this permission notice shall be included in # all copies or substantial portions of the Software. # # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, # FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE # AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN # THE SOFTWARE. """Reference implementation for Bech32/Bech32m and segwit addresses.""" from enum import Enum class Encoding(Enum): """Enumeration type to list the various supported encodings.""" BECH32 = 1 BECH32M = 2 CHARSET = "qpzry9x8gf2tvdw0s3jn54khce6mua7l" BECH32M_CONST = 0x2bc830a3 def bech32_polymod(values): """Internal function that computes the Bech32 checksum.""" generator = [0x3b6a57b2, 0x26508e6d, 0x1ea119fa, 0x3d4233dd, 0x2a1462b3] chk = 1 for value in values: top = chk >> 25 chk = (chk & 0x1ffffff) << 5 ^ value for i in range(5): chk ^= generator[i] if ((top >> i) & 1) else 0 return chk def bech32_hrp_expand(hrp): """Expand the HRP into values for checksum computation.""" return [ord(x) >> 5 for x in hrp] + [0] + [ord(x) & 31 for x in hrp] def bech32_verify_checksum(hrp, data): """Verify a checksum given HRP and converted data characters.""" const = bech32_polymod(bech32_hrp_expand(hrp) + data) if const == 1: return Encoding.BECH32 if const == BECH32M_CONST: return Encoding.BECH32M return None def bech32_create_checksum(hrp, data, spec): """Compute the checksum values given HRP and data.""" values = bech32_hrp_expand(hrp) + data const = BECH32M_CONST if spec == Encoding.BECH32M else 1 polymod = bech32_polymod(values + [0, 0, 0, 0, 0, 0]) ^ const return [(polymod >> 5 * (5 - i)) & 31 for i in range(6)] def bech32_encode(hrp, data, spec): """Compute a Bech32 string given HRP and data values.""" combined = data + bech32_create_checksum(hrp, data, spec) return hrp + '1' + ''.join([CHARSET[d] for d in combined]) def bech32_decode(bech): """Validate a Bech32/Bech32m string, and determine HRP and data.""" if ((any(ord(x) < 33 or ord(x) > 126 for x in bech)) or (bech.lower() != bech and bech.upper() != bech)): return (None, None, None) bech = bech.lower() pos = bech.rfind('1') # remove the requirement that bech32m be less than 90 chars if pos < 1 or pos + 7 > len(bech): return (None, None, None) if not all(x in CHARSET for x in bech[pos+1:]): return (None, None, None) hrp = bech[:pos] data = [CHARSET.find(x) for x in bech[pos+1:]] spec = bech32_verify_checksum(hrp, data) if spec is None: return (None, None, None) return (hrp, data[:-6], spec) def convertbits(data, frombits, tobits, pad=True): """General power-of-2 base conversion.""" acc = 0 bits = 0 ret = [] maxv = (1 << tobits) - 1 max_acc = (1 << (frombits + tobits - 1)) - 1 for value in data: if value < 0 or (value >> frombits): return None acc = ((acc << frombits) | value) & max_acc bits += frombits while bits >= tobits: bits -= tobits ret.append((acc >> bits) & maxv) if pad: if bits: ret.append((acc << (tobits - bits)) & maxv) elif bits >= frombits or ((acc << (tobits - bits)) & maxv): return None return ret def decode(hrp, addr): """Decode a segwit address.""" hrpgot, data, spec = bech32_decode(addr) if hrpgot != hrp: return (None, None) decoded = convertbits(data[1:], 5, 8, False) if decoded is None or len(decoded) < 2: return (None, None) if data[0] > 16: return (None, None) return (data[0], decoded) def encode(hrp, witver, witprog): """Encode a segwit address.""" spec = Encoding.BECH32 if witver == 0 else Encoding.BECH32M ret = bech32_encode(hrp, [witver] + convertbits(witprog, 8, 5), spec) if decode(hrp, ret) == (None, None): return None return ret ================================================ FILE: bip-0352/bitcoin_utils.py ================================================ import hashlib import struct from io import BytesIO from ripemd160 import ripemd160 from secp256k1lab.secp256k1 import Scalar from typing import Union def from_hex(hex_string): """Deserialize from a hex string representation (e.g. from RPC)""" return BytesIO(bytes.fromhex(hex_string)) def ser_uint32(u: int) -> bytes: return u.to_bytes(4, "big") def ser_uint256(u): return u.to_bytes(32, 'little') def deser_uint256(f): return int.from_bytes(f.read(32), 'little') def deser_txid(txid: str): # recall that txids are serialized little-endian, but displayed big-endian # this means when converting from a human readable hex txid, we need to first # reverse it before deserializing it dixt = "".join(map(str.__add__, txid[-2::-2], txid[-1::-2])) return bytes.fromhex(dixt) def deser_compact_size(f: BytesIO): view = f.getbuffer() nbytes = view.nbytes view.release() if (nbytes == 0): return 0 # end of stream nit = struct.unpack(" bytes: return ripemd160(hashlib.sha256(s).digest()) def is_p2tr(spk: bytes) -> bool: if len(spk) != 34: return False # OP_1 OP_PUSHBYTES_32 <32 bytes> return (spk[0] == 0x51) & (spk[1] == 0x20) def is_p2wpkh(spk: bytes) -> bool: if len(spk) != 22: return False # OP_0 OP_PUSHBYTES_20 <20 bytes> return (spk[0] == 0x00) & (spk[1] == 0x14) def is_p2sh(spk: bytes) -> bool: if len(spk) != 23: return False # OP_HASH160 OP_PUSHBYTES_20 <20 bytes> OP_EQUAL return (spk[0] == 0xA9) & (spk[1] == 0x14) & (spk[-1] == 0x87) def is_p2pkh(spk: bytes) -> bool: if len(spk) != 25: return False # OP_DUP OP_HASH160 OP_PUSHBYTES_20 <20 bytes> OP_EQUALVERIFY OP_CHECKSIG return (spk[0] == 0x76) & (spk[1] == 0xA9) & (spk[2] == 0x14) & (spk[-2] == 0x88) & (spk[-1] == 0xAC) ================================================ FILE: bip-0352/reference.py ================================================ #!/usr/bin/env python3 # For running the test vectors, run this script: # ./reference.py send_and_receive_test_vectors.json import json from pathlib import Path import sys from typing import List, Tuple, Dict, cast # import the vendored copy of secp256k1lab sys.path.insert(0, str(Path(__file__).parent / "secp256k1lab/src")) from secp256k1lab.bip340 import schnorr_sign, schnorr_verify from secp256k1lab.secp256k1 import G, GE, Scalar from secp256k1lab.util import tagged_hash, hash_sha256 from bech32m import convertbits, bech32_encode, decode, Encoding from bitcoin_utils import ( deser_txid, from_hex, hash160, is_p2pkh, is_p2sh, is_p2wpkh, is_p2tr, ser_uint32, COutPoint, CTxInWitness, VinInfo, ) K_max = 2323 # per-group recipient limit NUMS_H = 0x50929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac0 def get_pubkey_from_input(vin: VinInfo) -> GE: if is_p2pkh(vin.prevout): # skip the first 3 op_codes and grab the 20 byte hash # from the scriptPubKey spk_hash = vin.prevout[3:3 + 20] for i in range(len(vin.scriptSig), 0, -1): if i - 33 >= 0: # starting from the back, we move over the scriptSig with a 33 byte # window (to match a compressed pubkey). we hash this and check if it matches # the 20 byte hash from the scriptPubKey. for standard scriptSigs, this will match # right away because the pubkey is the last item in the scriptSig. # if its a non-standard (malleated) scriptSig, we will still find the pubkey if its # a compressed pubkey. # # note: this is an incredibly inefficient implementation, for demonstration purposes only. pubkey_bytes = vin.scriptSig[i - 33:i] pubkey_hash = hash160(pubkey_bytes) if pubkey_hash == spk_hash: try: return GE.from_bytes_compressed(pubkey_bytes) except ValueError: pass if is_p2sh(vin.prevout): redeem_script = vin.scriptSig[1:] if is_p2wpkh(redeem_script): try: return GE.from_bytes_compressed(vin.txinwitness.scriptWitness.stack[-1]) except (ValueError, AssertionError): pass if is_p2wpkh(vin.prevout): try: return GE.from_bytes_compressed(vin.txinwitness.scriptWitness.stack[-1]) except (ValueError, AssertionError): pass if is_p2tr(vin.prevout): witnessStack = vin.txinwitness.scriptWitness.stack if (len(witnessStack) >= 1): if (len(witnessStack) > 1 and witnessStack[-1][0] == 0x50): # Last item is annex witnessStack.pop() if (len(witnessStack) > 1): # Script-path spend control_block = witnessStack[-1] # control block is <32 byte internal key> and 0 or more <32 byte hash> internal_key = control_block[1:33] if (internal_key == NUMS_H.to_bytes(32, 'big')): # Skip if NUMS_H return GE() try: return GE.from_bytes_xonly(vin.prevout[2:]) except ValueError: pass return GE() def get_input_hash(outpoints: List[COutPoint], sum_input_pubkeys: GE) -> bytes: lowest_outpoint = sorted(outpoints, key=lambda outpoint: outpoint.serialize())[0] return tagged_hash("BIP0352/Inputs", lowest_outpoint.serialize() + sum_input_pubkeys.to_bytes_compressed()) def encode_silent_payment_address(B_scan: GE, B_m: GE, hrp: str = "tsp", version: int = 0) -> str: data = convertbits(B_scan.to_bytes_compressed() + B_m.to_bytes_compressed(), 8, 5) return bech32_encode(hrp, [version] + cast(List[int], data), Encoding.BECH32M) def generate_label(b_scan: Scalar, m: int) -> Scalar: return Scalar.from_bytes_checked(tagged_hash("BIP0352/Label", b_scan.to_bytes() + ser_uint32(m))) def create_labeled_silent_payment_address(b_scan: Scalar, B_spend: GE, m: int, hrp: str = "tsp", version: int = 0) -> str: B_scan = b_scan * G B_m = B_spend + generate_label(b_scan, m) * G labeled_address = encode_silent_payment_address(B_scan, B_m, hrp, version) return labeled_address def decode_silent_payment_address(address: str, hrp: str = "tsp") -> Tuple[GE, GE]: _, data = decode(hrp, address) if data is None: return GE(), GE() B_scan = GE.from_bytes_compressed(data[:33]) B_spend = GE.from_bytes_compressed(data[33:]) return B_scan, B_spend def create_outputs(input_priv_keys: List[Tuple[Scalar, bool]], outpoints: List[COutPoint], recipients: List[str], expected: Dict[str, any] = None, hrp="tsp") -> List[str]: negated_keys = [] for key, is_xonly in input_priv_keys: k = Scalar.from_bytes_checked(key.to_bytes()) if is_xonly and not (k * G).has_even_y(): k = -k negated_keys.append(k) a_sum = Scalar.sum(*negated_keys) if a_sum == 0: # Input privkeys sum is zero -> fail return [] assert Scalar.from_bytes_checked(bytes.fromhex(expected.get("input_private_key_sum"))) == a_sum, "a_sum did not match expected input_private_key_sum" input_hash_scalar = Scalar.from_bytes_checked(get_input_hash(outpoints, a_sum * G)) silent_payment_groups: Dict[GE, List[GE]] = {} for recipient in recipients: B_scan, B_m = decode_silent_payment_address(recipient["address"], hrp=hrp) # Verify decoded intermediate keys for recipient expected_B_scan = GE.from_bytes_compressed(bytes.fromhex(recipient["scan_pub_key"])) expected_B_m = GE.from_bytes_compressed(bytes.fromhex(recipient["spend_pub_key"])) assert expected_B_scan == B_scan, "B_scan did not match expected recipient.scan_pub_key" assert expected_B_m == B_m, "B_m did not match expected recipient.spend_pub_key" if B_scan in silent_payment_groups: silent_payment_groups[B_scan].append(B_m) else: silent_payment_groups[B_scan] = [B_m] # Fail if per-group recipient limit (K_max) is exceeded if any([len(group) > K_max for group in silent_payment_groups.values()]): return [] outputs = [] for B_scan, B_m_values in silent_payment_groups.items(): ecdh_shared_secret = input_hash_scalar * a_sum * B_scan expected_shared_secrets = expected.get("shared_secrets", {}) # Find the recipient address that corresponds to this B_scan and get its index for recipient_idx, recipient in enumerate(recipients): recipient_B_scan = GE.from_bytes_compressed(bytes.fromhex(recipient["scan_pub_key"])) if recipient_B_scan == B_scan: expected_shared_secret_hex = expected_shared_secrets[recipient_idx] assert ecdh_shared_secret.to_bytes_compressed().hex() == expected_shared_secret_hex, f"ecdh_shared_secret did not match expected, recipient {recipient_idx} ({recipient['address']}): expected={expected_shared_secret_hex}" break k = 0 for B_m in B_m_values: t_k = Scalar.from_bytes_checked(tagged_hash("BIP0352/SharedSecret", ecdh_shared_secret.to_bytes_compressed() + ser_uint32(k))) P_km = B_m + t_k * G outputs.append(P_km.to_bytes_xonly().hex()) k += 1 return list(set(outputs)) def scanning(b_scan: Scalar, B_spend: GE, A_sum: GE, input_hash: bytes, outputs_to_check: List[bytes], labels: Dict[str, str] = None, expected: Dict[str, any] = None) -> List[Dict[str, str]]: input_hash_scalar = Scalar.from_bytes_checked(input_hash) computed_tweak_point = input_hash_scalar * A_sum assert computed_tweak_point.to_bytes_compressed().hex() == expected.get("tweak"), "tweak did not match expected" ecdh_shared_secret = input_hash_scalar * b_scan * A_sum assert ecdh_shared_secret.to_bytes_compressed().hex() == expected.get("shared_secret"), "ecdh_shared_secret did not match expected shared_secret" k = 0 wallet = [] while True: if k == K_max: # Don't look further than the per-group recipient limit (K_max) break t_k = Scalar.from_bytes_checked(tagged_hash("BIP0352/SharedSecret", ecdh_shared_secret.to_bytes_compressed() + ser_uint32(k))) P_k = B_spend + t_k * G for output in outputs_to_check: output_ge = GE.from_bytes_xonly(output) if P_k.to_bytes_xonly() == output: wallet.append({"pub_key": P_k.to_bytes_xonly().hex(), "priv_key_tweak": t_k.to_bytes().hex()}) outputs_to_check.remove(output) k += 1 break elif labels: m_G_sub = output_ge - P_k if m_G_sub.to_bytes_compressed().hex() in labels: P_km = P_k + m_G_sub wallet.append({ "pub_key": P_km.to_bytes_xonly().hex(), "priv_key_tweak": (t_k + Scalar.from_bytes_checked( bytes.fromhex(labels[m_G_sub.to_bytes_compressed().hex()]) )).to_bytes().hex(), }) outputs_to_check.remove(output) k += 1 break else: m_G_sub = -output_ge - P_k if m_G_sub.to_bytes_compressed().hex() in labels: P_km = P_k + m_G_sub wallet.append({ "pub_key": P_km.to_bytes_xonly().hex(), "priv_key_tweak": (t_k + Scalar.from_bytes_checked( bytes.fromhex(labels[m_G_sub.to_bytes_compressed().hex()]) )).to_bytes().hex(), }) outputs_to_check.remove(output) k += 1 break else: break return wallet if __name__ == "__main__": if len(sys.argv) != 2 or sys.argv[1] in ('-h', '--help'): print("Usage: ./reference.py send_and_receive_test_vectors.json") sys.exit(0) with open(sys.argv[1], "r") as f: test_data = json.loads(f.read()) for case in test_data: print(case["comment"]) # Test sending for sending_test in case["sending"]: given = sending_test["given"] expected = sending_test["expected"] vins = [ VinInfo( outpoint=COutPoint(hash=deser_txid(input["txid"]), n=input["vout"]), scriptSig=bytes.fromhex(input["scriptSig"]), txinwitness=CTxInWitness().deserialize(from_hex(input["txinwitness"])), prevout=bytes.fromhex(input["prevout"]["scriptPubKey"]["hex"]), private_key=Scalar.from_bytes_checked(bytes.fromhex(input["private_key"])), ) for input in given["vin"] ] # Convert the tuples to lists so they can be easily compared to the json list of lists from the given test vectors input_priv_keys = [] input_pub_keys = [] for vin in vins: pubkey = get_pubkey_from_input(vin) if pubkey.infinity: continue input_priv_keys.append(( vin.private_key, is_p2tr(vin.prevout), )) input_pub_keys.append(pubkey) assert [pk.to_bytes_compressed().hex() for pk in input_pub_keys] == expected.get("input_pub_keys"), "input_pub_keys did not match expected" sending_outputs = [] if (len(input_pub_keys) > 0): outpoints = [vin.outpoint for vin in vins] recipients = [] # expand given recipient entries to full list for recipient_entry in given["recipients"]: count = recipient_entry.get("count", 1) recipients.extend([recipient_entry] * count) sending_outputs = create_outputs(input_priv_keys, outpoints, recipients, expected=expected, hrp="sp") # Note: order doesn't matter for creating/finding the outputs. However, different orderings of the recipient addresses # will produce different generated outputs if sending to multiple silent payment addresses belonging to the # same sender but with different labels. Because of this, expected["outputs"] contains all possible valid output sets, # based on all possible permutations of recipient address orderings. Must match exactly one of the possible output sets. assert(any(set(sending_outputs) == set(lst) for lst in expected["outputs"])), "Sending test failed" else: assert(sending_outputs == expected["outputs"][0] == []), "Sending test failed" # Test receiving msg = hash_sha256(b"message") aux = hash_sha256(b"random auxiliary data") for receiving_test in case["receiving"]: given = receiving_test["given"] expected = receiving_test["expected"] outputs_to_check = [ bytes.fromhex(p) for p in given["outputs"] ] vins = [ VinInfo( outpoint=COutPoint(hash=deser_txid(input["txid"]), n=input["vout"]), scriptSig=bytes.fromhex(input["scriptSig"]), txinwitness=CTxInWitness().deserialize(from_hex(input["txinwitness"])), prevout=bytes.fromhex(input["prevout"]["scriptPubKey"]["hex"]), ) for input in given["vin"] ] # Check that the given inputs for the receiving test match what was generated during the sending test receiving_addresses = [] b_scan = Scalar.from_bytes_checked(bytes.fromhex(given["key_material"]["scan_priv_key"])) b_spend = Scalar.from_bytes_checked(bytes.fromhex(given["key_material"]["spend_priv_key"])) B_scan = b_scan * G B_spend = b_spend * G receiving_addresses.append( encode_silent_payment_address(B_scan, B_spend, hrp="sp") ) if given["labels"]: for label in given["labels"]: receiving_addresses.append( create_labeled_silent_payment_address( b_scan, B_spend, m=label, hrp="sp" ) ) # Check that the silent payment addresses match for the given BIP32 seed and labels dictionary assert (receiving_addresses == expected["addresses"]), "Receiving addresses don't match" input_pub_keys = [] for vin in vins: pubkey = get_pubkey_from_input(vin) if pubkey.infinity: continue input_pub_keys.append(pubkey) add_to_wallet = [] if (len(input_pub_keys) > 0): A_sum = GE.sum(*input_pub_keys) if A_sum.infinity: # Input pubkeys sum is point at infinity -> skip tx assert expected["outputs"] == [] continue assert A_sum.to_bytes_compressed().hex() == expected.get("input_pub_key_sum"), "A_sum did not match expected input_pub_key_sum" input_hash = get_input_hash([vin.outpoint for vin in vins], A_sum) pre_computed_labels = { (generate_label(b_scan, label) * G).to_bytes_compressed().hex(): generate_label(b_scan, label).to_bytes().hex() for label in given["labels"] } add_to_wallet = scanning( b_scan=b_scan, B_spend=B_spend, A_sum=A_sum, input_hash=input_hash, outputs_to_check=outputs_to_check, labels=pre_computed_labels, expected=expected, ) # Check that the private key is correct for the found output public key for output in add_to_wallet: pub_key = GE.from_bytes_xonly(bytes.fromhex(output["pub_key"])) full_private_key = b_spend + Scalar.from_bytes_checked(bytes.fromhex(output["priv_key_tweak"])) if not (full_private_key * G).has_even_y(): full_private_key = -full_private_key sig = schnorr_sign(msg, full_private_key.to_bytes(), aux) assert schnorr_verify(msg, pub_key.to_bytes_xonly(), sig), f"Invalid signature for {pub_key}" output["signature"] = sig.hex() # Note: order doesn't matter for creating/finding the outputs. However, different orderings of the recipient addresses # will produce different generated outputs if sending to multiple silent payment addresses belonging to the # same sender but with different labels. Because of this, expected["outputs"] contains all possible valid output sets, # based on all possible permutations of recipient address orderings. Must match exactly one of the possible found output # sets in expected["outputs"] if "outputs" in expected: # detailed check against expected outputs generated_set = {frozenset(d.items()) for d in add_to_wallet} expected_set = {frozenset(d.items()) for d in expected["outputs"]} assert generated_set == expected_set, "Receive test failed" elif "n_outputs" in expected: # only check the number of found outputs assert len(add_to_wallet) == expected["n_outputs"], "Receive test failed" else: assert False, "either 'outputs' or 'n_outputs' must be specified in 'expected' field of receiving test vector" print("All tests passed") ================================================ FILE: bip-0352/ripemd160.py ================================================ # Copyright (c) 2021 Pieter Wuille # Distributed under the MIT software license, see the accompanying # file COPYING or http://www.opensource.org/licenses/mit-license.php. """Test-only pure Python RIPEMD160 implementation.""" import unittest # Message schedule indexes for the left path. ML = [ 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 7, 4, 13, 1, 10, 6, 15, 3, 12, 0, 9, 5, 2, 14, 11, 8, 3, 10, 14, 4, 9, 15, 8, 1, 2, 7, 0, 6, 13, 11, 5, 12, 1, 9, 11, 10, 0, 8, 12, 4, 13, 3, 7, 15, 14, 5, 6, 2, 4, 0, 5, 9, 7, 12, 2, 10, 14, 1, 3, 8, 11, 6, 15, 13 ] # Message schedule indexes for the right path. MR = [ 5, 14, 7, 0, 9, 2, 11, 4, 13, 6, 15, 8, 1, 10, 3, 12, 6, 11, 3, 7, 0, 13, 5, 10, 14, 15, 8, 12, 4, 9, 1, 2, 15, 5, 1, 3, 7, 14, 6, 9, 11, 8, 12, 2, 10, 0, 4, 13, 8, 6, 4, 1, 3, 11, 15, 0, 5, 12, 2, 13, 9, 7, 10, 14, 12, 15, 10, 4, 1, 5, 8, 7, 6, 2, 13, 14, 0, 3, 9, 11 ] # Rotation counts for the left path. RL = [ 11, 14, 15, 12, 5, 8, 7, 9, 11, 13, 14, 15, 6, 7, 9, 8, 7, 6, 8, 13, 11, 9, 7, 15, 7, 12, 15, 9, 11, 7, 13, 12, 11, 13, 6, 7, 14, 9, 13, 15, 14, 8, 13, 6, 5, 12, 7, 5, 11, 12, 14, 15, 14, 15, 9, 8, 9, 14, 5, 6, 8, 6, 5, 12, 9, 15, 5, 11, 6, 8, 13, 12, 5, 12, 13, 14, 11, 8, 5, 6 ] # Rotation counts for the right path. RR = [ 8, 9, 9, 11, 13, 15, 15, 5, 7, 7, 8, 11, 14, 14, 12, 6, 9, 13, 15, 7, 12, 8, 9, 11, 7, 7, 12, 7, 6, 15, 13, 11, 9, 7, 15, 11, 8, 6, 6, 14, 12, 13, 5, 14, 13, 13, 7, 5, 15, 5, 8, 11, 14, 14, 6, 14, 6, 9, 12, 9, 12, 5, 15, 8, 8, 5, 12, 9, 12, 5, 14, 6, 8, 13, 6, 5, 15, 13, 11, 11 ] # K constants for the left path. KL = [0, 0x5a827999, 0x6ed9eba1, 0x8f1bbcdc, 0xa953fd4e] # K constants for the right path. KR = [0x50a28be6, 0x5c4dd124, 0x6d703ef3, 0x7a6d76e9, 0] def fi(x, y, z, i): """The f1, f2, f3, f4, and f5 functions from the specification.""" if i == 0: return x ^ y ^ z elif i == 1: return (x & y) | (~x & z) elif i == 2: return (x | ~y) ^ z elif i == 3: return (x & z) | (y & ~z) elif i == 4: return x ^ (y | ~z) else: assert False def rol(x, i): """Rotate the bottom 32 bits of x left by i bits.""" return ((x << i) | ((x & 0xffffffff) >> (32 - i))) & 0xffffffff def compress(h0, h1, h2, h3, h4, block): """Compress state (h0, h1, h2, h3, h4) with block.""" # Left path variables. al, bl, cl, dl, el = h0, h1, h2, h3, h4 # Right path variables. ar, br, cr, dr, er = h0, h1, h2, h3, h4 # Message variables. x = [int.from_bytes(block[4*i:4*(i+1)], 'little') for i in range(16)] # Iterate over the 80 rounds of the compression. for j in range(80): rnd = j >> 4 # Perform left side of the transformation. al = rol(al + fi(bl, cl, dl, rnd) + x[ML[j]] + KL[rnd], RL[j]) + el al, bl, cl, dl, el = el, al, bl, rol(cl, 10), dl # Perform right side of the transformation. ar = rol(ar + fi(br, cr, dr, 4 - rnd) + x[MR[j]] + KR[rnd], RR[j]) + er ar, br, cr, dr, er = er, ar, br, rol(cr, 10), dr # Compose old state, left transform, and right transform into new state. return h1 + cl + dr, h2 + dl + er, h3 + el + ar, h4 + al + br, h0 + bl + cr def ripemd160(data): """Compute the RIPEMD-160 hash of data.""" # Initialize state. state = (0x67452301, 0xefcdab89, 0x98badcfe, 0x10325476, 0xc3d2e1f0) # Process full 64-byte blocks in the input. for b in range(len(data) >> 6): state = compress(*state, data[64*b:64*(b+1)]) # Construct final blocks (with padding and size). pad = b"\x80" + b"\x00" * ((119 - len(data)) & 63) fin = data[len(data) & ~63:] + pad + (8 * len(data)).to_bytes(8, 'little') # Process final blocks. for b in range(len(fin) >> 6): state = compress(*state, fin[64*b:64*(b+1)]) # Produce output. return b"".join((h & 0xffffffff).to_bytes(4, 'little') for h in state) class TestFrameworkKey(unittest.TestCase): def test_ripemd160(self): """RIPEMD-160 test vectors.""" # See https://homes.esat.kuleuven.be/~bosselae/ripemd160.html for msg, hexout in [ (b"", "9c1185a5c5e9fc54612808977ee8f548b2258d31"), (b"a", "0bdc9d2d256b3ee9daae347be6f4dc835a467ffe"), (b"abc", "8eb208f7e05d987a9b044a8e98c6b087f15a0bfc"), (b"message digest", "5d0689ef49d2fae572b881b123a85ffa21595f36"), (b"abcdefghijklmnopqrstuvwxyz", "f71c27109c692c1b56bbdceb5b9d2865b3708dbc"), (b"abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq", "12a053384a9c0c88e405a06c27dcf49ada62eb2b"), (b"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789", "b0e20b6e3116640286ed3a87a5713079b21f5189"), (b"1234567890" * 8, "9b752e45573d4b39f4dbd3323cab82bf63326bfb"), (b"a" * 1000000, "52783243c1697bdbe16d37f97f68f08325dc1528") ]: self.assertEqual(ripemd160(msg).hex(), hexout) ================================================ FILE: bip-0352/secp256k1lab/.github/workflows/main.yml ================================================ name: Tests on: [push, pull_request] jobs: ruff: runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - name: Install the latest version of uv uses: astral-sh/setup-uv@v5 - run: uvx ruff check . mypy: runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - name: Install the latest version of uv uses: astral-sh/setup-uv@v5 - run: uvx mypy . ================================================ FILE: bip-0352/secp256k1lab/.python-version ================================================ 3.9 ================================================ FILE: bip-0352/secp256k1lab/CHANGELOG.md ================================================ # Changelog All notable changes to this project will be documented in this file. The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/), and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html). ## [1.0.0] - 2025-03-31 Initial release. ================================================ FILE: bip-0352/secp256k1lab/COPYING ================================================ The MIT License (MIT) Copyright (c) 2009-2024 The Bitcoin Core developers Copyright (c) 2009-2024 Bitcoin Developers Copyright (c) 2025- The secp256k1lab Developers Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. ================================================ FILE: bip-0352/secp256k1lab/README.md ================================================ secp256k1lab ============ ![Dependencies: None](https://img.shields.io/badge/dependencies-none-success) An INSECURE implementation of the secp256k1 elliptic curve and related cryptographic schemes written in Python, intended for prototyping, experimentation and education. Features: * Low-level secp256k1 field and group arithmetic. * Schnorr signing/verification and key generation according to [BIP-340](https://github.com/bitcoin/bips/blob/master/bip-0340.mediawiki). * ECDH key exchange. WARNING: The code in this library is slow and trivially vulnerable to side channel attacks. ================================================ FILE: bip-0352/secp256k1lab/pyproject.toml ================================================ [project] name = "secp256k1lab" version = "1.0.0" description = "An INSECURE implementation of the secp256k1 elliptic curve and related cryptographic schemes, intended for prototyping, experimentation and education" readme = "README.md" authors = [ { name = "Pieter Wuille", email = "pieter@wuille.net" }, { name = "Tim Ruffing", email = "me@real-or-random.org" }, { name = "Jonas Nick", email = "jonasd.nick@gmail.com" }, { name = "Sebastian Falbesoner", email = "sebastian.falbesoner@gmail.com" } ] maintainers = [ { name = "Tim Ruffing", email = "me@real-or-random.org" }, { name = "Jonas Nick", email = "jonasd.nick@gmail.com" }, { name = "Sebastian Falbesoner", email = "sebastian.falbesoner@gmail.com" } ] requires-python = ">=3.9" license = "MIT" license-files = ["COPYING"] keywords = ["secp256k1", "elliptic curves", "cryptography", "Bitcoin"] classifiers = [ "Development Status :: 5 - Production/Stable", "Intended Audience :: Developers", "Intended Audience :: Education", "Intended Audience :: Science/Research", "License :: OSI Approved :: MIT License", "Programming Language :: Python", "Topic :: Security :: Cryptography", ] dependencies = [] [build-system] requires = ["hatchling"] build-backend = "hatchling.build" ================================================ FILE: bip-0352/secp256k1lab/src/secp256k1lab/__init__.py ================================================ ================================================ FILE: bip-0352/secp256k1lab/src/secp256k1lab/bip340.py ================================================ # The following functions are based on the BIP 340 reference implementation: # https://github.com/bitcoin/bips/blob/master/bip-0340/reference.py from .secp256k1 import FE, GE, G from .util import int_from_bytes, bytes_from_int, xor_bytes, tagged_hash def pubkey_gen(seckey: bytes) -> bytes: d0 = int_from_bytes(seckey) if not (1 <= d0 <= GE.ORDER - 1): raise ValueError("The secret key must be an integer in the range 1..n-1.") P = d0 * G assert not P.infinity return P.to_bytes_xonly() def schnorr_sign( msg: bytes, seckey: bytes, aux_rand: bytes, tag_prefix: str = "BIP0340" ) -> bytes: d0 = int_from_bytes(seckey) if not (1 <= d0 <= GE.ORDER - 1): raise ValueError("The secret key must be an integer in the range 1..n-1.") if len(aux_rand) != 32: raise ValueError("aux_rand must be 32 bytes instead of %i." % len(aux_rand)) P = d0 * G assert not P.infinity d = d0 if P.has_even_y() else GE.ORDER - d0 t = xor_bytes(bytes_from_int(d), tagged_hash(tag_prefix + "/aux", aux_rand)) k0 = ( int_from_bytes(tagged_hash(tag_prefix + "/nonce", t + P.to_bytes_xonly() + msg)) % GE.ORDER ) if k0 == 0: raise RuntimeError("Failure. This happens only with negligible probability.") R = k0 * G assert not R.infinity k = k0 if R.has_even_y() else GE.ORDER - k0 e = ( int_from_bytes( tagged_hash( tag_prefix + "/challenge", R.to_bytes_xonly() + P.to_bytes_xonly() + msg ) ) % GE.ORDER ) sig = R.to_bytes_xonly() + bytes_from_int((k + e * d) % GE.ORDER) assert schnorr_verify(msg, P.to_bytes_xonly(), sig, tag_prefix=tag_prefix) return sig def schnorr_verify( msg: bytes, pubkey: bytes, sig: bytes, tag_prefix: str = "BIP0340" ) -> bool: if len(pubkey) != 32: raise ValueError("The public key must be a 32-byte array.") if len(sig) != 64: raise ValueError("The signature must be a 64-byte array.") try: P = GE.from_bytes_xonly(pubkey) except ValueError: return False r = int_from_bytes(sig[0:32]) s = int_from_bytes(sig[32:64]) if (r >= FE.SIZE) or (s >= GE.ORDER): return False e = ( int_from_bytes(tagged_hash(tag_prefix + "/challenge", sig[0:32] + pubkey + msg)) % GE.ORDER ) R = s * G - e * P if R.infinity or (not R.has_even_y()) or (R.x != r): return False return True ================================================ FILE: bip-0352/secp256k1lab/src/secp256k1lab/ecdh.py ================================================ import hashlib from .secp256k1 import GE, Scalar def ecdh_compressed_in_raw_out(seckey: bytes, pubkey: bytes) -> GE: """TODO""" shared_secret = Scalar.from_bytes_checked(seckey) * GE.from_bytes_compressed(pubkey) assert not shared_secret.infinity # prime-order group return shared_secret def ecdh_libsecp256k1(seckey: bytes, pubkey: bytes) -> bytes: """TODO""" shared_secret = ecdh_compressed_in_raw_out(seckey, pubkey) return hashlib.sha256(shared_secret.to_bytes_compressed()).digest() ================================================ FILE: bip-0352/secp256k1lab/src/secp256k1lab/keys.py ================================================ from .secp256k1 import GE, G from .util import int_from_bytes # The following function is based on the BIP 327 reference implementation # https://github.com/bitcoin/bips/blob/master/bip-0327/reference.py # Return the plain public key corresponding to a given secret key def pubkey_gen_plain(seckey: bytes) -> bytes: d0 = int_from_bytes(seckey) if not (1 <= d0 <= GE.ORDER - 1): raise ValueError("The secret key must be an integer in the range 1..n-1.") P = d0 * G assert not P.infinity return P.to_bytes_compressed() ================================================ FILE: bip-0352/secp256k1lab/src/secp256k1lab/py.typed ================================================ ================================================ FILE: bip-0352/secp256k1lab/src/secp256k1lab/secp256k1.py ================================================ # Copyright (c) 2022-2023 The Bitcoin Core developers # Distributed under the MIT software license, see the accompanying # file COPYING or http://www.opensource.org/licenses/mit-license.php. """Test-only implementation of low-level secp256k1 field and group arithmetic It is designed for ease of understanding, not performance. WARNING: This code is slow and trivially vulnerable to side channel attacks. Do not use for anything but tests. Exports: * FE: class for secp256k1 field elements * GE: class for secp256k1 group elements * G: the secp256k1 generator point """ # TODO Docstrings of methods still say "field element" class APrimeFE: """Objects of this class represent elements of a prime field. They are represented internally in numerator / denominator form, in order to delay inversions. """ # The size of the field (also its modulus and characteristic). SIZE: int def __init__(self, a=0, b=1): """Initialize a field element a/b; both a and b can be ints or field elements.""" if isinstance(a, type(self)): num = a._num den = a._den else: num = a % self.SIZE den = 1 if isinstance(b, type(self)): den = (den * b._num) % self.SIZE num = (num * b._den) % self.SIZE else: den = (den * b) % self.SIZE assert den != 0 if num == 0: den = 1 self._num = num self._den = den def __add__(self, a): """Compute the sum of two field elements (second may be int).""" if isinstance(a, type(self)): return type(self)(self._num * a._den + self._den * a._num, self._den * a._den) if isinstance(a, int): return type(self)(self._num + self._den * a, self._den) return NotImplemented def __radd__(self, a): """Compute the sum of an integer and a field element.""" return type(self)(a) + self @classmethod # REVIEW This should be # def sum(cls, *es: Iterable[Self]) -> Self: # but Self needs the typing_extension package on Python <= 3.12. def sum(cls, *es): """Compute the sum of field elements. sum(a, b, c, ...) is identical to (0 + a + b + c + ...).""" return sum(es, start=cls(0)) def __sub__(self, a): """Compute the difference of two field elements (second may be int).""" if isinstance(a, type(self)): return type(self)(self._num * a._den - self._den * a._num, self._den * a._den) if isinstance(a, int): return type(self)(self._num - self._den * a, self._den) return NotImplemented def __rsub__(self, a): """Compute the difference of an integer and a field element.""" return type(self)(a) - self def __mul__(self, a): """Compute the product of two field elements (second may be int).""" if isinstance(a, type(self)): return type(self)(self._num * a._num, self._den * a._den) if isinstance(a, int): return type(self)(self._num * a, self._den) return NotImplemented def __rmul__(self, a): """Compute the product of an integer with a field element.""" return type(self)(a) * self def __truediv__(self, a): """Compute the ratio of two field elements (second may be int).""" if isinstance(a, type(self)) or isinstance(a, int): return type(self)(self, a) return NotImplemented def __pow__(self, a): """Raise a field element to an integer power.""" return type(self)(pow(self._num, a, self.SIZE), pow(self._den, a, self.SIZE)) def __neg__(self): """Negate a field element.""" return type(self)(-self._num, self._den) def __int__(self): """Convert a field element to an integer in range 0..SIZE-1. The result is cached.""" if self._den != 1: self._num = (self._num * pow(self._den, -1, self.SIZE)) % self.SIZE self._den = 1 return self._num def sqrt(self): """Compute the square root of a field element if it exists (None otherwise).""" raise NotImplementedError def is_square(self): """Determine if this field element has a square root.""" # A more efficient algorithm is possible here (Jacobi symbol). return self.sqrt() is not None def is_even(self): """Determine whether this field element, represented as integer in 0..SIZE-1, is even.""" return int(self) & 1 == 0 def __eq__(self, a): """Check whether two field elements are equal (second may be an int).""" if isinstance(a, type(self)): return (self._num * a._den - self._den * a._num) % self.SIZE == 0 return (self._num - self._den * a) % self.SIZE == 0 def to_bytes(self): """Convert a field element to a 32-byte array (BE byte order).""" return int(self).to_bytes(32, 'big') @classmethod def from_int_checked(cls, v): """Convert an integer to a field element (no overflow allowed).""" if v >= cls.SIZE: raise ValueError return cls(v) @classmethod def from_int_wrapping(cls, v): """Convert an integer to a field element (reduced modulo SIZE).""" return cls(v % cls.SIZE) @classmethod def from_bytes_checked(cls, b): """Convert a 32-byte array to a field element (BE byte order, no overflow allowed).""" v = int.from_bytes(b, 'big') return cls.from_int_checked(v) @classmethod def from_bytes_wrapping(cls, b): """Convert a 32-byte array to a field element (BE byte order, reduced modulo SIZE).""" v = int.from_bytes(b, 'big') return cls.from_int_wrapping(v) def __str__(self): """Convert this field element to a 64 character hex string.""" return f"{int(self):064x}" def __repr__(self): """Get a string representation of this field element.""" return f"{type(self).__qualname__}(0x{int(self):x})" class FE(APrimeFE): SIZE = 2**256 - 2**32 - 977 def sqrt(self): # Due to the fact that our modulus p is of the form (p % 4) == 3, the Tonelli-Shanks # algorithm (https://en.wikipedia.org/wiki/Tonelli-Shanks_algorithm) is simply # raising the argument to the power (p + 1) / 4. # To see why: (p-1) % 2 = 0, so 2 divides the order of the multiplicative group, # and thus only half of the non-zero field elements are squares. An element a is # a (nonzero) square when Euler's criterion, a^((p-1)/2) = 1 (mod p), holds. We're # looking for x such that x^2 = a (mod p). Given a^((p-1)/2) = 1, that is equivalent # to x^2 = a^(1 + (p-1)/2) mod p. As (1 + (p-1)/2) is even, this is equivalent to # x = a^((1 + (p-1)/2)/2) mod p, or x = a^((p+1)/4) mod p. v = int(self) s = pow(v, (self.SIZE + 1) // 4, self.SIZE) if s**2 % self.SIZE == v: return type(self)(s) return None class Scalar(APrimeFE): """TODO Docstring""" SIZE = 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141 class GE: """Objects of this class represent secp256k1 group elements (curve points or infinity) GE objects are immutable. Normal points on the curve have fields: * x: the x coordinate (a field element) * y: the y coordinate (a field element, satisfying y^2 = x^3 + 7) * infinity: False The point at infinity has field: * infinity: True """ # TODO The following two class attributes should probably be just getters as # classmethods to enforce immutability. Unfortunately Python makes it hard # to create "classproperties". `G` could then also be just a classmethod. # Order of the group (number of points on the curve, plus 1 for infinity) ORDER = Scalar.SIZE # Number of valid distinct x coordinates on the curve. ORDER_HALF = ORDER // 2 @property def infinity(self): """Whether the group element is the point at infinity.""" return self._infinity @property def x(self): """The x coordinate (a field element) of a non-infinite group element.""" assert not self.infinity return self._x @property def y(self): """The y coordinate (a field element) of a non-infinite group element.""" assert not self.infinity return self._y def __init__(self, x=None, y=None): """Initialize a group element with specified x and y coordinates, or infinity.""" if x is None: # Initialize as infinity. assert y is None self._infinity = True else: # Initialize as point on the curve (and check that it is). fx = FE(x) fy = FE(y) assert fy**2 == fx**3 + 7 self._infinity = False self._x = fx self._y = fy def __add__(self, a): """Add two group elements together.""" # Deal with infinity: a + infinity == infinity + a == a. if self.infinity: return a if a.infinity: return self if self.x == a.x: if self.y != a.y: # A point added to its own negation is infinity. assert self.y + a.y == 0 return GE() else: # For identical inputs, use the tangent (doubling formula). lam = (3 * self.x**2) / (2 * self.y) else: # For distinct inputs, use the line through both points (adding formula). lam = (self.y - a.y) / (self.x - a.x) # Determine point opposite to the intersection of that line with the curve. x = lam**2 - (self.x + a.x) y = lam * (self.x - x) - self.y return GE(x, y) @staticmethod def sum(*ps): """Compute the sum of group elements. GE.sum(a, b, c, ...) is identical to (GE() + a + b + c + ...).""" return sum(ps, start=GE()) @staticmethod def batch_mul(*aps): """Compute a (batch) scalar group element multiplication. GE.batch_mul((a1, p1), (a2, p2), (a3, p3)) is identical to a1*p1 + a2*p2 + a3*p3, but more efficient.""" # Reduce all the scalars modulo order first (so we can deal with negatives etc). naps = [(int(a), p) for a, p in aps] # Start with point at infinity. r = GE() # Iterate over all bit positions, from high to low. for i in range(255, -1, -1): # Double what we have so far. r = r + r # Add then add the points for which the corresponding scalar bit is set. for (a, p) in naps: if (a >> i) & 1: r += p return r def __rmul__(self, a): """Multiply an integer with a group element.""" if self == G: return FAST_G.mul(Scalar(a)) return GE.batch_mul((Scalar(a), self)) def __neg__(self): """Compute the negation of a group element.""" if self.infinity: return self return GE(self.x, -self.y) def __sub__(self, a): """Subtract a group element from another.""" return self + (-a) def __eq__(self, a): """Check if two group elements are equal.""" return (self - a).infinity def has_even_y(self): """Determine whether a non-infinity group element has an even y coordinate.""" assert not self.infinity return self.y.is_even() def to_bytes_compressed(self): """Convert a non-infinite group element to 33-byte compressed encoding.""" assert not self.infinity return bytes([3 - self.y.is_even()]) + self.x.to_bytes() def to_bytes_compressed_with_infinity(self): """Convert a group element to 33-byte compressed encoding, mapping infinity to zeros.""" if self.infinity: return 33 * b"\x00" return self.to_bytes_compressed() def to_bytes_uncompressed(self): """Convert a non-infinite group element to 65-byte uncompressed encoding.""" assert not self.infinity return b'\x04' + self.x.to_bytes() + self.y.to_bytes() def to_bytes_xonly(self): """Convert (the x coordinate of) a non-infinite group element to 32-byte xonly encoding.""" assert not self.infinity return self.x.to_bytes() @staticmethod def lift_x(x): """Return group element with specified field element as x coordinate (and even y).""" y = (FE(x)**3 + 7).sqrt() if y is None: raise ValueError if not y.is_even(): y = -y return GE(x, y) @staticmethod def from_bytes_compressed(b): """Convert a compressed to a group element.""" assert len(b) == 33 if b[0] != 2 and b[0] != 3: raise ValueError x = FE.from_bytes_checked(b[1:]) r = GE.lift_x(x) if b[0] == 3: r = -r return r @staticmethod def from_bytes_uncompressed(b): """Convert an uncompressed to a group element.""" assert len(b) == 65 if b[0] != 4: raise ValueError x = FE.from_bytes_checked(b[1:33]) y = FE.from_bytes_checked(b[33:]) if y**2 != x**3 + 7: raise ValueError return GE(x, y) @staticmethod def from_bytes(b): """Convert a compressed or uncompressed encoding to a group element.""" assert len(b) in (33, 65) if len(b) == 33: return GE.from_bytes_compressed(b) else: return GE.from_bytes_uncompressed(b) @staticmethod def from_bytes_xonly(b): """Convert a point given in xonly encoding to a group element.""" assert len(b) == 32 x = FE.from_bytes_checked(b) r = GE.lift_x(x) return r @staticmethod def is_valid_x(x): """Determine whether the provided field element is a valid X coordinate.""" return (FE(x)**3 + 7).is_square() def __str__(self): """Convert this group element to a string.""" if self.infinity: return "(inf)" return f"({self.x},{self.y})" def __repr__(self): """Get a string representation for this group element.""" if self.infinity: return "GE()" return f"GE(0x{int(self.x):x},0x{int(self.y):x})" def __hash__(self): """Compute a non-cryptographic hash of the group element.""" if self.infinity: return 0 # 0 is not a valid x coordinate return int(self.x) # The secp256k1 generator point G = GE.lift_x(0x79BE667EF9DCBBAC55A06295CE870B07029BFCDB2DCE28D959F2815B16F81798) class FastGEMul: """Table for fast multiplication with a constant group element. Speed up scalar multiplication with a fixed point P by using a precomputed lookup table with its powers of 2: table = [P, 2*P, 4*P, (2^3)*P, (2^4)*P, ..., (2^255)*P] During multiplication, the points corresponding to each bit set in the scalar are added up, i.e. on average ~128 point additions take place. """ def __init__(self, p): self.table = [p] # table[i] = (2^i) * p for _ in range(255): p = p + p self.table.append(p) def mul(self, a): result = GE() a = int(a) for bit in range(a.bit_length()): if a & (1 << bit): result += self.table[bit] return result # Precomputed table with multiples of G for fast multiplication FAST_G = FastGEMul(G) ================================================ FILE: bip-0352/secp256k1lab/src/secp256k1lab/util.py ================================================ import hashlib # This implementation can be sped up by storing the midstate after hashing # tag_hash instead of rehashing it all the time. def tagged_hash(tag: str, msg: bytes) -> bytes: tag_hash = hashlib.sha256(tag.encode()).digest() return hashlib.sha256(tag_hash + tag_hash + msg).digest() def bytes_from_int(x: int) -> bytes: return x.to_bytes(32, byteorder="big") def xor_bytes(b0: bytes, b1: bytes) -> bytes: return bytes(x ^ y for (x, y) in zip(b0, b1)) def int_from_bytes(b: bytes) -> int: return int.from_bytes(b, byteorder="big") def hash_sha256(b: bytes) -> bytes: return hashlib.sha256(b).digest() ================================================ FILE: bip-0352/send_and_receive_test_vectors.json ================================================ [ { "comment": "Simple send: two inputs", "sending": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "48304602210086783ded73e961037e77d49d9deee4edc2b23136e9728d56e4491c80015c3a63022100fda4c0f21ea18de29edbce57f7134d613e044ee150a89e2e64700de2d4e83d4e2103bd85685d03d111699b15d046319febe77f8de5286e9e512703cdee1bf3be3792", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a914d9317c66f54ff0a152ec50b1d19c25be50c8e15988ac" } }, "private_key": "93f5ed907ad5b2bdbbdcb5d9116ebc0a4e1f92f910d5260237fa45a9408aad16" } ], "recipients": [ { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "025cc9856d6f8375350e123978daac200c260cb5b5ae83106cab90484dcd8fcf36" } ] }, "expected": { "outputs": [ [ "3e9fce73d4e77a4809908e3c3a2e54ee147b9312dc5044a193d1fc85de46e3c1" ] ], "shared_secrets": [ "028158aff7d61ea66b2fa7f555bc3c5937d1debbde16423d630f9aa7943e14d80d" ], "input_private_key_sum": "7ed265a6dac7aba8508a32d6d6b84c7f1dbd0a0941dd01088d69e8d556345f86", "input_pub_keys": [ "025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "03bd85685d03d111699b15d046319febe77f8de5286e9e512703cdee1bf3be3792" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } } }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "48304602210086783ded73e961037e77d49d9deee4edc2b23136e9728d56e4491c80015c3a63022100fda4c0f21ea18de29edbce57f7134d613e044ee150a89e2e64700de2d4e83d4e2103bd85685d03d111699b15d046319febe77f8de5286e9e512703cdee1bf3be3792", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a914d9317c66f54ff0a152ec50b1d19c25be50c8e15988ac" } } } ], "outputs": [ "3e9fce73d4e77a4809908e3c3a2e54ee147b9312dc5044a193d1fc85de46e3c1" ], "key_material": { "spend_priv_key": "9d6ad855ce3417ef84e836892e5a56392bfba05fa5d97ccea30e266f540e08b3", "scan_priv_key": "0f694e068028a717f8af6b9411f9a133dd3565258714cc226594b34db90c1f2c" }, "labels": [] }, "expected": { "addresses": [ "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv" ], "outputs": [ { "priv_key_tweak": "f438b40179a3c4262de12986c0e6cce0634007cdc79c1dcd3e20b9ebc2e7eef6", "pub_key": "3e9fce73d4e77a4809908e3c3a2e54ee147b9312dc5044a193d1fc85de46e3c1", "signature": "74f85b856337fbe837643b86f462118159f93ac4acc2671522f27e8f67b079959195ccc7a5dbee396d2909f5d680d6e30cda7359aa2755822509b70d6b0687a1" } ], "tweak": "024ac253c216532e961988e2a8ce266a447c894c781e52ef6cee902361db960004", "shared_secret": "028158aff7d61ea66b2fa7f555bc3c5937d1debbde16423d630f9aa7943e14d80d", "input_pub_key_sum": "032562c1ab2d6bd45d7ca4d78f569999e5333dffd3ac5263924fd00d00dedc4bee" } } ] }, { "comment": "Simple send: two inputs, order reversed", "sending": [ { "given": { "vin": [ { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" }, { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "48304602210086783ded73e961037e77d49d9deee4edc2b23136e9728d56e4491c80015c3a63022100fda4c0f21ea18de29edbce57f7134d613e044ee150a89e2e64700de2d4e83d4e2103bd85685d03d111699b15d046319febe77f8de5286e9e512703cdee1bf3be3792", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a914d9317c66f54ff0a152ec50b1d19c25be50c8e15988ac" } }, "private_key": "93f5ed907ad5b2bdbbdcb5d9116ebc0a4e1f92f910d5260237fa45a9408aad16" } ], "recipients": [ { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "025cc9856d6f8375350e123978daac200c260cb5b5ae83106cab90484dcd8fcf36" } ] }, "expected": { "outputs": [ [ "3e9fce73d4e77a4809908e3c3a2e54ee147b9312dc5044a193d1fc85de46e3c1" ] ], "shared_secrets": [ "028158aff7d61ea66b2fa7f555bc3c5937d1debbde16423d630f9aa7943e14d80d" ], "input_private_key_sum": "7ed265a6dac7aba8508a32d6d6b84c7f1dbd0a0941dd01088d69e8d556345f86", "input_pub_keys": [ "025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "03bd85685d03d111699b15d046319febe77f8de5286e9e512703cdee1bf3be3792" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } } }, { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "48304602210086783ded73e961037e77d49d9deee4edc2b23136e9728d56e4491c80015c3a63022100fda4c0f21ea18de29edbce57f7134d613e044ee150a89e2e64700de2d4e83d4e2103bd85685d03d111699b15d046319febe77f8de5286e9e512703cdee1bf3be3792", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a914d9317c66f54ff0a152ec50b1d19c25be50c8e15988ac" } } } ], "outputs": [ "3e9fce73d4e77a4809908e3c3a2e54ee147b9312dc5044a193d1fc85de46e3c1" ], "key_material": { "spend_priv_key": "9d6ad855ce3417ef84e836892e5a56392bfba05fa5d97ccea30e266f540e08b3", "scan_priv_key": "0f694e068028a717f8af6b9411f9a133dd3565258714cc226594b34db90c1f2c" }, "labels": [] }, "expected": { "addresses": [ "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv" ], "outputs": [ { "priv_key_tweak": "f438b40179a3c4262de12986c0e6cce0634007cdc79c1dcd3e20b9ebc2e7eef6", "pub_key": "3e9fce73d4e77a4809908e3c3a2e54ee147b9312dc5044a193d1fc85de46e3c1", "signature": "74f85b856337fbe837643b86f462118159f93ac4acc2671522f27e8f67b079959195ccc7a5dbee396d2909f5d680d6e30cda7359aa2755822509b70d6b0687a1" } ], "tweak": "024ac253c216532e961988e2a8ce266a447c894c781e52ef6cee902361db960004", "shared_secret": "028158aff7d61ea66b2fa7f555bc3c5937d1debbde16423d630f9aa7943e14d80d", "input_pub_key_sum": "032562c1ab2d6bd45d7ca4d78f569999e5333dffd3ac5263924fd00d00dedc4bee" } } ] }, { "comment": "Simple send: two inputs from the same transaction", "sending": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 3, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" }, { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 7, "scriptSig": "48304602210086783ded73e961037e77d49d9deee4edc2b23136e9728d56e4491c80015c3a63022100fda4c0f21ea18de29edbce57f7134d613e044ee150a89e2e64700de2d4e83d4e2103bd85685d03d111699b15d046319febe77f8de5286e9e512703cdee1bf3be3792", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a914d9317c66f54ff0a152ec50b1d19c25be50c8e15988ac" } }, "private_key": "93f5ed907ad5b2bdbbdcb5d9116ebc0a4e1f92f910d5260237fa45a9408aad16" } ], "recipients": [ { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "025cc9856d6f8375350e123978daac200c260cb5b5ae83106cab90484dcd8fcf36" } ] }, "expected": { "outputs": [ [ "79e71baa2ba3fc66396de3a04f168c7bf24d6870ec88ca877754790c1db357b6" ] ], "shared_secrets": [ "03aa707f7b5e94b448abd28aa217e3d7a7cc6bb07f1a8d07be4de91bf7b1417469" ], "input_private_key_sum": "7ed265a6dac7aba8508a32d6d6b84c7f1dbd0a0941dd01088d69e8d556345f86", "input_pub_keys": [ "025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "03bd85685d03d111699b15d046319febe77f8de5286e9e512703cdee1bf3be3792" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 3, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } } }, { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 7, "scriptSig": "48304602210086783ded73e961037e77d49d9deee4edc2b23136e9728d56e4491c80015c3a63022100fda4c0f21ea18de29edbce57f7134d613e044ee150a89e2e64700de2d4e83d4e2103bd85685d03d111699b15d046319febe77f8de5286e9e512703cdee1bf3be3792", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a914d9317c66f54ff0a152ec50b1d19c25be50c8e15988ac" } } } ], "outputs": [ "79e71baa2ba3fc66396de3a04f168c7bf24d6870ec88ca877754790c1db357b6" ], "key_material": { "spend_priv_key": "9d6ad855ce3417ef84e836892e5a56392bfba05fa5d97ccea30e266f540e08b3", "scan_priv_key": "0f694e068028a717f8af6b9411f9a133dd3565258714cc226594b34db90c1f2c" }, "labels": [] }, "expected": { "addresses": [ "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv" ], "outputs": [ { "priv_key_tweak": "4851455bfbe1ab4f80156570aa45063201aa5c9e1b1dcd29f0f8c33d10bf77ae", "pub_key": "79e71baa2ba3fc66396de3a04f168c7bf24d6870ec88ca877754790c1db357b6", "signature": "10332eea808b6a13f70059a8a73195808db782012907f5ba32b6eae66a2f66b4f65147e2b968a1678c5f73d57d5d195dbaf667b606ff80c8490eac1f3b710657" } ], "tweak": "03aeea547819c08413974e2ab2b12212e007166bb2058f88b009e082b9b4914a58", "shared_secret": "03aa707f7b5e94b448abd28aa217e3d7a7cc6bb07f1a8d07be4de91bf7b1417469", "input_pub_key_sum": "032562c1ab2d6bd45d7ca4d78f569999e5333dffd3ac5263924fd00d00dedc4bee" } } ] }, { "comment": "Simple send: two inputs from the same transaction, order reversed", "sending": [ { "given": { "vin": [ { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 7, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 3, "scriptSig": "48304602210086783ded73e961037e77d49d9deee4edc2b23136e9728d56e4491c80015c3a63022100fda4c0f21ea18de29edbce57f7134d613e044ee150a89e2e64700de2d4e83d4e2103bd85685d03d111699b15d046319febe77f8de5286e9e512703cdee1bf3be3792", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a914d9317c66f54ff0a152ec50b1d19c25be50c8e15988ac" } }, "private_key": "93f5ed907ad5b2bdbbdcb5d9116ebc0a4e1f92f910d5260237fa45a9408aad16" } ], "recipients": [ { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "025cc9856d6f8375350e123978daac200c260cb5b5ae83106cab90484dcd8fcf36" } ] }, "expected": { "outputs": [ [ "f4c2da807f89cb1501f1a77322a895acfb93c28e08ed2724d2beb8e44539ba38" ] ], "shared_secrets": [ "03054f5c84b07182ba2a2e10a35e088778f95c04f059f4574b024c372eb8ce5468" ], "input_private_key_sum": "7ed265a6dac7aba8508a32d6d6b84c7f1dbd0a0941dd01088d69e8d556345f86", "input_pub_keys": [ "025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "03bd85685d03d111699b15d046319febe77f8de5286e9e512703cdee1bf3be3792" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 7, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } } }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 3, "scriptSig": "48304602210086783ded73e961037e77d49d9deee4edc2b23136e9728d56e4491c80015c3a63022100fda4c0f21ea18de29edbce57f7134d613e044ee150a89e2e64700de2d4e83d4e2103bd85685d03d111699b15d046319febe77f8de5286e9e512703cdee1bf3be3792", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a914d9317c66f54ff0a152ec50b1d19c25be50c8e15988ac" } } } ], "outputs": [ "f4c2da807f89cb1501f1a77322a895acfb93c28e08ed2724d2beb8e44539ba38" ], "key_material": { "spend_priv_key": "9d6ad855ce3417ef84e836892e5a56392bfba05fa5d97ccea30e266f540e08b3", "scan_priv_key": "0f694e068028a717f8af6b9411f9a133dd3565258714cc226594b34db90c1f2c" }, "labels": [] }, "expected": { "addresses": [ "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv" ], "outputs": [ { "priv_key_tweak": "ab0c9b87181bf527879f48db9f14a02233619b986f8e8f2d5d408ce68a709f51", "pub_key": "f4c2da807f89cb1501f1a77322a895acfb93c28e08ed2724d2beb8e44539ba38", "signature": "398a9790865791a9db41a8015afad3a47d60fec5086c50557806a49a1bc038808632b8fe679a7bb65fc6b455be994502eed849f1da3729cd948fc7be73d67295" } ], "tweak": "024cad5180a093d3af0f49f586bdf37f890920178e68e80561ed53351d0fa499ad", "shared_secret": "03054f5c84b07182ba2a2e10a35e088778f95c04f059f4574b024c372eb8ce5468", "input_pub_key_sum": "032562c1ab2d6bd45d7ca4d78f569999e5333dffd3ac5263924fd00d00dedc4bee" } } ] }, { "comment": "Outpoint ordering byte-lexicographically vs. vout-integer", "sending": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 1, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" }, { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 256, "scriptSig": "48304602210086783ded73e961037e77d49d9deee4edc2b23136e9728d56e4491c80015c3a63022100fda4c0f21ea18de29edbce57f7134d613e044ee150a89e2e64700de2d4e83d4e2103bd85685d03d111699b15d046319febe77f8de5286e9e512703cdee1bf3be3792", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a914d9317c66f54ff0a152ec50b1d19c25be50c8e15988ac" } }, "private_key": "93f5ed907ad5b2bdbbdcb5d9116ebc0a4e1f92f910d5260237fa45a9408aad16" } ], "recipients": [ { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "025cc9856d6f8375350e123978daac200c260cb5b5ae83106cab90484dcd8fcf36" } ] }, "expected": { "outputs": [ [ "a85ef8701394b517a4b35217c4bd37ac01ebeed4b008f8d0879f9e09ba95319c" ] ], "shared_secrets": [ "02cb25a6e7c9b7c6d550e0413da63834678465b5e80853a51d0335d318296ac182" ], "input_private_key_sum": "7ed265a6dac7aba8508a32d6d6b84c7f1dbd0a0941dd01088d69e8d556345f86", "input_pub_keys": [ "025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "03bd85685d03d111699b15d046319febe77f8de5286e9e512703cdee1bf3be3792" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 1, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } } }, { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 256, "scriptSig": "48304602210086783ded73e961037e77d49d9deee4edc2b23136e9728d56e4491c80015c3a63022100fda4c0f21ea18de29edbce57f7134d613e044ee150a89e2e64700de2d4e83d4e2103bd85685d03d111699b15d046319febe77f8de5286e9e512703cdee1bf3be3792", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a914d9317c66f54ff0a152ec50b1d19c25be50c8e15988ac" } } } ], "outputs": [ "a85ef8701394b517a4b35217c4bd37ac01ebeed4b008f8d0879f9e09ba95319c" ], "key_material": { "spend_priv_key": "9d6ad855ce3417ef84e836892e5a56392bfba05fa5d97ccea30e266f540e08b3", "scan_priv_key": "0f694e068028a717f8af6b9411f9a133dd3565258714cc226594b34db90c1f2c" }, "labels": [] }, "expected": { "addresses": [ "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv" ], "outputs": [ { "priv_key_tweak": "c8ac0292997b5bca98b3ebd99a57e253071137550f270452cd3df8a3e2266d36", "pub_key": "a85ef8701394b517a4b35217c4bd37ac01ebeed4b008f8d0879f9e09ba95319c", "signature": "c036ee38bfe46aba03234339ae7219b31b824b52ef9d5ce05810a0d6f62330dedc2b55652578aa5bdabf930fae941acd839d5a66f8fce7caa9710ccb446bddd1" } ], "tweak": "031f9a80d0938cf980b51f7cc4fad713d49037f430646dff129c0570d75a40d8f0", "shared_secret": "02cb25a6e7c9b7c6d550e0413da63834678465b5e80853a51d0335d318296ac182", "input_pub_key_sum": "032562c1ab2d6bd45d7ca4d78f569999e5333dffd3ac5263924fd00d00dedc4bee" } } ] }, { "comment": "Single recipient: multiple UTXOs from the same public key", "sending": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" } ], "recipients": [ { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "025cc9856d6f8375350e123978daac200c260cb5b5ae83106cab90484dcd8fcf36" } ] }, "expected": { "outputs": [ [ "548ae55c8eec1e736e8d3e520f011f1f42a56d166116ad210b3937599f87f566" ] ], "shared_secrets": [ "02f6b40ff17f4010fe732ac4b0f2f211281aa09c9a5fb41f1c151ec2606fee9ec2" ], "input_private_key_sum": "d5b8f02cbfe3f1d5295af9fb8a9320e859e9cb07115856486ab1a4e4fb89a621", "input_pub_keys": [ "025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } } }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } } } ], "outputs": [ "548ae55c8eec1e736e8d3e520f011f1f42a56d166116ad210b3937599f87f566" ], "key_material": { "spend_priv_key": "9d6ad855ce3417ef84e836892e5a56392bfba05fa5d97ccea30e266f540e08b3", "scan_priv_key": "0f694e068028a717f8af6b9411f9a133dd3565258714cc226594b34db90c1f2c" }, "labels": [] }, "expected": { "addresses": [ "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv" ], "outputs": [ { "priv_key_tweak": "f032695e2636619efa523fffaa9ef93c8802299181fd0461913c1b8daf9784cd", "pub_key": "548ae55c8eec1e736e8d3e520f011f1f42a56d166116ad210b3937599f87f566", "signature": "f238386c5d5e5444f8d2c75aabbcb28c346f208c76f60823f5de3b67b79e0ec72ea5de2d7caec314e0971d3454f122dda342b3eede01b3857e83654e36b25f76" } ], "tweak": "0319949463fc6a2368d999a2a6a2bcb2dbf64a2ac6e00b3ba5659780c860a6d9e0", "shared_secret": "02f6b40ff17f4010fe732ac4b0f2f211281aa09c9a5fb41f1c151ec2606fee9ec2", "input_pub_key_sum": "03e40664e222ba71e29b80efc907fa22a3c6c64f45e89dbb8511dc7a3712b0a186" } } ] }, { "comment": "Single recipient: taproot only inputs with even y-values", "sending": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "", "txinwitness": "0140c459b671370d12cfb5acee76da7e3ba7cc29b0b4653e3af8388591082660137d087fdc8e89a612cd5d15be0febe61fc7cdcf3161a26e599a4514aa5c3e86f47b", "prevout": { "scriptPubKey": { "hex": "51205a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "", "txinwitness": "0140bd1e708f92dbeaf24a6b8dd22e59c6274355424d62baea976b449e220fd75b13578e262ab11b7aa58e037f0c6b0519b66803b7d9decaa1906dedebfb531c56c1", "prevout": { "scriptPubKey": { "hex": "5120782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338" } }, "private_key": "fc8716a97a48ba9a05a98ae47b5cd201a25a7fd5d8b73c203c5f7b6b6b3b6ad7" } ], "recipients": [ { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "025cc9856d6f8375350e123978daac200c260cb5b5ae83106cab90484dcd8fcf36" } ] }, "expected": { "outputs": [ [ "de88bea8e7ffc9ce1af30d1132f910323c505185aec8eae361670421e749a1fb" ] ], "shared_secrets": [ "02de9719785c6d09f71571dadf44bca59edba2af3e689c65cbc3bb5a4a387732ef" ], "input_private_key_sum": "e7638ebfda3ab3849a5707e240a6627671f7f6e609bf172691cf1e9780e51d47", "input_pub_keys": [ "025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "02782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "", "txinwitness": "0140c459b671370d12cfb5acee76da7e3ba7cc29b0b4653e3af8388591082660137d087fdc8e89a612cd5d15be0febe61fc7cdcf3161a26e599a4514aa5c3e86f47b", "prevout": { "scriptPubKey": { "hex": "51205a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5" } } }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "", "txinwitness": "0140bd1e708f92dbeaf24a6b8dd22e59c6274355424d62baea976b449e220fd75b13578e262ab11b7aa58e037f0c6b0519b66803b7d9decaa1906dedebfb531c56c1", "prevout": { "scriptPubKey": { "hex": "5120782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338" } } } ], "outputs": [ "de88bea8e7ffc9ce1af30d1132f910323c505185aec8eae361670421e749a1fb" ], "key_material": { "spend_priv_key": "9d6ad855ce3417ef84e836892e5a56392bfba05fa5d97ccea30e266f540e08b3", "scan_priv_key": "0f694e068028a717f8af6b9411f9a133dd3565258714cc226594b34db90c1f2c" }, "labels": [] }, "expected": { "addresses": [ "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv" ], "outputs": [ { "priv_key_tweak": "3fb9ce5ce1746ced103c8ed254e81f6690764637ddbc876ec1f9b3ddab776b03", "pub_key": "de88bea8e7ffc9ce1af30d1132f910323c505185aec8eae361670421e749a1fb", "signature": "c5acd25a8f021a4192f93bc34403fd8b76484613466336fb259c72d04c169824f2690ca34e96cee86b69f376c8377003268fda56feeb1b873e5783d7e19bcca5" } ], "tweak": "02dc59cc8e8873b65c1dd5c416d4fbeb647372c329bd84a70c05b310e222e2c183", "shared_secret": "02de9719785c6d09f71571dadf44bca59edba2af3e689c65cbc3bb5a4a387732ef", "input_pub_key_sum": "038180a2125f9d6dd116e1a6139be4d72fd5057dab6aaabaa5654817c11baeb3ba" } } ] }, { "comment": "Single recipient: taproot only with mixed even/odd y-values", "sending": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "", "txinwitness": "0140c459b671370d12cfb5acee76da7e3ba7cc29b0b4653e3af8388591082660137d087fdc8e89a612cd5d15be0febe61fc7cdcf3161a26e599a4514aa5c3e86f47b", "prevout": { "scriptPubKey": { "hex": "51205a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "", "txinwitness": "01400a4d0dca6293f40499394d7eefe14a1de11e0e3454f51de2e802592abf5ee549042a1b1a8fb2e149ee9dd3f086c1b69b2f182565ab6ecf599b1ec9ebadfda6c5", "prevout": { "scriptPubKey": { "hex": "51208c8d23d4764feffcd5e72e380802540fa0f88e3d62ad5e0b47955f74d7b283c4" } }, "private_key": "1d37787c2b7116ee983e9f9c13269df29091b391c04db94239e0d2bc2182c3bf" } ], "recipients": [ { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "025cc9856d6f8375350e123978daac200c260cb5b5ae83106cab90484dcd8fcf36" } ] }, "expected": { "outputs": [ [ "77cab7dd12b10259ee82c6ea4b509774e33e7078e7138f568092241bf26b99f1" ] ], "shared_secrets": [ "030e7f5ca4bf109fc35c8c2d878f756c891ac04c456cc5f0b05fcec4d3b2b1beb2" ], "input_private_key_sum": "cda4ff9a3480e1fbfc6edd61b222f280f9baa0652002c1ffdb612efcc45d2ff2", "input_pub_keys": [ "025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "028c8d23d4764feffcd5e72e380802540fa0f88e3d62ad5e0b47955f74d7b283c4" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "", "txinwitness": "0140c459b671370d12cfb5acee76da7e3ba7cc29b0b4653e3af8388591082660137d087fdc8e89a612cd5d15be0febe61fc7cdcf3161a26e599a4514aa5c3e86f47b", "prevout": { "scriptPubKey": { "hex": "51205a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5" } } }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "", "txinwitness": "01400a4d0dca6293f40499394d7eefe14a1de11e0e3454f51de2e802592abf5ee549042a1b1a8fb2e149ee9dd3f086c1b69b2f182565ab6ecf599b1ec9ebadfda6c5", "prevout": { "scriptPubKey": { "hex": "51208c8d23d4764feffcd5e72e380802540fa0f88e3d62ad5e0b47955f74d7b283c4" } } } ], "outputs": [ "77cab7dd12b10259ee82c6ea4b509774e33e7078e7138f568092241bf26b99f1" ], "key_material": { "spend_priv_key": "9d6ad855ce3417ef84e836892e5a56392bfba05fa5d97ccea30e266f540e08b3", "scan_priv_key": "0f694e068028a717f8af6b9411f9a133dd3565258714cc226594b34db90c1f2c" }, "labels": [] }, "expected": { "addresses": [ "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv" ], "outputs": [ { "priv_key_tweak": "f5382508609771068ed079b24e1f72e4a17ee6d1c979066bf1d4e2a5676f09d4", "pub_key": "77cab7dd12b10259ee82c6ea4b509774e33e7078e7138f568092241bf26b99f1", "signature": "ff65833b8fd1ed3ef9d0443b4f702b45a3f2dd457ba247687e8207745c3be9d2bdad0ab3f07118f8b2efc6a04b95f7b3e218daf8a64137ec91bd2fc67fc137a5" } ], "tweak": "03b990f5b1d90ea8fd4bdd5c856a9dfe17035d196958062e2c6cb4c99e413f3548", "shared_secret": "030e7f5ca4bf109fc35c8c2d878f756c891ac04c456cc5f0b05fcec4d3b2b1beb2", "input_pub_key_sum": "020f0ab50f420ab1249bc2a21659c607f2873400853035aad0ca6d0ded04d62623" } } ] }, { "comment": "Single recipient: taproot input with even y-value and non-taproot input", "sending": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "", "txinwitness": "0140c459b671370d12cfb5acee76da7e3ba7cc29b0b4653e3af8388591082660137d087fdc8e89a612cd5d15be0febe61fc7cdcf3161a26e599a4514aa5c3e86f47b", "prevout": { "scriptPubKey": { "hex": "51205a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "463044021f24e010c6e475814740ba24c8cf9362c4db1276b7f46a7b1e63473159a80ec30221008198e8ece7b7f88e6c6cc6bb8c86f9f00b7458222a8c91addf6e1577bcf7697e2103e0ec4f64b3fa2e463ccfcf4e856e37d5e1e20275bc89ec1def9eb098eff1f85d", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9148cbc7dfe44f1579bff3340bbef1eddeaeb1fc97788ac" } }, "private_key": "8d4751f6e8a3586880fb66c19ae277969bd5aa06f61c4ee2f1e2486efdf666d3" } ], "recipients": [ { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "025cc9856d6f8375350e123978daac200c260cb5b5ae83106cab90484dcd8fcf36" } ] }, "expected": { "outputs": [ [ "30523cca96b2a9ae3c98beb5e60f7d190ec5bc79b2d11a0b2d4d09a608c448f0" ] ], "shared_secrets": [ "021cd92ff153e638d0a97bcd11fafc81c321b111f5ba1efff593371b7b688efdd3" ], "input_private_key_sum": "7823ca0d4895515315a8e3bf602c080b6b732117272429e94751eb9b13a01943", "input_pub_keys": [ "025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "03e0ec4f64b3fa2e463ccfcf4e856e37d5e1e20275bc89ec1def9eb098eff1f85d" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "", "txinwitness": "0140c459b671370d12cfb5acee76da7e3ba7cc29b0b4653e3af8388591082660137d087fdc8e89a612cd5d15be0febe61fc7cdcf3161a26e599a4514aa5c3e86f47b", "prevout": { "scriptPubKey": { "hex": "51205a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5" } } }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "463044021f24e010c6e475814740ba24c8cf9362c4db1276b7f46a7b1e63473159a80ec30221008198e8ece7b7f88e6c6cc6bb8c86f9f00b7458222a8c91addf6e1577bcf7697e2103e0ec4f64b3fa2e463ccfcf4e856e37d5e1e20275bc89ec1def9eb098eff1f85d", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9148cbc7dfe44f1579bff3340bbef1eddeaeb1fc97788ac" } } } ], "outputs": [ "30523cca96b2a9ae3c98beb5e60f7d190ec5bc79b2d11a0b2d4d09a608c448f0" ], "key_material": { "spend_priv_key": "9d6ad855ce3417ef84e836892e5a56392bfba05fa5d97ccea30e266f540e08b3", "scan_priv_key": "0f694e068028a717f8af6b9411f9a133dd3565258714cc226594b34db90c1f2c" }, "labels": [] }, "expected": { "addresses": [ "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv" ], "outputs": [ { "priv_key_tweak": "b40017865c79b1fcbed68896791be93186d08f47e416b289b8c063777e14e8df", "pub_key": "30523cca96b2a9ae3c98beb5e60f7d190ec5bc79b2d11a0b2d4d09a608c448f0", "signature": "d1edeea28cf1033bcb3d89376cabaaaa2886cbd8fda112b5c61cc90a4e7f1878bdd62180b07d1dfc8ffee1863c525a0c7b5bcd413183282cfda756cb65787266" } ], "tweak": "0233c2a447b8b244e4ffcfb59fe365eaa3bb22288b31e2113b9998861f40d4d6da", "shared_secret": "021cd92ff153e638d0a97bcd11fafc81c321b111f5ba1efff593371b7b688efdd3", "input_pub_key_sum": "031ecda9c64faaa6cd57c9f3d7c62bcfc0763c2627ed8dc0e2c3018e9ff37a0bf0" } } ] }, { "comment": "Single recipient: taproot input with odd y-value and non-taproot input", "sending": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "", "txinwitness": "01400a4d0dca6293f40499394d7eefe14a1de11e0e3454f51de2e802592abf5ee549042a1b1a8fb2e149ee9dd3f086c1b69b2f182565ab6ecf599b1ec9ebadfda6c5", "prevout": { "scriptPubKey": { "hex": "51208c8d23d4764feffcd5e72e380802540fa0f88e3d62ad5e0b47955f74d7b283c4" } }, "private_key": "1d37787c2b7116ee983e9f9c13269df29091b391c04db94239e0d2bc2182c3bf" }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "463044021f24e010c6e475814740ba24c8cf9362c4db1276b7f46a7b1e63473159a80ec30221008198e8ece7b7f88e6c6cc6bb8c86f9f00b7458222a8c91addf6e1577bcf7697e2103e0ec4f64b3fa2e463ccfcf4e856e37d5e1e20275bc89ec1def9eb098eff1f85d", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9148cbc7dfe44f1579bff3340bbef1eddeaeb1fc97788ac" } }, "private_key": "8d4751f6e8a3586880fb66c19ae277969bd5aa06f61c4ee2f1e2486efdf666d3" } ], "recipients": [ { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "025cc9856d6f8375350e123978daac200c260cb5b5ae83106cab90484dcd8fcf36" } ] }, "expected": { "outputs": [ [ "359358f59ee9e9eec3f00bdf4882570fd5c182e451aa2650b788544aff012a3a" ] ], "shared_secrets": [ "03d9437eb3676cf5cc00feebe68bc44c4567332e4b89788dec9eceb3779054442b" ], "input_private_key_sum": "700fd97abd324179e8bcc72587bbd9a40b43f67535ce95a0b80175b2dc73a314", "input_pub_keys": [ "028c8d23d4764feffcd5e72e380802540fa0f88e3d62ad5e0b47955f74d7b283c4", "03e0ec4f64b3fa2e463ccfcf4e856e37d5e1e20275bc89ec1def9eb098eff1f85d" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "", "txinwitness": "01400a4d0dca6293f40499394d7eefe14a1de11e0e3454f51de2e802592abf5ee549042a1b1a8fb2e149ee9dd3f086c1b69b2f182565ab6ecf599b1ec9ebadfda6c5", "prevout": { "scriptPubKey": { "hex": "51208c8d23d4764feffcd5e72e380802540fa0f88e3d62ad5e0b47955f74d7b283c4" } } }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "463044021f24e010c6e475814740ba24c8cf9362c4db1276b7f46a7b1e63473159a80ec30221008198e8ece7b7f88e6c6cc6bb8c86f9f00b7458222a8c91addf6e1577bcf7697e2103e0ec4f64b3fa2e463ccfcf4e856e37d5e1e20275bc89ec1def9eb098eff1f85d", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9148cbc7dfe44f1579bff3340bbef1eddeaeb1fc97788ac" } } } ], "outputs": [ "359358f59ee9e9eec3f00bdf4882570fd5c182e451aa2650b788544aff012a3a" ], "key_material": { "spend_priv_key": "9d6ad855ce3417ef84e836892e5a56392bfba05fa5d97ccea30e266f540e08b3", "scan_priv_key": "0f694e068028a717f8af6b9411f9a133dd3565258714cc226594b34db90c1f2c" }, "labels": [] }, "expected": { "addresses": [ "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv" ], "outputs": [ { "priv_key_tweak": "a2f9dd05d1d398347c885d9c61a64d18a264de6d49cea4326bafc2791d627fa7", "pub_key": "359358f59ee9e9eec3f00bdf4882570fd5c182e451aa2650b788544aff012a3a", "signature": "96038ad233d8befe342573a6e54828d863471fb2afbad575cc65271a2a649480ea14912b6abbd3fbf92efc1928c036f6e3eef927105af4ec1dd57cb909f360b8" } ], "tweak": "02d4e4f2c4cdb71c9c39a700a9ee1a0fc05b98362a441183f5770af7d6e2b3038c", "shared_secret": "03d9437eb3676cf5cc00feebe68bc44c4567332e4b89788dec9eceb3779054442b", "input_pub_key_sum": "03bc118b1c8178915b716d6137633722c71adfe721551ec7b3938054691de6a2b9" } } ] }, { "comment": "Multiple outputs: multiple outputs, same recipient", "sending": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b972103782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9147cdd63cc408564188e8e472640e921c7c90e651d88ac" } }, "private_key": "0378e95685b74565fa56751b84a32dfd18545d10d691641b8372e32164fad66a" } ], "recipients": [ { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "025cc9856d6f8375350e123978daac200c260cb5b5ae83106cab90484dcd8fcf36" }, { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "025cc9856d6f8375350e123978daac200c260cb5b5ae83106cab90484dcd8fcf36" } ] }, "expected": { "outputs": [ [ "e976a58fbd38aeb4e6093d4df02e9c1de0c4513ae0c588cef68cda5b2f8834ca", "f207162b1a7abc51c42017bef055e9ec1efc3d3567cb720357e2b84325db33ac" ] ], "shared_secrets": [ "038efbcbc1b0938fba3bf59fea1219a3c54b6d6f9107560da05001407adc13f413", "038efbcbc1b0938fba3bf59fea1219a3c54b6d6f9107560da05001407adc13f413" ], "input_private_key_sum": "ee55616ce5a93e508f03f21949ecbe70a2a0b107b6e1df5d98b4e4da4adaca1b", "input_pub_keys": [ "025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "03782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } } }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b972103782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9147cdd63cc408564188e8e472640e921c7c90e651d88ac" } } } ], "outputs": [ "e976a58fbd38aeb4e6093d4df02e9c1de0c4513ae0c588cef68cda5b2f8834ca", "f207162b1a7abc51c42017bef055e9ec1efc3d3567cb720357e2b84325db33ac" ], "key_material": { "spend_priv_key": "9d6ad855ce3417ef84e836892e5a56392bfba05fa5d97ccea30e266f540e08b3", "scan_priv_key": "0f694e068028a717f8af6b9411f9a133dd3565258714cc226594b34db90c1f2c" }, "labels": [] }, "expected": { "addresses": [ "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv" ], "outputs": [ { "priv_key_tweak": "d97e442d110c0bdd31161a7bb6e7862e038d02a09b1484dfbb463f2e0f7c9230", "pub_key": "e976a58fbd38aeb4e6093d4df02e9c1de0c4513ae0c588cef68cda5b2f8834ca", "signature": "29bd25d0f808d7fcd2aa6d5ed206053899198397506c301b218a9e47a3d7070af03e903ff718978d50d1b6b9af8cc0e313d84eda5d5b1e8e85e5516d630bbeb9" }, { "priv_key_tweak": "33ce085c3c11eaad13694aae3c20301a6c83382ec89a7cde96c6799e2f88805a", "pub_key": "f207162b1a7abc51c42017bef055e9ec1efc3d3567cb720357e2b84325db33ac", "signature": "335667ca6cae7a26438f5cfdd73b3d48fa832fa9768521d7d5445f22c203ab0d74ed85088f27d29959ba627a4509996676f47df8ff284d292567b1beef0e3912" } ], "tweak": "0314bec14463d6c0181083d607fecfba67bb83f95915f6f247975ec566d5642ee8", "shared_secret": "038efbcbc1b0938fba3bf59fea1219a3c54b6d6f9107560da05001407adc13f413", "input_pub_key_sum": "03853f51bef283502181e93238c8708ae27235dc51ae45a0c4053987c52fc6428b" } } ] }, { "comment": "Multiple outputs: multiple outputs, multiple recipients", "sending": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b972103782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9147cdd63cc408564188e8e472640e921c7c90e651d88ac" } }, "private_key": "0378e95685b74565fa56751b84a32dfd18545d10d691641b8372e32164fad66a" } ], "recipients": [ { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "025cc9856d6f8375350e123978daac200c260cb5b5ae83106cab90484dcd8fcf36" }, { "address": "sp1qqgrz6j0lcqnc04vxccydl0kpsj4frfje0ktmgcl2t346hkw30226xqupawdf48k8882j0strrvcmgg2kdawz53a54dd376ngdhak364hzcmynqtn", "scan_pub_key": "02062d49ffc02787d586c608dfbec184aa91a6597d97b463ea5c6babd9d17a95a3", "spend_pub_key": "0381eb9a9a9ec739d527c1631b31b421566f5c2a47b4ab5b1f6a686dfb68eab716" }, { "address": "sp1qqgrz6j0lcqnc04vxccydl0kpsj4frfje0ktmgcl2t346hkw30226xqupawdf48k8882j0strrvcmgg2kdawz53a54dd376ngdhak364hzcmynqtn", "scan_pub_key": "02062d49ffc02787d586c608dfbec184aa91a6597d97b463ea5c6babd9d17a95a3", "spend_pub_key": "0381eb9a9a9ec739d527c1631b31b421566f5c2a47b4ab5b1f6a686dfb68eab716" } ] }, "expected": { "outputs": [ [ "2e847bb01d1b491da512ddd760b8509617ee38057003d6115d00ba562451323a", "841792c33c9dc6193e76744134125d40add8f2f4a96475f28ba150be032d64e8", "f207162b1a7abc51c42017bef055e9ec1efc3d3567cb720357e2b84325db33ac" ] ], "shared_secrets": [ "038efbcbc1b0938fba3bf59fea1219a3c54b6d6f9107560da05001407adc13f413", "03dd5fd04d3c8863be750a1bd7474df06161461d38d3ce1397a5c78cee112cdcd2", "03dd5fd04d3c8863be750a1bd7474df06161461d38d3ce1397a5c78cee112cdcd2" ], "input_private_key_sum": "ee55616ce5a93e508f03f21949ecbe70a2a0b107b6e1df5d98b4e4da4adaca1b", "input_pub_keys": [ "025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "03782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } } }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b972103782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9147cdd63cc408564188e8e472640e921c7c90e651d88ac" } } } ], "outputs": [ "2e847bb01d1b491da512ddd760b8509617ee38057003d6115d00ba562451323a", "841792c33c9dc6193e76744134125d40add8f2f4a96475f28ba150be032d64e8", "f207162b1a7abc51c42017bef055e9ec1efc3d3567cb720357e2b84325db33ac" ], "key_material": { "spend_priv_key": "9902c3c56e84002a7cd410113a9ab21d142be7f53cf5200720bb01314c5eb920", "scan_priv_key": "060b751d7892149006ed7b98606955a29fe284a1e900070c0971f5fb93dbf422" }, "labels": [] }, "expected": { "addresses": [ "sp1qqgrz6j0lcqnc04vxccydl0kpsj4frfje0ktmgcl2t346hkw30226xqupawdf48k8882j0strrvcmgg2kdawz53a54dd376ngdhak364hzcmynqtn" ], "outputs": [ { "priv_key_tweak": "72cd082cccb633bf85240a83494b32dc943a4d05647a6686d23ad4ca59c0ebe4", "pub_key": "2e847bb01d1b491da512ddd760b8509617ee38057003d6115d00ba562451323a", "signature": "38745f3d9f5eef0b1cfb17ca314efa8c521efab28a23aa20ec5e3abb561d42804d539906dce60c4ee7977966184e6f2cab1faa0e5377ceb7148ec5218b4e7878" }, { "priv_key_tweak": "2f17ea873a0047fc01ba8010fef0969e76d0e4283f600d48f735098b1fee6eb9", "pub_key": "841792c33c9dc6193e76744134125d40add8f2f4a96475f28ba150be032d64e8", "signature": "c26f4e3cf371b90b840f48ea0e761b5ec31883ed55719f9ef06a90e282d85f565790ab780a3f491bc2668cc64e944dca849d1022a878cdadb8d168b8da4a6da3" } ], "tweak": "0314bec14463d6c0181083d607fecfba67bb83f95915f6f247975ec566d5642ee8", "shared_secret": "03dd5fd04d3c8863be750a1bd7474df06161461d38d3ce1397a5c78cee112cdcd2", "input_pub_key_sum": "03853f51bef283502181e93238c8708ae27235dc51ae45a0c4053987c52fc6428b" } } ] }, { "comment": "Receiving with labels: label with even parity", "sending": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b972103782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9147cdd63cc408564188e8e472640e921c7c90e651d88ac" } }, "private_key": "0378e95685b74565fa56751b84a32dfd18545d10d691641b8372e32164fad66a" } ], "recipients": [ { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjex54dmqmmv6rw353tsuqhs99ydvadxzrsy9nuvk74epvee55drs734pqq", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "0259352add837b6686e8d22b87017814a46b3ad308702167c65bd5c8599cd28d1c" } ] }, "expected": { "outputs": [ [ "d014d4860f67d607d60b1af70e0ee236b99658b61bb769832acbbe87c374439a" ] ], "shared_secrets": [ "038efbcbc1b0938fba3bf59fea1219a3c54b6d6f9107560da05001407adc13f413" ], "input_private_key_sum": "ee55616ce5a93e508f03f21949ecbe70a2a0b107b6e1df5d98b4e4da4adaca1b", "input_pub_keys": [ "025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "03782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } } }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b972103782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9147cdd63cc408564188e8e472640e921c7c90e651d88ac" } } } ], "outputs": [ "d014d4860f67d607d60b1af70e0ee236b99658b61bb769832acbbe87c374439a" ], "key_material": { "spend_priv_key": "9d6ad855ce3417ef84e836892e5a56392bfba05fa5d97ccea30e266f540e08b3", "scan_priv_key": "0f694e068028a717f8af6b9411f9a133dd3565258714cc226594b34db90c1f2c" }, "labels": [ 2, 3, 1001337 ] }, "expected": { "addresses": [ "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjex54dmqmmv6rw353tsuqhs99ydvadxzrsy9nuvk74epvee55drs734pqq", "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqsg59z2rppn4qlkx0yz9sdltmjv3j8zgcqadjn4ug98m3t6plujsq9qvu5n", "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgq7c2zfthc6x3a5yecwc52nxa0kfd20xuz08zyrjpfw4l2j257yq6qgnkdh5" ], "outputs": [ { "priv_key_tweak": "51d4e9d0d482b5700109b4b2e16ff508269b03d800192a043d61dca4a0a72a52", "pub_key": "d014d4860f67d607d60b1af70e0ee236b99658b61bb769832acbbe87c374439a", "signature": "c30fa63bad6f0a317f39a773a5cbf0b0f8193c71dfebba05ee6ae4ed28e3775e6e04c3ea70a83703bb888122855dc894cab61692e7fd10c9b3494d479a60785e" } ], "tweak": "0314bec14463d6c0181083d607fecfba67bb83f95915f6f247975ec566d5642ee8", "shared_secret": "038efbcbc1b0938fba3bf59fea1219a3c54b6d6f9107560da05001407adc13f413", "input_pub_key_sum": "03853f51bef283502181e93238c8708ae27235dc51ae45a0c4053987c52fc6428b" } } ] }, { "comment": "Receiving with labels: label with odd parity", "sending": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b972103782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9147cdd63cc408564188e8e472640e921c7c90e651d88ac" } }, "private_key": "0378e95685b74565fa56751b84a32dfd18545d10d691641b8372e32164fad66a" } ], "recipients": [ { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqsg59z2rppn4qlkx0yz9sdltmjv3j8zgcqadjn4ug98m3t6plujsq9qvu5n", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "0208a144a18433a83f633c822c1bf5ee4c8c8e24601d6ca75e20a7dc57a0ff9280" } ] }, "expected": { "outputs": [ [ "67626aebb3c4307cf0f6c39ca23247598fabf675ab783292eb2f81ae75ad1f8c" ] ], "shared_secrets": [ "038efbcbc1b0938fba3bf59fea1219a3c54b6d6f9107560da05001407adc13f413" ], "input_private_key_sum": "ee55616ce5a93e508f03f21949ecbe70a2a0b107b6e1df5d98b4e4da4adaca1b", "input_pub_keys": [ "025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "03782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } } }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b972103782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9147cdd63cc408564188e8e472640e921c7c90e651d88ac" } } } ], "outputs": [ "67626aebb3c4307cf0f6c39ca23247598fabf675ab783292eb2f81ae75ad1f8c" ], "key_material": { "spend_priv_key": "9d6ad855ce3417ef84e836892e5a56392bfba05fa5d97ccea30e266f540e08b3", "scan_priv_key": "0f694e068028a717f8af6b9411f9a133dd3565258714cc226594b34db90c1f2c" }, "labels": [ 2, 3, 1001337 ] }, "expected": { "addresses": [ "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjex54dmqmmv6rw353tsuqhs99ydvadxzrsy9nuvk74epvee55drs734pqq", "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqsg59z2rppn4qlkx0yz9sdltmjv3j8zgcqadjn4ug98m3t6plujsq9qvu5n", "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgq7c2zfthc6x3a5yecwc52nxa0kfd20xuz08zyrjpfw4l2j257yq6qgnkdh5" ], "outputs": [ { "priv_key_tweak": "6024ae214876356b8d917716e7707d267ae16a0fdb07de2a786b74a7bbcddead", "pub_key": "67626aebb3c4307cf0f6c39ca23247598fabf675ab783292eb2f81ae75ad1f8c", "signature": "a86d554d0d6b7aa0907155f7e0b47f0182752472fffaeddd68da90e99b9402f166fd9b33039c302c7115098d971c1399e67c19e9e4de180b10ea0b9d6f0db832" } ], "tweak": "0314bec14463d6c0181083d607fecfba67bb83f95915f6f247975ec566d5642ee8", "shared_secret": "038efbcbc1b0938fba3bf59fea1219a3c54b6d6f9107560da05001407adc13f413", "input_pub_key_sum": "03853f51bef283502181e93238c8708ae27235dc51ae45a0c4053987c52fc6428b" } } ] }, { "comment": "Receiving with labels: large label integer", "sending": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b972103782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9147cdd63cc408564188e8e472640e921c7c90e651d88ac" } }, "private_key": "0378e95685b74565fa56751b84a32dfd18545d10d691641b8372e32164fad66a" } ], "recipients": [ { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgq7c2zfthc6x3a5yecwc52nxa0kfd20xuz08zyrjpfw4l2j257yq6qgnkdh5", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "03d85092bbe3468f684ce1d8a2a66ebec96a9e6e09e7110720a5d5faa4aa7880d0" } ] }, "expected": { "outputs": [ [ "7efa60ce78ac343df8a013a2027c6c5ef29f9502edcbd769d2c21717fecc5951" ] ], "shared_secrets": [ "038efbcbc1b0938fba3bf59fea1219a3c54b6d6f9107560da05001407adc13f413" ], "input_private_key_sum": "ee55616ce5a93e508f03f21949ecbe70a2a0b107b6e1df5d98b4e4da4adaca1b", "input_pub_keys": [ "025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "03782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } } }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b972103782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9147cdd63cc408564188e8e472640e921c7c90e651d88ac" } } } ], "outputs": [ "7efa60ce78ac343df8a013a2027c6c5ef29f9502edcbd769d2c21717fecc5951" ], "key_material": { "spend_priv_key": "9d6ad855ce3417ef84e836892e5a56392bfba05fa5d97ccea30e266f540e08b3", "scan_priv_key": "0f694e068028a717f8af6b9411f9a133dd3565258714cc226594b34db90c1f2c" }, "labels": [ 2, 3, 1001337 ] }, "expected": { "addresses": [ "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjex54dmqmmv6rw353tsuqhs99ydvadxzrsy9nuvk74epvee55drs734pqq", "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqsg59z2rppn4qlkx0yz9sdltmjv3j8zgcqadjn4ug98m3t6plujsq9qvu5n", "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgq7c2zfthc6x3a5yecwc52nxa0kfd20xuz08zyrjpfw4l2j257yq6qgnkdh5" ], "outputs": [ { "priv_key_tweak": "e336b92330c33030285ce42e4115ad92d5197913c88e06b9072b4a9b47c664a2", "pub_key": "7efa60ce78ac343df8a013a2027c6c5ef29f9502edcbd769d2c21717fecc5951", "signature": "c9e80dd3bdd25ca2d352ce77510f1aed37ba3509dc8cc0677f2d7c2dd04090707950ce9dd6c83d2a428063063aff5c04f1744e334f661f2fc01b4ef80b50f739" } ], "tweak": "0314bec14463d6c0181083d607fecfba67bb83f95915f6f247975ec566d5642ee8", "shared_secret": "038efbcbc1b0938fba3bf59fea1219a3c54b6d6f9107560da05001407adc13f413", "input_pub_key_sum": "03853f51bef283502181e93238c8708ae27235dc51ae45a0c4053987c52fc6428b" } } ] }, { "comment": "Multiple outputs with labels: un-labeled and labeled address; same recipient", "sending": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b972103782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9147cdd63cc408564188e8e472640e921c7c90e651d88ac" } }, "private_key": "0378e95685b74565fa56751b84a32dfd18545d10d691641b8372e32164fad66a" } ], "recipients": [ { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqaxww2fnhrx05cghth75n0qcj59e3e2anscr0q9wyknjxtxycg07y3pevyj", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "03a6739499dc667d308baefea4de0c4a85cc72aece181bc05712d3919662610ff1" }, { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "025cc9856d6f8375350e123978daac200c260cb5b5ae83106cab90484dcd8fcf36" } ] }, "expected": { "outputs": [ [ "39f42624d5c32a77fda80ff0acee269afec601d3791803e80252ae04e4ffcf4c", "f207162b1a7abc51c42017bef055e9ec1efc3d3567cb720357e2b84325db33ac" ], [ "83dc944e61603137294829aed56c74c9b087d80f2c021b98a7fae5799000696c", "e976a58fbd38aeb4e6093d4df02e9c1de0c4513ae0c588cef68cda5b2f8834ca" ] ], "shared_secrets": [ "038efbcbc1b0938fba3bf59fea1219a3c54b6d6f9107560da05001407adc13f413", "038efbcbc1b0938fba3bf59fea1219a3c54b6d6f9107560da05001407adc13f413" ], "input_private_key_sum": "ee55616ce5a93e508f03f21949ecbe70a2a0b107b6e1df5d98b4e4da4adaca1b", "input_pub_keys": [ "025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "03782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } } }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b972103782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9147cdd63cc408564188e8e472640e921c7c90e651d88ac" } } } ], "outputs": [ "39f42624d5c32a77fda80ff0acee269afec601d3791803e80252ae04e4ffcf4c", "f207162b1a7abc51c42017bef055e9ec1efc3d3567cb720357e2b84325db33ac" ], "key_material": { "spend_priv_key": "9d6ad855ce3417ef84e836892e5a56392bfba05fa5d97ccea30e266f540e08b3", "scan_priv_key": "0f694e068028a717f8af6b9411f9a133dd3565258714cc226594b34db90c1f2c" }, "labels": [ 1 ] }, "expected": { "addresses": [ "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqaxww2fnhrx05cghth75n0qcj59e3e2anscr0q9wyknjxtxycg07y3pevyj" ], "outputs": [ { "priv_key_tweak": "43100f89f1a6bf10081c92b473ffc57ceac7dbed600b6aba9bb3976f17dbb914", "pub_key": "39f42624d5c32a77fda80ff0acee269afec601d3791803e80252ae04e4ffcf4c", "signature": "15c92509b67a6c211ebb4a51b7528d0666e6720de2343b2e92cfb97942ca14693c1f1fdc8451acfdb2644039f8f5c76114807fdc3d3a002d8a46afab6756bd75" }, { "priv_key_tweak": "33ce085c3c11eaad13694aae3c20301a6c83382ec89a7cde96c6799e2f88805a", "pub_key": "f207162b1a7abc51c42017bef055e9ec1efc3d3567cb720357e2b84325db33ac", "signature": "335667ca6cae7a26438f5cfdd73b3d48fa832fa9768521d7d5445f22c203ab0d74ed85088f27d29959ba627a4509996676f47df8ff284d292567b1beef0e3912" } ], "tweak": "0314bec14463d6c0181083d607fecfba67bb83f95915f6f247975ec566d5642ee8", "shared_secret": "038efbcbc1b0938fba3bf59fea1219a3c54b6d6f9107560da05001407adc13f413", "input_pub_key_sum": "03853f51bef283502181e93238c8708ae27235dc51ae45a0c4053987c52fc6428b" } } ] }, { "comment": "Multiple outputs with labels: multiple outputs for labeled address; same recipient", "sending": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b972103782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9147cdd63cc408564188e8e472640e921c7c90e651d88ac" } }, "private_key": "0378e95685b74565fa56751b84a32dfd18545d10d691641b8372e32164fad66a" } ], "recipients": [ { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqaxww2fnhrx05cghth75n0qcj59e3e2anscr0q9wyknjxtxycg07y3pevyj", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "03a6739499dc667d308baefea4de0c4a85cc72aece181bc05712d3919662610ff1" }, { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqaxww2fnhrx05cghth75n0qcj59e3e2anscr0q9wyknjxtxycg07y3pevyj", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "03a6739499dc667d308baefea4de0c4a85cc72aece181bc05712d3919662610ff1" } ] }, "expected": { "outputs": [ [ "39f42624d5c32a77fda80ff0acee269afec601d3791803e80252ae04e4ffcf4c", "83dc944e61603137294829aed56c74c9b087d80f2c021b98a7fae5799000696c" ] ], "shared_secrets": [ "038efbcbc1b0938fba3bf59fea1219a3c54b6d6f9107560da05001407adc13f413", "038efbcbc1b0938fba3bf59fea1219a3c54b6d6f9107560da05001407adc13f413" ], "input_private_key_sum": "ee55616ce5a93e508f03f21949ecbe70a2a0b107b6e1df5d98b4e4da4adaca1b", "input_pub_keys": [ "025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "03782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } } }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b972103782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9147cdd63cc408564188e8e472640e921c7c90e651d88ac" } } } ], "outputs": [ "39f42624d5c32a77fda80ff0acee269afec601d3791803e80252ae04e4ffcf4c", "83dc944e61603137294829aed56c74c9b087d80f2c021b98a7fae5799000696c" ], "key_material": { "spend_priv_key": "9d6ad855ce3417ef84e836892e5a56392bfba05fa5d97ccea30e266f540e08b3", "scan_priv_key": "0f694e068028a717f8af6b9411f9a133dd3565258714cc226594b34db90c1f2c" }, "labels": [ 1 ] }, "expected": { "addresses": [ "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqaxww2fnhrx05cghth75n0qcj59e3e2anscr0q9wyknjxtxycg07y3pevyj" ], "outputs": [ { "priv_key_tweak": "43100f89f1a6bf10081c92b473ffc57ceac7dbed600b6aba9bb3976f17dbb914", "pub_key": "39f42624d5c32a77fda80ff0acee269afec601d3791803e80252ae04e4ffcf4c", "signature": "15c92509b67a6c211ebb4a51b7528d0666e6720de2343b2e92cfb97942ca14693c1f1fdc8451acfdb2644039f8f5c76114807fdc3d3a002d8a46afab6756bd75" }, { "priv_key_tweak": "9d5fd3b91cac9ddfea6fc2e6f9386f680e6cee623cda02f53706306c081de87f", "pub_key": "83dc944e61603137294829aed56c74c9b087d80f2c021b98a7fae5799000696c", "signature": "db0dfacc98b6a6fcc67cc4631f080b1ca38c60d8c397f2f19843f8f95ec91594b24e47c5bd39480a861c1209f7e3145c440371f9191fb96e324690101eac8e8e" } ], "tweak": "0314bec14463d6c0181083d607fecfba67bb83f95915f6f247975ec566d5642ee8", "shared_secret": "038efbcbc1b0938fba3bf59fea1219a3c54b6d6f9107560da05001407adc13f413", "input_pub_key_sum": "03853f51bef283502181e93238c8708ae27235dc51ae45a0c4053987c52fc6428b" } } ] }, { "comment": "Multiple outputs with labels: un-labeled, labeled, and multiple outputs for labeled address; same recipients", "sending": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b972103782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9147cdd63cc408564188e8e472640e921c7c90e651d88ac" } }, "private_key": "0378e95685b74565fa56751b84a32dfd18545d10d691641b8372e32164fad66a" } ], "recipients": [ { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "025cc9856d6f8375350e123978daac200c260cb5b5ae83106cab90484dcd8fcf36" }, { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqaxww2fnhrx05cghth75n0qcj59e3e2anscr0q9wyknjxtxycg07y3pevyj", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "03a6739499dc667d308baefea4de0c4a85cc72aece181bc05712d3919662610ff1" }, { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjyh2ju7hd5gj57jg5r9lev3pckk4n2shtzaq34467erzzdfajfggty6aa5", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "0244baa5cf5db444a9e922832ff2c88716b566a85d62e8235aebd91884d4f64942" }, { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjyh2ju7hd5gj57jg5r9lev3pckk4n2shtzaq34467erzzdfajfggty6aa5", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "0244baa5cf5db444a9e922832ff2c88716b566a85d62e8235aebd91884d4f64942" } ] }, "expected": { "outputs": [ [ "006a02c308ccdbf3ac49f0638f6de128f875db5a213095cf112b3b77722472ae", "39f42624d5c32a77fda80ff0acee269afec601d3791803e80252ae04e4ffcf4c", "ae1a780c04237bd577283c3ddb2e499767c3214160d5a6b0767e6b8c278bd701", "ca64abe1e0f737823fb9a94f597eed418fb2df77b1317e26b881a14bb594faaa" ], [ "006a02c308ccdbf3ac49f0638f6de128f875db5a213095cf112b3b77722472ae", "3edf1ff6657c6e69568811bd726a7a7f480493aa42161acfe8dd4f44521f99ed", "7ee1543ed5d123ffa66fbebc128c020173eb490d5fa2ba306e0c9573a77db8f3", "ca64abe1e0f737823fb9a94f597eed418fb2df77b1317e26b881a14bb594faaa" ], [ "006a02c308ccdbf3ac49f0638f6de128f875db5a213095cf112b3b77722472ae", "7ee1543ed5d123ffa66fbebc128c020173eb490d5fa2ba306e0c9573a77db8f3", "83dc944e61603137294829aed56c74c9b087d80f2c021b98a7fae5799000696c", "ae1a780c04237bd577283c3ddb2e499767c3214160d5a6b0767e6b8c278bd701" ], [ "39f42624d5c32a77fda80ff0acee269afec601d3791803e80252ae04e4ffcf4c", "3c54444944d176437644378c23efb999ab6ab1cacdfe1dc1537b607e3df330e2", "ca64abe1e0f737823fb9a94f597eed418fb2df77b1317e26b881a14bb594faaa", "f4569fc5f69c10f0082cfbb8e072e6266ec55f69fba8cffca4cbb4c144b7e59b" ], [ "39f42624d5c32a77fda80ff0acee269afec601d3791803e80252ae04e4ffcf4c", "ae1a780c04237bd577283c3ddb2e499767c3214160d5a6b0767e6b8c278bd701", "f207162b1a7abc51c42017bef055e9ec1efc3d3567cb720357e2b84325db33ac", "f4569fc5f69c10f0082cfbb8e072e6266ec55f69fba8cffca4cbb4c144b7e59b" ], [ "3c54444944d176437644378c23efb999ab6ab1cacdfe1dc1537b607e3df330e2", "602e10e6944107c9b48bd885b493676578c935723287e0ab2f8b7f136862568e", "7ee1543ed5d123ffa66fbebc128c020173eb490d5fa2ba306e0c9573a77db8f3", "ca64abe1e0f737823fb9a94f597eed418fb2df77b1317e26b881a14bb594faaa" ], [ "3c54444944d176437644378c23efb999ab6ab1cacdfe1dc1537b607e3df330e2", "7ee1543ed5d123ffa66fbebc128c020173eb490d5fa2ba306e0c9573a77db8f3", "83dc944e61603137294829aed56c74c9b087d80f2c021b98a7fae5799000696c", "f4569fc5f69c10f0082cfbb8e072e6266ec55f69fba8cffca4cbb4c144b7e59b" ], [ "3edf1ff6657c6e69568811bd726a7a7f480493aa42161acfe8dd4f44521f99ed", "7ee1543ed5d123ffa66fbebc128c020173eb490d5fa2ba306e0c9573a77db8f3", "f207162b1a7abc51c42017bef055e9ec1efc3d3567cb720357e2b84325db33ac", "f4569fc5f69c10f0082cfbb8e072e6266ec55f69fba8cffca4cbb4c144b7e59b" ], [ "3edf1ff6657c6e69568811bd726a7a7f480493aa42161acfe8dd4f44521f99ed", "ca64abe1e0f737823fb9a94f597eed418fb2df77b1317e26b881a14bb594faaa", "e976a58fbd38aeb4e6093d4df02e9c1de0c4513ae0c588cef68cda5b2f8834ca", "f4569fc5f69c10f0082cfbb8e072e6266ec55f69fba8cffca4cbb4c144b7e59b" ], [ "602e10e6944107c9b48bd885b493676578c935723287e0ab2f8b7f136862568e", "7ee1543ed5d123ffa66fbebc128c020173eb490d5fa2ba306e0c9573a77db8f3", "ae1a780c04237bd577283c3ddb2e499767c3214160d5a6b0767e6b8c278bd701", "f207162b1a7abc51c42017bef055e9ec1efc3d3567cb720357e2b84325db33ac" ], [ "602e10e6944107c9b48bd885b493676578c935723287e0ab2f8b7f136862568e", "ae1a780c04237bd577283c3ddb2e499767c3214160d5a6b0767e6b8c278bd701", "ca64abe1e0f737823fb9a94f597eed418fb2df77b1317e26b881a14bb594faaa", "e976a58fbd38aeb4e6093d4df02e9c1de0c4513ae0c588cef68cda5b2f8834ca" ], [ "83dc944e61603137294829aed56c74c9b087d80f2c021b98a7fae5799000696c", "ae1a780c04237bd577283c3ddb2e499767c3214160d5a6b0767e6b8c278bd701", "e976a58fbd38aeb4e6093d4df02e9c1de0c4513ae0c588cef68cda5b2f8834ca", "f4569fc5f69c10f0082cfbb8e072e6266ec55f69fba8cffca4cbb4c144b7e59b" ] ], "shared_secrets": [ "038efbcbc1b0938fba3bf59fea1219a3c54b6d6f9107560da05001407adc13f413", "038efbcbc1b0938fba3bf59fea1219a3c54b6d6f9107560da05001407adc13f413", "038efbcbc1b0938fba3bf59fea1219a3c54b6d6f9107560da05001407adc13f413", "038efbcbc1b0938fba3bf59fea1219a3c54b6d6f9107560da05001407adc13f413" ], "input_private_key_sum": "ee55616ce5a93e508f03f21949ecbe70a2a0b107b6e1df5d98b4e4da4adaca1b", "input_pub_keys": [ "025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "03782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } } }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b972103782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9147cdd63cc408564188e8e472640e921c7c90e651d88ac" } } } ], "outputs": [ "006a02c308ccdbf3ac49f0638f6de128f875db5a213095cf112b3b77722472ae", "39f42624d5c32a77fda80ff0acee269afec601d3791803e80252ae04e4ffcf4c", "ae1a780c04237bd577283c3ddb2e499767c3214160d5a6b0767e6b8c278bd701", "ca64abe1e0f737823fb9a94f597eed418fb2df77b1317e26b881a14bb594faaa" ], "key_material": { "spend_priv_key": "9d6ad855ce3417ef84e836892e5a56392bfba05fa5d97ccea30e266f540e08b3", "scan_priv_key": "0f694e068028a717f8af6b9411f9a133dd3565258714cc226594b34db90c1f2c" }, "labels": [ 1, 1337 ] }, "expected": { "addresses": [ "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqaxww2fnhrx05cghth75n0qcj59e3e2anscr0q9wyknjxtxycg07y3pevyj", "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjyh2ju7hd5gj57jg5r9lev3pckk4n2shtzaq34467erzzdfajfggty6aa5" ], "outputs": [ { "priv_key_tweak": "4e3352fbe0505c25e718d96007c259ef08db34f8c844e4ff742d9855ff03805a", "pub_key": "006a02c308ccdbf3ac49f0638f6de128f875db5a213095cf112b3b77722472ae", "signature": "6eeae1ea9eb826e3d0e812f65937100e0836ea188c04f36fabc4981eda29de8d3d3529390a0a8b3d830f7bca4f5eae5994b9788ddaf05ad259ffe26d86144b4b" }, { "priv_key_tweak": "43100f89f1a6bf10081c92b473ffc57ceac7dbed600b6aba9bb3976f17dbb914", "pub_key": "39f42624d5c32a77fda80ff0acee269afec601d3791803e80252ae04e4ffcf4c", "signature": "15c92509b67a6c211ebb4a51b7528d0666e6720de2343b2e92cfb97942ca14693c1f1fdc8451acfdb2644039f8f5c76114807fdc3d3a002d8a46afab6756bd75" }, { "priv_key_tweak": "bf709f98d4418f8a67e738154ae48818dad44689cd37fbc070891a396dd1c633", "pub_key": "ae1a780c04237bd577283c3ddb2e499767c3214160d5a6b0767e6b8c278bd701", "signature": "42a19fd8a63dde1824966a95d65a28203e631e49bf96ca5dae1b390e7a0ace2cc8709c9b0c5715047032f57f536a3c80273cbecf4c05be0b5456c183fa122c06" }, { "priv_key_tweak": "736f05e4e3072c3b8656bedef2e9bf54cbcaa2b6fe5320d3e86f5b96874dda71", "pub_key": "ca64abe1e0f737823fb9a94f597eed418fb2df77b1317e26b881a14bb594faaa", "signature": "2e61bb3d79418ecf55f68847cf121bfc12d397b39d1da8643246b2f0a9b96c3daa4bfe9651beb5c9ce20e1f29282c4566400a4b45ee6657ec3b18fdc554da0b4" } ], "tweak": "0314bec14463d6c0181083d607fecfba67bb83f95915f6f247975ec566d5642ee8", "shared_secret": "038efbcbc1b0938fba3bf59fea1219a3c54b6d6f9107560da05001407adc13f413", "input_pub_key_sum": "03853f51bef283502181e93238c8708ae27235dc51ae45a0c4053987c52fc6428b" } } ] }, { "comment": "Single recipient: use silent payments for sender change", "sending": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b972103782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9147cdd63cc408564188e8e472640e921c7c90e651d88ac" } }, "private_key": "0378e95685b74565fa56751b84a32dfd18545d10d691641b8372e32164fad66a" } ], "recipients": [ { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "025cc9856d6f8375350e123978daac200c260cb5b5ae83106cab90484dcd8fcf36" }, { "address": "sp1qqw6vczcfpdh5nf5y2ky99kmqae0tr30hgdfg88parz50cp80wd2wqqlv6saelkk5snl4wfutyxrchpzzwm8rjp3z6q7apna59z9huq4x754e5atr", "scan_pub_key": "03b4cc0b090b6f49a684558852db60ee5eb1c5f74352839c3d18a8fc04ef7354e0", "spend_pub_key": "03ecd43b9fdad484ff57278b21878b844276ce390622d03dd0cfb4288b7e02a6f5" } ] }, "expected": { "outputs": [ [ "be368e28979d950245d742891ae6064020ba548c1e2e65a639a8bb0675d95cff", "f207162b1a7abc51c42017bef055e9ec1efc3d3567cb720357e2b84325db33ac" ] ], "shared_secrets": [ "038efbcbc1b0938fba3bf59fea1219a3c54b6d6f9107560da05001407adc13f413", "037d12c02c3aed482658a28b8d1be030dac1daf995551491d74c00543af98572fb" ], "input_private_key_sum": "ee55616ce5a93e508f03f21949ecbe70a2a0b107b6e1df5d98b4e4da4adaca1b", "input_pub_keys": [ "025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "03782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } } }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b972103782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9147cdd63cc408564188e8e472640e921c7c90e651d88ac" } } } ], "outputs": [ "be368e28979d950245d742891ae6064020ba548c1e2e65a639a8bb0675d95cff", "f207162b1a7abc51c42017bef055e9ec1efc3d3567cb720357e2b84325db33ac" ], "key_material": { "spend_priv_key": "b8f87388cbb41934c50daca018901b00070a5ff6cc25a7e9e716a9d5b9e4d664", "scan_priv_key": "11b7a82e06ca2648d5fded2366478078ec4fc9dc1d8ff487518226f229d768fd" }, "labels": [ 0 ] }, "expected": { "addresses": [ "sp1qqw6vczcfpdh5nf5y2ky99kmqae0tr30hgdfg88parz50cp80wd2wqqauj52ymtc4xdkmx3tgyhrsemg2g3303xk2gtzfy8h8ejet8fz8jcw23zua", "sp1qqw6vczcfpdh5nf5y2ky99kmqae0tr30hgdfg88parz50cp80wd2wqqlv6saelkk5snl4wfutyxrchpzzwm8rjp3z6q7apna59z9huq4x754e5atr" ], "outputs": [ { "priv_key_tweak": "80cd767ed20bd0bb7d8ea5e803f8c381293a62e8a073cf46fb0081da46e64e1f", "pub_key": "be368e28979d950245d742891ae6064020ba548c1e2e65a639a8bb0675d95cff", "signature": "7fbd5074cf1377273155eefafc7c330cb61b31da252f22206ac27530d2b2567040d9af7808342ed4a09598c26d8307446e4ed77079e6a2e61fea736e44da5f5a" } ], "tweak": "0314bec14463d6c0181083d607fecfba67bb83f95915f6f247975ec566d5642ee8", "shared_secret": "037d12c02c3aed482658a28b8d1be030dac1daf995551491d74c00543af98572fb", "input_pub_key_sum": "03853f51bef283502181e93238c8708ae27235dc51ae45a0c4053987c52fc6428b" } }, { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } } }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b972103782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9147cdd63cc408564188e8e472640e921c7c90e651d88ac" } } } ], "outputs": [ "be368e28979d950245d742891ae6064020ba548c1e2e65a639a8bb0675d95cff", "f207162b1a7abc51c42017bef055e9ec1efc3d3567cb720357e2b84325db33ac" ], "key_material": { "spend_priv_key": "9d6ad855ce3417ef84e836892e5a56392bfba05fa5d97ccea30e266f540e08b3", "scan_priv_key": "0f694e068028a717f8af6b9411f9a133dd3565258714cc226594b34db90c1f2c" }, "labels": [] }, "expected": { "addresses": [ "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv" ], "outputs": [ { "priv_key_tweak": "33ce085c3c11eaad13694aae3c20301a6c83382ec89a7cde96c6799e2f88805a", "pub_key": "f207162b1a7abc51c42017bef055e9ec1efc3d3567cb720357e2b84325db33ac", "signature": "335667ca6cae7a26438f5cfdd73b3d48fa832fa9768521d7d5445f22c203ab0d74ed85088f27d29959ba627a4509996676f47df8ff284d292567b1beef0e3912" } ], "tweak": "0314bec14463d6c0181083d607fecfba67bb83f95915f6f247975ec566d5642ee8", "shared_secret": "038efbcbc1b0938fba3bf59fea1219a3c54b6d6f9107560da05001407adc13f413", "input_pub_key_sum": "03853f51bef283502181e93238c8708ae27235dc51ae45a0c4053987c52fc6428b" } } ] }, { "comment": "Single recipient: taproot input with NUMS point", "sending": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "", "txinwitness": "0440c459b671370d12cfb5acee76da7e3ba7cc29b0b4653e3af8388591082660137d087fdc8e89a612cd5d15be0febe61fc7cdcf3161a26e599a4514aa5c3e86f47b22205a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5ac21c150929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac00150", "prevout": { "scriptPubKey": { "hex": "5120da6f0595ecb302bbe73e2f221f05ab10f336b06817d36fd28fc6691725ddaa85" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "", "txinwitness": "0140bd1e708f92dbeaf24a6b8dd22e59c6274355424d62baea976b449e220fd75b13578e262ab11b7aa58e037f0c6b0519b66803b7d9decaa1906dedebfb531c56c1", "prevout": { "scriptPubKey": { "hex": "5120782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338" } }, "private_key": "fc8716a97a48ba9a05a98ae47b5cd201a25a7fd5d8b73c203c5f7b6b6b3b6ad7" }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 1, "scriptSig": "", "txinwitness": "0340268d31a9276f6380107d5321cafa6d9e8e5ea39204318fdc8206b31507c891c3bbcea3c99e2208d73bd127a8e8c5f1e45a54f1bd217205414ddb566ab7eda0092220e0ec4f64b3fa2e463ccfcf4e856e37d5e1e20275bc89ec1def9eb098eff1f85dac21c150929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac0", "prevout": { "scriptPubKey": { "hex": "51200a3c9365ceb131f89b0a4feb6896ebd67bb15a98c31eaa3da143bb955a0f3fcb" } }, "private_key": "8d4751f6e8a3586880fb66c19ae277969bd5aa06f61c4ee2f1e2486efdf666d3" } ], "recipients": [ { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "025cc9856d6f8375350e123978daac200c260cb5b5ae83106cab90484dcd8fcf36" } ] }, "expected": { "outputs": [ [ "79e79897c52935bfd97fc6e076a6431a0c7543ca8c31e0fc3cf719bb572c842d" ] ], "shared_secrets": [ "036f040608cd1e5ee79c54e78bea85904c895591f547beae080d0c5f6946c2730d" ], "input_private_key_sum": "fc8716a97a48ba9a05a98ae47b5cd201a25a7fd5d8b73c203c5f7b6b6b3b6ad7", "input_pub_keys": [ "02782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "", "txinwitness": "0440c459b671370d12cfb5acee76da7e3ba7cc29b0b4653e3af8388591082660137d087fdc8e89a612cd5d15be0febe61fc7cdcf3161a26e599a4514aa5c3e86f47b22205a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5ac21c150929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac00150", "prevout": { "scriptPubKey": { "hex": "5120da6f0595ecb302bbe73e2f221f05ab10f336b06817d36fd28fc6691725ddaa85" } } }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "", "txinwitness": "0140bd1e708f92dbeaf24a6b8dd22e59c6274355424d62baea976b449e220fd75b13578e262ab11b7aa58e037f0c6b0519b66803b7d9decaa1906dedebfb531c56c1", "prevout": { "scriptPubKey": { "hex": "5120782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338" } } }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 1, "scriptSig": "", "txinwitness": "0340268d31a9276f6380107d5321cafa6d9e8e5ea39204318fdc8206b31507c891c3bbcea3c99e2208d73bd127a8e8c5f1e45a54f1bd217205414ddb566ab7eda0092220e0ec4f64b3fa2e463ccfcf4e856e37d5e1e20275bc89ec1def9eb098eff1f85dac21c150929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac0", "prevout": { "scriptPubKey": { "hex": "51200a3c9365ceb131f89b0a4feb6896ebd67bb15a98c31eaa3da143bb955a0f3fcb" } } } ], "outputs": [ "79e79897c52935bfd97fc6e076a6431a0c7543ca8c31e0fc3cf719bb572c842d" ], "key_material": { "spend_priv_key": "9d6ad855ce3417ef84e836892e5a56392bfba05fa5d97ccea30e266f540e08b3", "scan_priv_key": "0f694e068028a717f8af6b9411f9a133dd3565258714cc226594b34db90c1f2c" }, "labels": [] }, "expected": { "addresses": [ "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv" ], "outputs": [ { "priv_key_tweak": "3ddec3232609d348d6b8b53123b4f40f6d4f5398ca586f087b0416ec3b851496", "pub_key": "79e79897c52935bfd97fc6e076a6431a0c7543ca8c31e0fc3cf719bb572c842d", "signature": "d7d06e3afb68363031e4eb18035c46ceae41bdbebe7888a4754bc9848c596436869aeaecff0527649a1f458b71c9ceecec10b535c09d01d720229aa228547706" } ], "tweak": "02213b872c9a6ee28a0d861384a1b3e3ec7257f4855ed09b4323e3899f3b028989", "shared_secret": "036f040608cd1e5ee79c54e78bea85904c895591f547beae080d0c5f6946c2730d", "input_pub_key_sum": "02782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338" } } ] }, { "comment": "Pubkey extraction from malleated p2pkh", "sending": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" }, { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 1, "scriptSig": "0075473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b972103782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9147cdd63cc408564188e8e472640e921c7c90e651d88ac" } }, "private_key": "0378e95685b74565fa56751b84a32dfd18545d10d691641b8372e32164fad66a" }, { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 2, "scriptSig": "5163473045022100e7d26e77290b37128f5215ade25b9b908ce87cc9a4d498908b5bb8fd6daa1b8d022002568c3a8226f4f0436510283052bfb780b76f3fe4aa60c4c5eb118e43b187372102e0ec4f64b3fa2e463ccfcf4e856e37d5e1e20275bc89ec1def9eb098eff1f85d67483046022100c0d3c851d3bd562ae93d56bcefd735ea57c027af46145a4d5e9cac113bfeb0c2022100ee5b2239af199fa9b7aa1d98da83a29d0a2cf1e4f29e2f37134ce386d51c544c2102ad0f26ddc7b3fcc340155963b3051b85289c1869612ecb290184ac952e2864ec68", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a914c82c5ec473cbc6c86e5ef410e36f9495adcf979988ac" } }, "private_key": "72b8ae09175ca7977f04993e651d88681ed932dfb92c5158cdf0161dd23fda6e" } ], "recipients": [ { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "025cc9856d6f8375350e123978daac200c260cb5b5ae83106cab90484dcd8fcf36" } ] }, "expected": { "outputs": [ [ "4612cdbf845c66c7511d70aab4d9aed11e49e48cdb8d799d787101cdd0d53e4f" ] ], "shared_secrets": [ "034773b97ccad9791cb4213964ff9896ccd6581ee69345de5d114786d9d86b03a2" ], "input_private_key_sum": "610e0f75fd05e5e80e088b57af0a46da06cb0700c0c5907aa6d29c6b4ce46348", "input_pub_keys": [ "025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "03782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338", "02e0ec4f64b3fa2e463ccfcf4e856e37d5e1e20275bc89ec1def9eb098eff1f85d" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } } }, { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 1, "scriptSig": "0075473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b972103782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9147cdd63cc408564188e8e472640e921c7c90e651d88ac" } } }, { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 2, "scriptSig": "5163473045022100e7d26e77290b37128f5215ade25b9b908ce87cc9a4d498908b5bb8fd6daa1b8d022002568c3a8226f4f0436510283052bfb780b76f3fe4aa60c4c5eb118e43b187372102e0ec4f64b3fa2e463ccfcf4e856e37d5e1e20275bc89ec1def9eb098eff1f85d67483046022100c0d3c851d3bd562ae93d56bcefd735ea57c027af46145a4d5e9cac113bfeb0c2022100ee5b2239af199fa9b7aa1d98da83a29d0a2cf1e4f29e2f37134ce386d51c544c2102ad0f26ddc7b3fcc340155963b3051b85289c1869612ecb290184ac952e2864ec68", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a914c82c5ec473cbc6c86e5ef410e36f9495adcf979988ac" } } } ], "outputs": [ "4612cdbf845c66c7511d70aab4d9aed11e49e48cdb8d799d787101cdd0d53e4f" ], "key_material": { "spend_priv_key": "9d6ad855ce3417ef84e836892e5a56392bfba05fa5d97ccea30e266f540e08b3", "scan_priv_key": "0f694e068028a717f8af6b9411f9a133dd3565258714cc226594b34db90c1f2c" }, "labels": [] }, "expected": { "addresses": [ "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv" ], "outputs": [ { "priv_key_tweak": "10bde9781def20d7701e7603ef1b1e5e71c67bae7154818814e3c81ef5b1a3d3", "pub_key": "4612cdbf845c66c7511d70aab4d9aed11e49e48cdb8d799d787101cdd0d53e4f", "signature": "6137969f810e9e8ef6c9755010e808f5dd1aed705882e44d7f0ae64eb0c509ec8b62a0671bee0d5914ac27d2c463443e28e999d82dc3d3a4919f093872d947bb" } ], "tweak": "028d6617f9bfe08604beb2188f4eebec923f5f8cc436fa6d14e4256e49bc32e7c8", "shared_secret": "034773b97ccad9791cb4213964ff9896ccd6581ee69345de5d114786d9d86b03a2", "input_pub_key_sum": "038b0d201fe111bdc0e6953772bd02a41959d25d5b2f66bcbe348af27bbdd42735" } } ] }, { "comment": "P2PKH and P2WPKH Uncompressed Keys are skipped", "sending": [ { "given": { "vin": [ { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" }, { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b974104782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c3799373233387c5343bf58e23269e903335b958a12182f9849297321e8d710e49a8727129cab", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9144b92ac4ac6fe6212393894addda332f2e47a315688ac" } }, "private_key": "0378e95685b74565fa56751b84a32dfd18545d10d691641b8372e32164fad66a" }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 1, "scriptSig": "", "txinwitness": "02473045022100e7d26e77290b37128f5215ade25b9b908ce87cc9a4d498908b5bb8fd6daa1b8d022002568c3a8226f4f0436510283052bfb780b76f3fe4aa60c4c5eb118e43b187374104e0ec4f64b3fa2e463ccfcf4e856e37d5e1e20275bc89ec1def9eb098eff1f85d6fe8190e189be57d0d5bcd17dbcbcd04c9b4a1c5f605b10d5c90abfcc0d12884", "prevout": { "scriptPubKey": { "hex": "00140423f731a07491364e8dce98b7c00bda63336950" } }, "private_key": "72b8ae09175ca7977f04993e651d88681ed932dfb92c5158cdf0161dd23fda6e" } ], "recipients": [ { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "025cc9856d6f8375350e123978daac200c260cb5b5ae83106cab90484dcd8fcf36" } ] }, "expected": { "outputs": [ [ "67fee277da9e8542b5d2e6f32d660a9bbd3f0e107c2d53638ab1d869088882d6" ] ], "shared_secrets": [ "0295a54c359da5b2640601ddbedb26e040cb97b6a3432e60b76d1258e85f72fa64" ], "input_private_key_sum": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1", "input_pub_keys": [ "025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a91419c2f3ae0ca3b642bd3e49598b8da89f50c1416188ac" } } }, { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b974104782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c3799373233387c5343bf58e23269e903335b958a12182f9849297321e8d710e49a8727129cab", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9144b92ac4ac6fe6212393894addda332f2e47a315688ac" } } }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 1, "scriptSig": "", "txinwitness": "02473045022100e7d26e77290b37128f5215ade25b9b908ce87cc9a4d498908b5bb8fd6daa1b8d022002568c3a8226f4f0436510283052bfb780b76f3fe4aa60c4c5eb118e43b187374104e0ec4f64b3fa2e463ccfcf4e856e37d5e1e20275bc89ec1def9eb098eff1f85d6fe8190e189be57d0d5bcd17dbcbcd04c9b4a1c5f605b10d5c90abfcc0d12884", "prevout": { "scriptPubKey": { "hex": "00140423f731a07491364e8dce98b7c00bda63336950" } } } ], "outputs": [ "67fee277da9e8542b5d2e6f32d660a9bbd3f0e107c2d53638ab1d869088882d6" ], "key_material": { "spend_priv_key": "9d6ad855ce3417ef84e836892e5a56392bfba05fa5d97ccea30e266f540e08b3", "scan_priv_key": "0f694e068028a717f8af6b9411f9a133dd3565258714cc226594b34db90c1f2c" }, "labels": [] }, "expected": { "addresses": [ "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv" ], "outputs": [ { "priv_key_tweak": "688fa3aeb97d2a46ae87b03591921c2eaf4b505eb0ddca2733c94701e01060cf", "pub_key": "67fee277da9e8542b5d2e6f32d660a9bbd3f0e107c2d53638ab1d869088882d6", "signature": "72e7ad573ac23255d4651d5b0326a200496588acb7a4894b22092236d5eda6a0a9a4d8429b022c2219081fefce5b33795cae488d10f5ea9438849ed8353624f2" } ], "tweak": "02b04034f00da0678507d1345b7d56fecef825a1151f9dc7d8ca6946452a9e1f43", "shared_secret": "0295a54c359da5b2640601ddbedb26e040cb97b6a3432e60b76d1258e85f72fa64", "input_pub_key_sum": "025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5" } } ] }, { "comment": "Skip invalid P2SH inputs", "sending": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "16001419c2f3ae0ca3b642bd3e49598b8da89f50c14161", "txinwitness": "02483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "prevout": { "scriptPubKey": { "hex": "a9148629db5007d5fcfbdbb466637af09daf9125969387" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" }, { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 1, "scriptSig": "1600144b92ac4ac6fe6212393894addda332f2e47a3156", "txinwitness": "02473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b974104782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c3799373233387c5343bf58e23269e903335b958a12182f9849297321e8d710e49a8727129cab", "prevout": { "scriptPubKey": { "hex": "a9146c9bf136fbb7305fd99d771a95127fcf87dedd0d87" } }, "private_key": "0378e95685b74565fa56751b84a32dfd18545d10d691641b8372e32164fad66a" }, { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 2, "scriptSig": "00493046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d601483045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b97014c695221025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be52103782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c3799373233382102e0ec4f64b3fa2e463ccfcf4e856e37d5e1e20275bc89ec1def9eb098eff1f85d53ae", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "a9141044ddc6cea09e4ac40fbec2ba34ad62de6db25b87" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" } ], "recipients": [ { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "025cc9856d6f8375350e123978daac200c260cb5b5ae83106cab90484dcd8fcf36" } ] }, "expected": { "outputs": [ [ "67fee277da9e8542b5d2e6f32d660a9bbd3f0e107c2d53638ab1d869088882d6" ] ], "shared_secrets": [ "0295a54c359da5b2640601ddbedb26e040cb97b6a3432e60b76d1258e85f72fa64" ], "input_private_key_sum": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1", "input_pub_keys": [ "025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "16001419c2f3ae0ca3b642bd3e49598b8da89f50c14161", "txinwitness": "02483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d621025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "prevout": { "scriptPubKey": { "hex": "a9148629db5007d5fcfbdbb466637af09daf9125969387" } } }, { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 1, "scriptSig": "1600144b92ac4ac6fe6212393894addda332f2e47a3156", "txinwitness": "02473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b974104782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c3799373233387c5343bf58e23269e903335b958a12182f9849297321e8d710e49a8727129cab", "prevout": { "scriptPubKey": { "hex": "a9146c9bf136fbb7305fd99d771a95127fcf87dedd0d87" } } }, { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 2, "scriptSig": "00493046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d601483045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b97014c695221025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be52103782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c3799373233382102e0ec4f64b3fa2e463ccfcf4e856e37d5e1e20275bc89ec1def9eb098eff1f85d53ae", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "a9141044ddc6cea09e4ac40fbec2ba34ad62de6db25b87" } } } ], "outputs": [ "67fee277da9e8542b5d2e6f32d660a9bbd3f0e107c2d53638ab1d869088882d6" ], "key_material": { "spend_priv_key": "9d6ad855ce3417ef84e836892e5a56392bfba05fa5d97ccea30e266f540e08b3", "scan_priv_key": "0f694e068028a717f8af6b9411f9a133dd3565258714cc226594b34db90c1f2c" }, "labels": [] }, "expected": { "addresses": [ "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv" ], "outputs": [ { "priv_key_tweak": "688fa3aeb97d2a46ae87b03591921c2eaf4b505eb0ddca2733c94701e01060cf", "pub_key": "67fee277da9e8542b5d2e6f32d660a9bbd3f0e107c2d53638ab1d869088882d6", "signature": "72e7ad573ac23255d4651d5b0326a200496588acb7a4894b22092236d5eda6a0a9a4d8429b022c2219081fefce5b33795cae488d10f5ea9438849ed8353624f2" } ], "tweak": "02b04034f00da0678507d1345b7d56fecef825a1151f9dc7d8ca6946452a9e1f43", "shared_secret": "0295a54c359da5b2640601ddbedb26e040cb97b6a3432e60b76d1258e85f72fa64", "input_pub_key_sum": "025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5" } } ] }, { "comment": "Recipient ignores unrelated outputs", "sending": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "", "txinwitness": "0140c459b671370d12cfb5acee76da7e3ba7cc29b0b4653e3af8388591082660137d087fdc8e89a612cd5d15be0febe61fc7cdcf3161a26e599a4514aa5c3e86f47b", "prevout": { "scriptPubKey": { "hex": "51205a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b972103782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9147cdd63cc408564188e8e472640e921c7c90e651d88ac" } }, "private_key": "0378e95685b74565fa56751b84a32dfd18545d10d691641b8372e32164fad66a" } ], "recipients": [ { "address": "sp1qqgrz6j0lcqnc04vxccydl0kpsj4frfje0ktmgcl2t346hkw30226xqupawdf48k8882j0strrvcmgg2kdawz53a54dd376ngdhak364hzcmynqtn", "scan_pub_key": "02062d49ffc02787d586c608dfbec184aa91a6597d97b463ea5c6babd9d17a95a3", "spend_pub_key": "0381eb9a9a9ec739d527c1631b31b421566f5c2a47b4ab5b1f6a686dfb68eab716" } ] }, "expected": { "outputs": [ [ "841792c33c9dc6193e76744134125d40add8f2f4a96475f28ba150be032d64e8" ] ], "shared_secrets": [ "03dd5fd04d3c8863be750a1bd7474df06161461d38d3ce1397a5c78cee112cdcd2" ], "input_private_key_sum": "ee55616ce5a93e508f03f21949ecbe70a2a0b107b6e1df5d98b4e4da4adaca1b", "input_pub_keys": [ "025a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5", "03782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "", "txinwitness": "0140c459b671370d12cfb5acee76da7e3ba7cc29b0b4653e3af8388591082660137d087fdc8e89a612cd5d15be0febe61fc7cdcf3161a26e599a4514aa5c3e86f47b", "prevout": { "scriptPubKey": { "hex": "51205a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5" } } }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b972103782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9147cdd63cc408564188e8e472640e921c7c90e651d88ac" } } } ], "outputs": [ "841792c33c9dc6193e76744134125d40add8f2f4a96475f28ba150be032d64e8", "782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338" ], "key_material": { "spend_priv_key": "9d6ad855ce3417ef84e836892e5a56392bfba05fa5d97ccea30e266f540e08b3", "scan_priv_key": "0f694e068028a717f8af6b9411f9a133dd3565258714cc226594b34db90c1f2c" }, "labels": [] }, "expected": { "addresses": [ "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv" ], "outputs": [], "tweak": "0314bec14463d6c0181083d607fecfba67bb83f95915f6f247975ec566d5642ee8", "shared_secret": "038efbcbc1b0938fba3bf59fea1219a3c54b6d6f9107560da05001407adc13f413", "input_pub_key_sum": "03853f51bef283502181e93238c8708ae27235dc51ae45a0c4053987c52fc6428b" } } ] }, { "comment": "No valid inputs, sender generates no outputs", "sending": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d641045a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5c61836c9b1688ba431f7ea3039742251f62f0dca3da1bee58a47fa9b456c2d52", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a914460e8b41545d2dbe7e0671f0f573e2232814260a88ac" } }, "private_key": "eadc78165ff1f8ea94ad7cfdc54990738a4c53f6e0507b42154201b8e5dff3b1" }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b974104782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c3799373233387c5343bf58e23269e903335b958a12182f9849297321e8d710e49a8727129cab", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9144b92ac4ac6fe6212393894addda332f2e47a315688ac" } }, "private_key": "0378e95685b74565fa56751b84a32dfd18545d10d691641b8372e32164fad66a" } ], "recipients": [ { "address": "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv", "scan_pub_key": "0220bcfac5b99e04ad1a06ddfb016ee13582609d60b6291e98d01a9bc9a16c96d4", "spend_pub_key": "025cc9856d6f8375350e123978daac200c260cb5b5ae83106cab90484dcd8fcf36" } ] }, "expected": { "outputs": [ [] ], "shared_secrets": [ null ], "input_pub_keys": [] } } ], "receiving": [ { "given": { "vin": [ { "txid": "f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16", "vout": 0, "scriptSig": "483046022100ad79e6801dd9a8727f342f31c71c4912866f59dc6e7981878e92c5844a0ce929022100fb0d2393e813968648b9753b7e9871d90ab3d815ebf91820d704b19f4ed224d641045a1e61f898173040e20616d43e9f496fba90338a39faa1ed98fcbaeee4dd9be5c61836c9b1688ba431f7ea3039742251f62f0dca3da1bee58a47fa9b456c2d52", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a914460e8b41545d2dbe7e0671f0f573e2232814260a88ac" } } }, { "txid": "a1075db55d416d3ca199f55b6084e2115b9345e16c5cf302fc80e9d5fbf5d48d", "vout": 0, "scriptSig": "473045022100a8c61b2d470e393279d1ba54f254b7c237de299580b7fa01ffcc940442ecec4502201afba952f4e4661c40acde7acc0341589031ba103a307b886eb867b23b850b974104782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c3799373233387c5343bf58e23269e903335b958a12182f9849297321e8d710e49a8727129cab", "txinwitness": "", "prevout": { "scriptPubKey": { "hex": "76a9144b92ac4ac6fe6212393894addda332f2e47a315688ac" } } } ], "outputs": [ "782eeb913431ca6e9b8c2fd80a5f72ed2024ef72a3c6fb10263c379937323338", "e0ec4f64b3fa2e463ccfcf4e856e37d5e1e20275bc89ec1def9eb098eff1f85d" ], "key_material": { "spend_priv_key": "9d6ad855ce3417ef84e836892e5a56392bfba05fa5d97ccea30e266f540e08b3", "scan_priv_key": "0f694e068028a717f8af6b9411f9a133dd3565258714cc226594b34db90c1f2c" }, "labels": [] }, "expected": { "addresses": [ "sp1qqgste7k9hx0qftg6qmwlkqtwuy6cycyavzmzj85c6qdfhjdpdjtdgqjuexzk6murw56suy3e0rd2cgqvycxttddwsvgxe2usfpxumr70xc9pkqwv" ], "outputs": [], "tweak": null, "shared_secret": null } } ] }, { "comment": "Input keys sum up to zero / point at infinity: sending fails, receiver skips tx", "sending": [ { "given": { "vin": [ { "txid": "3a286147b25e16ae80aff406f2673c6e565418c40f45c071245cdebc8a94174e", "vout": 0, "scriptSig": "", "txinwitness": "024730440220085003179ce1a3a88ce0069aa6ea045e140761ab88c22a26ae2a8cfe983a6e4602204a8a39940f0735c8a4424270ac8da65240c261ab3fda9272f6d6efbf9cfea366012102557ef3e55b0a52489b4454c1169e06bdea43687a69c1f190eb50781644ab6975", "prevout": { "scriptPubKey": { "hex": "00149d9e24f9fab4e35bf1a6df4b46cb533296ac0792" } }, "private_key": "a6df6a0bb448992a301df4258e06a89fe7cf7146f59ac3bd5ff26083acb22ceb" }, { "txid": "3a286147b25e16ae80aff406f2673c6e565418c40f45c071245cdebc8a94174e", "vout": 1, "scriptSig": "", "txinwitness": "0247304402204586a68e1d97dd3c6928e3622799859f8c3b20c3c670cf654cc905c9be29fdb7022043fbcde1689f3f4045e8816caf6163624bd19e62e4565bc99f95c533e599782c012103557ef3e55b0a52489b4454c1169e06bdea43687a69c1f190eb50781644ab6975", "prevout": { "scriptPubKey": { "hex": "00149860538b5575962776ed0814ae222c7d60c72d7b" } }, "private_key": "592095f44bb766d5cfe20bda71f9575ed2df6b9fb9addc7e5fdffe0923841456" } ], "recipients": [ { "address": "sp1qqtrqglu5g8kh6mfsg4qxa9wq0nv9cauwfwxw70984wkqnw2uwz0w2qnehen8a7wuhwk9tgrzjh8gwzc8q2dlekedec5djk0js9d3d7qhnq6lqj3s", "scan_pub_key": "02c6047f9441ed7d6d3045406e95c07cd85c778e4b8cef3ca7abac09b95c709ee5", "spend_pub_key": "0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798" } ] }, "expected": { "outputs": [ [] ], "shared_secrets": [ null ], "input_pub_keys": [ "02557ef3e55b0a52489b4454c1169e06bdea43687a69c1f190eb50781644ab6975", "03557ef3e55b0a52489b4454c1169e06bdea43687a69c1f190eb50781644ab6975" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "3a286147b25e16ae80aff406f2673c6e565418c40f45c071245cdebc8a94174e", "vout": 0, "scriptSig": "", "txinwitness": "024730440220085003179ce1a3a88ce0069aa6ea045e140761ab88c22a26ae2a8cfe983a6e4602204a8a39940f0735c8a4424270ac8da65240c261ab3fda9272f6d6efbf9cfea366012102557ef3e55b0a52489b4454c1169e06bdea43687a69c1f190eb50781644ab6975", "prevout": { "scriptPubKey": { "hex": "00149d9e24f9fab4e35bf1a6df4b46cb533296ac0792" } } }, { "txid": "3a286147b25e16ae80aff406f2673c6e565418c40f45c071245cdebc8a94174e", "vout": 1, "scriptSig": "", "txinwitness": "0247304402204586a68e1d97dd3c6928e3622799859f8c3b20c3c670cf654cc905c9be29fdb7022043fbcde1689f3f4045e8816caf6163624bd19e62e4565bc99f95c533e599782c012103557ef3e55b0a52489b4454c1169e06bdea43687a69c1f190eb50781644ab6975", "prevout": { "scriptPubKey": { "hex": "00149860538b5575962776ed0814ae222c7d60c72d7b" } } } ], "outputs": [ "0000000000000000000000000000000000000000000000000000000000000000" ], "key_material": { "spend_priv_key": "0000000000000000000000000000000000000000000000000000000000000001", "scan_priv_key": "0000000000000000000000000000000000000000000000000000000000000002" }, "labels": [] }, "expected": { "addresses": [ "sp1qqtrqglu5g8kh6mfsg4qxa9wq0nv9cauwfwxw70984wkqnw2uwz0w2qnehen8a7wuhwk9tgrzjh8gwzc8q2dlekedec5djk0js9d3d7qhnq6lqj3s" ], "outputs": [], "tweak": null, "shared_secret": null } } ] }, { "comment": "Maximum per-group recipient limit K_max is exceeded (2324 matches): sending fails, receiver doesn't scan beyond limit", "sending": [ { "given": { "vin": [ { "txid": "3cde0e7ad8adf24a4e52fd18efafffb94f73f4c7facf2627a5b588ad1c9db87f", "vout": 0, "scriptSig": "", "txinwitness": "01407ce01bc5ef2e4aae353e7f291fec32623d6a491b5421be6dccc70345f32ebae5baa6654c60c074e72da76fd06b343474370e56d3ec0413156ec6261757125ad4", "prevout": { "scriptPubKey": { "hex": "5120bca87f72e604e8850064552bedf380ca4584227057efe12a6cc238470658aaa3" } }, "private_key": "0000000000000000000000000000000000000000000000000000000000001337" } ], "recipients": [ { "address": "sp1qqtnvg7hxjck9ag24naytgd7pjwsmevwh95ydwht58w3uh7uw0ta7kqmk4a3pm24z0yepw6aw27pku56md0hq5ace0l3p3jstkqaajwrsjqc5dde5", "scan_pub_key": "02e6c47ae6962c5ea1559f48b437c193a1bcb1d72d08d75d743ba3cbfb8e7afbeb", "spend_pub_key": "0376af621daaa27932176bae57836e535b6bee0a77197fe218ca0bb03bd9387090", "count": 2324 } ] }, "expected": { "outputs": [ [] ], "shared_secrets": [ null ], "input_private_key_sum": "0000000000000000000000000000000000000000000000000000000000001337", "input_pub_keys": [ "02bca87f72e604e8850064552bedf380ca4584227057efe12a6cc238470658aaa3" ] } } ], "receiving": [ { "given": { "vin": [ { "txid": "3cde0e7ad8adf24a4e52fd18efafffb94f73f4c7facf2627a5b588ad1c9db87f", "vout": 0, "scriptSig": "", "txinwitness": "01407ce01bc5ef2e4aae353e7f291fec32623d6a491b5421be6dccc70345f32ebae5baa6654c60c074e72da76fd06b343474370e56d3ec0413156ec6261757125ad4", "prevout": { "scriptPubKey": { "hex": "5120bca87f72e604e8850064552bedf380ca4584227057efe12a6cc238470658aaa3" } }, "private_key": "0000000000000000000000000000000000000000000000000000000000001337" } ], "outputs": [ "5cfb6fd7a7e5d2af0fee276f2104ce2e5c86cde7955b98f2f1fb32811b448f2f", "da290e0d79ead5cd2e5d150aac80dcab54dbd0e68f241a6c34dc30906eabd13d", "d4a2b1458f0c8b20d756bde8e545560d7e7a65f6b4158f01ed34a913ba3a4603", "24752e555b0edcca123f769113692224bf1e6db137cddeb7d69ae52e51144e9e", "c911f722ef9a3594d6b85c585d4f3ed8dc437f850591dc627a0154723644114b", "ef91ddaa83a0b748d638dc9be8c9771b049a04815f03967b7ee993bde6c260ab", "ee4ed334fb38af95f52c6bbadcf2f491e646b9cc8ed31da67635f36c3cfdaba0", "a17d61b4772e453b32782744902261e051510cbafc04f086f53480d1ceee1a9c", "44d89f5e903739072e3aff8a3eb2f351520f77ff288ac8be277be3f28834bdd2", "3eff02a4a04d66d63f6bc93a693f23db703f351c0a1ff1656b907ed348a9a35f", "628c23a6e21e6a47b80274fc80e4decb98ff79b8040c7f9ea5972e4920b62b6d", "e72190c0a5ea167c2663b18d378520b9228da61ebbc99c3fa2af39e01fb9501e", "24183edbc5b80588e0e5b803e924e77fc1cab1afca54cfd285dad9bfc2a34f6d", "c45bad25a223f0f617e8167f858037907e4454210a745f3b9798c8913646dfc6", "9f9cec85011d7f718f96ee1a2940df21920a857cd1a545255579cb615f285a42", "8c60891f9bc2f772efc51d44f7cc885161412835b6fd5aac3b0cf57c3c2f9154", "85ac46a6ac9569ed67d1bc5342ed3b591af5e01581d1b09bcb2c71deb9b2c2c9", "8a6bfe47e616c6854fc797a4af53ef51c942b99eae18f316594fc8eb8869ca05", "ed5e1aa6a8b4e805273367b8ec3ade16ed6494270fc2169ba920b89770efe8eb", "2448503c55a1a7035c069e1d5461b81774c43bf6061421fdd0157009bfe96a8a", "d0dcb3d7b551eac8d31fceccb83df415c554860d5541dd08ff5fa0028ce5704f", "f11a298b54b650613e0b0183552c9c9e42c3812e03cf713d351ef71106b6ee3f", "49749206f23791f858c453cb60160d48710075bdbfd33907b0046d10f0b0295e", "3fbfdb52cbf0ea9e6655a211748bf2ac2dc92ff3cfeeef0f0a26be9987016de0", "d4a29144511981919cadbe8227fc68379e85d3fe399f177c2ae36c304b6ad6b0", "c586cc196ff56f42396f426a0200afee3a6c41058d81f19caf6536ec0efd5605", "c666994f027ceab025256af28d8ea6aec452fb8b0e1f69e7e13a4f3c5119f4ae", "5c9216cc4529c3f9c62caf70b04f8354ce9ec2cabaef745092bea1b160328fda", "d9aea54323503d78c026a8cd465c19a6df54b32ee866714d190e8260054361da", "ba71f87ca1d74eee115d8e8a26293fe2c88d9d66cff185a7a079282f02f931ad", "b8b930666b2df74c33dc8963221080c115246070e3fcd51f39bee71312db4fc4", "b7f42d2f18a3ac61f570b64ae6864f7dbff774a370ba27358d76797e841d5304", "d636d179055241a0f8bb7db193912da513a8999684d9829b266985a8083819a9", "be9622aec125f9605bcee193a99ca27c16bc591122ff8b44c511a85e6f63ec9d", "af5beb25776f84fadd6079c3ffd85775a35ad74096a58229e1d5076d836ca25d", "75fb55ec31e304456f663c9a66321e67f9d9bd8f43749494acc5189ed57b0d4a", "8dfebff33c514486d06eeb4ab8eb8471496556858c4382f73780620101a77f71", "93bfd4e75706951de4a59c7f70c5d2ce4c617b4bde0b0b23ae046df096116726", "b6eeca22f43bd62a4fcb3eee719e07d39ea703fa0707970fc197916f2efebbb5", "0437c3971f73342e5c41178590e1cb1364cb855b2d20b7b6c1c1ed0e7da5b57b", "d284c831cd9d52793977925ce3111b68f36d1ea456e46716158fe6947fb6d635", "d95b8d2789fd06cc764d47cc7e0697404220ae8f938ef47dcc9a1bba299fbb9f", "33599fb1fe313b5a2680b126bfee93cb097d938915d425a63e307e5834479b95", "05ba86903fac2f02ef2e152072bc6067008ee8ee34ce55ad460801303373eaab", "0b757802e56728b6d5b28e671a90de573d7251a47fc1bcd9319b617cac8e1463", "b4a2451e725e4cbcdf47fc736139cfe29c847e2f75cbb7653d80c8522bd48a6c", "8dd800c3a7cb1ee60f52db3bb69413c4c4247b0b134576552c675970f9903c9b", "4de21129c6fdf5568040346bbdda272caaadd58218ec6f1f152518068dac4d4d", "22f6927eae0c3717395df6483d756028839fbf0814f8cf0391159efa65dd2854", "192d26fe0bc772c705c2657dd5c5033ac41ba408793e6c721f74c53747be16e8", "9527b8e19570a16ce2d8dd3620dfd915e461bccc82340fe682f7f811b978814d", "f84039ff95cd44f842d7cf6982a726957a89d90bb151a368e62770720d3efbee", "b5b36dd84b352cddf715246d0463984b9d7894f50b566a20042c4d485df41946", "592e1bd733a1095b9e5b770021769090df0c001260803fce9a9b761ba697a5e7", "dd2fdbd6932d8b56d6ff91db3ed28f282a6ca01588ee5a552d061da215580411", "82f95ef71d4d0b32e3f0cef89e6e90a8c271cd5536b38c507fc69b354ab51062", "1800903b2d5f8483a12f0b98a5b35ed39d6cf8f4a52f495395f1816d6e3c139c", "121a2c2ea70a6986af8bde71b7f75ac9f9e1189eeb9756395e7281702f01936d", "8578df7e8ec4b068f64dca679310894afec095dbbedbefef5944c3a319809b8b", "5cebde1dbb352ff62841d7c50c3c45cd0fd1b7b3ebe884a7cf29cef6686695ab", "362f7a73f2620ea061586b5edbee01f9c026ae6e0d95131c570c44933fc41f10", "3a19b5976236d44a3d1d6920b348fcef9ec830aac56aa672353c711471ebc36a", "842c43c5293b03811165f1ff7e04c189ccd355fe08d37808a843a0995541c075", "0ab1fdbf7117c88aed3f882d5f7dee8964c9246030086b9ee3e2ebed4eb2c731", "7cf8ca4463d4bd500cc12623ac9d3984cc48e7fbb98bebb4a498c2fd66d54cde", "631676f3369eb479686256cef33c4fb061c212cc215ab442d8f7837c039ddacc", "2fff6de5386b65efe6062cc2242b692a1e811a083612ab79fa7f7517f1488767", "3c7d8b7f2a56e22ade186a70a3039b4d4e4e3c0be6e661770b0a7b2ef18b178b", "e030882188281a754c00706f621084f96869bf95bb5d005ccc7b2649fbfc747e", "072cb899c3eb621240792a39bf727bf59398329748317d5ca1addfd8ee2f7e92", "37cfa6b7214e99bbec6323802115b9615b10851ac85cdc26f213b9532fdefcb8", "68b14b71ad6b5e2d41ef47fe1b9229a0b8297ede0812d1b9cb95aac185d1a5b8", "652ef549580cf412bb217fb15b2a0a1db8feb3c79969b95364a80dd97d565f09", "dd3504b7563a65115a050505bc88ee23a50e37c354773cac329355c16c43d839", "6d7f05d6ee71459d2ea982f7a5cd4a251d7466d4892e6c8b6aaf45eec66472d7", "14c28adbf9008d0cbcc978006b6c1ec7be51a134bd5587e94ee33844b62c1ffb", "f9c20067f16feaaf3f8daa8456dd9334725ebdc8b49b4f74f5a02c38ef5f2804", "e2c537948a01054b7a0d630952c2ddd395a3a265d618e22ee9d99d4597f82322", "70e3a71945fee29350b5b10a8ee8dcbd19c2f734e22407bb6b50ec3acb1035a5", "effbced848df72cd467b1ada7353b1ddc0b7f3f08190c0f2fc747f18303ed9f8", "02d6eedc5abc295bcfbd4c30a8fa3406c8256d8e51f4714800b4aecb795a976b", "92134c6158993a0390af92565e166418561c9b157989d02304b68c2ee1babe14", "6065e3e3aff3e2b2f33bf4af9256e9368b8a303335b0587c8cc9e31cb9db42bd", "732fd2ba9efabc6d79bd7404c1c6f1d5c1f14c9bfe02ee1320621824847935c2", "209f9c958b5f4813b32205a44d05c83aa1009cb7b9c7343f0ca3717ae069defc", "1d274fcb65b6d4c846e95030c37851a97d161f926ed88f6c4dec4ed7007fc23b", "1d3787106cf47e1e9d08761a6c6f427ef6c07d4a571f23d340ae2d31d34b1d8e", "5697a3f56a0a2a6bd6991ba05559df9b526d5c42e19604c398548a7cb0dec0b5", "8c0f581f38238215f10f8017e3d234cbda9d94ca017bbd6b076ac8666014b3d3", "78f061b0fc912fbbeb0d207b92528ad78ded55ec145c8f18133991847fb9cbe9", "1e3555081a869f3aafa3d74d6b5afa942baace60869ecd4cd33635f84602b715", "4f0e36ac0c4813db3fdf79d85ef0db89150dc1be2c879ba06299c049288ab8be", "6b048c38924b7a1f970cdff081124b739202b703db5c17bafa4ad23a5bcb97e9", "a5f5e9238aec20bd706262f64671ca2d05961f55ca383953d489edf857e4b2a4", "a047b08e2af7ae5bfb9e54f98051ff7cd5e7dc88a25afacdd9a324526cd33c63", "66ae2b9513a0e0ad125001bcd5f3a36e18b4ec009db4020ea4afc4951cb39a34", "621d8269c8f93b6336f8b7480516d2191cfb15a1d9501463771d0fb70c1afa33", "76b94079066bff52a077ba1d1ba8cdec4d6484d1ce2f7454b2b04aa3d9cf52ed", "33c6a108f9d4fe054c085991d89d2a5c32b8f108c95b0e688c5763424c283e54", "52575ed2ad84295a070a99e7785ff0e4dd32a93d3830be7f7c2811804f3df2f3", "158dfe014c271c148b38459ef16b49cc3b5c6bdfe052795a6f6a6aacbb3e47b4", "d471729cb231deeb2f1a67f91962ecfcb9e8c66f66b6b79fe1117d34ae86a7c0", "e086b1a09ab5307d953e25366b1acf7c41047a926aa6a4d122c5a34e3e0d93d4", "d541d825401a1734d9961fdb4f0e9ce7af220c6929648e0aa2e885cd28696343", "a555af7a52ac07e681c247f1d6597f8240d28e76036bbf3b2be1f7cfab90dfd6", "8598fe7a4a6c6fa865c0ca8e8e65c96301c80965e19e48f5d4ca29ac073551c7", "70c9ac61ab3508a7419ead73503d8fe51b4ecba73a55d4b167cd4db6c9b0cb8a", "e594eb83b38ad916176abff3f0ec16d7a814a461012c8f9bc8286274af3f1856", "fa4e0df6df82f21050394fc2caaa8a8713b131d0d1f7d21eb92b56796095bf17", "891711c535579b555105e5ec18ea0f2f610c6fe5126ff0f6a4257e99a24033c5", "f192c9b2c49dab7515d405052f825abead30ef9a870ba3bdad98c1d6256be461", "70c22f6ceb81744c83eb8dae69980f4583c75431457dbb14f5ecd6c9fae3e63d", "7d563f44bdfcb2a10ee053f4c05b8d46fa90d44822775f97ee8cfbdeda7a4ca1", "c09b3df69eaa232a9119e2fb805cdccacb658b2fb9c7f3a2106c8399aa928033", "15b4b3d50fef72de80fef6e3351dae0f203902e4c4db8ce8d8737b67aed9104d", "c9b7718633714b3ce1b489f13e53fc647be53cba7703f07a35a8815245b23ff3", "2d344af9852fc2451ca5d2ed7155e074efd2c53ca9cbed7f48c74658967aeca6", "c8b778b5c1fc378365d8b342915215117c3d365e12f61f3ccefbe4091879e373", "1deb076e44c029027c1aa10000305c3eded5d401a036c21a4dd3d3455c0c33a1", "d2d2dfe410cefbae2309e746690818e8d52dcd80ebd192cddaa00204b6833d05", "d18a0a0bcc678908ff00b236296f0a955a9aa52a802ee4175849d0bcb3d6738a", "7af51e08357e455e4dda86d60da75899b5ffce4bebc7f96037d1e404b1260ebe", "65b930580f9738e1a7af2ac56faad5bdc6a417e75cb872b7f62513f4e8e36b33", "71c8e88c7c478a4d919d0c80d351331102584d032d82aa25510801e18bb5d6b9", "2166bad16a6e4a1f77a22b0fb13f7f11d618a123c3c077dbf1ed1504ed68cbb4", "717a3a5903c2b12aea8be15599ea9864259a964c0139125e649fefbec763890e", "0d042f5767f6cb2f94526b5b6da8ef986e4a5927eb5f734bdeb6c6ec3bb8211a", "bb67d586774ae9f3653c609dbdd98f216315b54c0ce24ad9e359d0c2c21614a3", "945b2962ec44c54ea25e3e35e32a2362c130fc3a9495b16871e8a2eadbe457e7", "7d5324e5e158c82388cba0d497530c6de0c1ba97131688931c03dbfc60ca7541", "21805a8f8d43aede3e927b80ef04924d388e96f3cc3947a0dbc1bd1b812539f0", "27ec492fde5fc3d3784359d9a270b735c1820bc4a6f15ac87797d97de047a6b5", "4fda2f855ab08a8d4dcba1874402e1662315c872e3ad55681fc4d6c5a89665a3", "b0dc69204deaa17ac4e0f197f8b23211418b5d54f5bac55414445a66c57fd6f2", "209262521ab45331639a57523f2e3bbf8250052b84fba81c50c990166a6f58b6", "b02857949ebddecc58aaba80b9d635ae95cf71f4bfc5ea8fbe05fc55d4c73e96", "5194133163b28182a261ce0473b1f3ab991a53a08d0e813d3bfb533cfaf1255b", "c56fe98848fe79124ae1ee09d1b214ee87da51c1440134210c67fe15bf6d1bb0", "851d949ac91f439ec84f07c481598728ca93acf79cb6505bd77ef776559275f1", "eeccaf0cd29cb002e2140cffa9fe2c08c53ffd73b99167f4b5e6ab5c94481066", "821f1058ae54732723937c5ae535cdc0a9ce673eec7fc02bd03c240c93aff24c", "de836fd21ce91d4a6add661f5d259d0ade4e0ff927d03f67ab5d0b24bff37242", "fdac0470c61d81d1498e4e0c6fc4ca5ccd02f727413e33c84478ebe844feba13", "469b4f5af2b2377dc09e5824af17c57f1dd8fbe02294059e16641c1307eff125", "b77348b40d52d531378dead61cf2eb6fafb4c89f85285a98cd4b6032c0e30a16", "2cf9616aefee83eddb2df0dda1a3331185f0b772c3a8a62ea3ffbb325290f32b", "2d23a9035ec627187108b9d13b24134d69ad7cb6f77d2c3ab939db17cc6f129c", "4925a7008584e04fa769661dd9eb766fe2ea3b66622691249142ca155423f368", "69090019b3c1635da9d9e4661f55863cb3ab561bcedf2632360745e62b06afc5", "5cecb744c3e65889c22e14a58e42bb69d068c721f1c547c8c704fbc688c6c6e2", "2f7371ba97f17c64c4c487742f83755ab61aeb1ee537bcd5f16beb4440d0233a", "9d1e3dcad79b153296a67238771b91a92c430432a9cc9f7b2ad7667fd67b4de3", "e9a34ca0067dbb6dbba48e736e1d32337cca5e93f2b76229fafef501979d84ae", "4d5d36724a2baa0d73657a140493a9ba95e1de95cad74c9753eaad785ac18cbd", "d135fe3d44b6b0875c1662ecfe33556be0f1b39bc8279dc8730d5e9e351f36ae", "1fb8439b54ead68f72b7ba4fcaa5041f38d313d92826b57dbda299dab06ab716", "b96e8d59a7c1006f15b0ac10cd35c08a8008e0c2ecba26d87db3f08c0f6fc991", "73300dd04c53d270420023957c50410147ea4a2814085d3b98ef25d8d44afeed", "6941323a74081c1ee28846c4ffe3b4023b29eb3a3b64d0d2dea0f47349fc2138", "f7cebcfc608a982a3e11b3941abf482d8108a7d59c3719279563788173a2cc6c", "b76c687ff464c50b58e4231379c5105470264de2826574e8d7fc58d6889d0753", "f0148c800120bd34159684196bdfb34f08d1af93c74232dd9f59e2ca0a66aed4", "51e0334c027b5e43e7cd557e301bceb0189903a189dadec2a11c1e2d675e3e9c", "32a3f110862c9340106f2dbba85c8af5d7ed575635d55cf2af7637a59c83103d", "b35bc38a430ebd8c7584d0c90bdaaa15aa252b3977fcac456646e839746f9c0a", "87ea74b899c0b929e83bf31a8d146faea3d26140ea99a3d0d3e0be93a4d6eeb4", "e222ed1dfcf6505fad77b9cf2e3e38d0ea86fe89a969b88e729ebdf2e6c63f0e", "d5e92da54ae3432603ea96cd770f4da442f7dcbd0a4f2d82774a33675690297e", "01e372d5dee08beefd03317d0897d5ef1c5126bbfe00c8967ec9aa05523c5e25", "369df1d577f66ea1c93b58b770783a74606907713b14ad86b316319d94f84ac7", "ef7e648860a8b3490440f2a8d541a268b4613f4a94c0dbf685df5973b55f0e88", "f19f4b29d4d7b70abc4624c01a4ef7ab772bd4feae8cb33bb502f30a11dab29f", "8ccbea64791275ea047a3648b092ed281acfa21f62a4b50ed111b954e534a697", "d60a6b4846f218a8369db8deb45972760a1df33c7532d0ef1ae679ba0294216e", "7aa4638be336fb77bc1ac5dfcd3f5ae002aeed8c42bb46475f718e3c278f0097", "06a82a57d7951a5629a1153240f6b1f09c150f0b9b777d7c64a0a628e24a0bdc", "d23d2ce73e24b434f2fe5a6eef2b88eaed4e57848cf357055da6914bb234851d", "0dfbe791dfc86570004538c64195a7702e33ed121490fee5819537676a021932", "8e2a510bc84d4600f25812994dfd5b4566c281a153e459cc9460c006ababd093", "cf73a8cdabecf4323a194f3249cb5b1674037f779c747690eb0d9c9f703f7c8c", "a8999928014db24e80a27cfb572eacf902b50cdac259b5be80229fe73260ce08", "f2a13b90ffda09f999ca5d7f9a2cd171ac33ee2a9a889c70a2e2d454dee0ddeb", "a5fa0377e644e743a38f0b427adefab90d218ba8e9e2894fc1f1f71cd815a92d", "1a27dc6f452362eca3745218915d24726b72f5d6963a9c41a34b9b7a12aeedda", "74657a8b361a7d235d94878cf2ac2cf3e18dbd76fa1a88440e3be7ac7a8dc54a", "15059499248e579d66827fb6700d3c31ab3c1e824fd0b0de583668631f31abe1", "21dab269f60f67bbce69447b7fec674662bbfe2bf1fb998e164d44e92086a89a", "a266bfdd44a5969f46985337359fe5ebb6083b8a21cf310ebdf4a62aa16dcb89", "612ebf41822f25ab638867c1232596a83de60c5bc1a62aea81464cd87c50a53e", "7c7e8506946118e3af1f5c36f94fc5cddb945e6346a009d21934ea0a384778ac", "82cc3dcfa10188e9cee8d84a60ab86cef7b564208734ebe8d1c6f4fd583e5466", "7ec2dce8c901de5c5b5da218d4ca6c304c4a8691568631b1d9d625deab025e8a", "baf8884aec756bba04cafe11f82e84d5721bc66689a59418e24dba0471e5ed9c", "2033109b98dec88046390619d056fba7ab1e207591b049b5ca4e5ca7905a0736", "04337d0bc9948530c0f6bd541442a14cb8da9342cbaae84ffd21f49a3a4ff9b5", "95a390c9ff01592aefaab09d6409dd618263bd596d5134e024d2e04fc080f9d2", "c314b11e8ab0957c8c11770b6dd3bf9ba8a281c312f0c25d0dbdb0dab2bf6176", "9372c5731f8e38ca30845e277b499e77dd3f5fa442f5496c4bdde0512de1e922", "84ff2e4e6c23f0953aec51c9d8642b1d71c653731d7585fdf021e045ebaa0c11", "c4472b40a9ec2b01de30d79bafcff2cd4853edb77724a5ae02f4387597deaf53", "de59785aaed498deb953dc239d06847baed05797fe3dd2420a5c6f35a4ddaa1b", "9622558b5b744223868445c32fd92ff2ba0d9c56f5b34bbf9de7f3e26206a277", "80887a104ef050b442514ff8292132f050bfda9b640a840c3258f01893e75f42", "cbfb1b0ad1df2f84e6ddfa190362225f9306eb62a9f5541cc5deb5da781fa213", "b01734822f1598f9edceacfe3d828203c629313c7ea0f51111f6b10474e070f9", "a12cab7ec7e781e90a49f837e6efab253d896dab615aba3f6327b264df5b91be", "ff54a2a3cae5ac505347c5577e010f713411b5401bff7491cebc18b34592683c", "99529fea4b50b9b8bd91aee8f8a25cf88dd3612ede12610acb24e73a1fda35ae", "679c55a753495d26c5ff8ee7e9dd2f6329fe76bc3bba1324f27ff5f3ecb7f8c5", "c805e4ae5d2358af561cce2ab0ae13a83b68a80886fd11ce5e8200b0194a0085", "5fbec47c66e62ecc3c483c440f0e39711f414dcc8c0ad72b17325bedb8bce577", "c8e43b97b4aae188ac288e16f856f16e839e67ee149d8bc8f8bb6aa05a186704", "ff4748fce9a654b3876905aef033f19030938880da461ae9e05bfe84698658ff", "c6e39da9593ab92827ce0e81d29fd85003d110bb2e85d530769eaeb0b3fcb122", "0a1cd405a53aeeb8c03e69eda64aca2dc6df3d599c41551e0e71067c2c3299d2", "41a3b0883541b8e28e321b9cf326c99f07fe0bf8354e080539511dc27d382728", "47f3ee76ee3a53b8b6c84de48dbfe40d4487c0f1e024be7ad735b4cb01b240e3", "4605541e0a8b64ebfb694d092456455e366312df0fdb6edb975d5df6738d5f64", "f140f701e73403c39925a8ec3bf6fc033df1de9c5d013a0b866b71808f77c3b2", "0a9f71c5ea3656600032d72147b1fb795f1ec515eb0c0e9b142a51b63ccdd236", "773a797fa4bb49ec882c2c972b71e509bcc094b89083340df1ebdd64a68f6045", "bd004ac4dc73dd5304e33abe88de5b3889f233d1b27327b14814f2941f47131e", "5c2b636057904e70179efc5366acf56b238780b1bd50d5733f3cfd06e4a894f8", "30cd462a2b16211e365728808b2dea5591fdae5f8e7f816300440e255839d9aa", "388cd1a37c37a2e7fc75da6363e894618c7e011f6db275cf64011312f3d377ed", "f88beb132412107250f73babe32b820fe6b277b2cf21035bb4c36e7b60a9585a", "c38eb4323358d7ae5f9aa8d459dee525427a9a490650246a2e8104d1346599dd", "212947c08a738977407b769756f1f4d192eca956b07413bb3f702402aeff1307", "c6bb090f1ea6e4350d6e71cba3c096adca356ce16d997f48dd081eaeeac50267", "2da0a61f2510fe2fbafb40b27ba5aa8d0fac8254d7d69e475fdff6f3777b4d6a", "785fc19dee1f3e84307dc836550f5ace30b672460267751e6fcd5e33ac46c296", "370020c80d7e1f3f53566b5f51931a1297fa1a4efdc81ccf7c5ab72e2577ae40", "259bc6129f4c136073173a83e0d5d5954203beb997ce140d8f69d7b950e0187c", "11cb148948a9c92a2c962f6f2da0bc9a024ce63c12e62aab3f0693847c23ad0e", "a09df031dc5d362e71b730b91a0e84677353406309aa06fce96f83eb77671b4c", "046bd72f9bedc26c0ffa2bb7bb9679b7b1afc7c9cc72a0de2da2fd9e9f08837e", "9ee8b7df8898711a797fd8816a32c181e641ae77f9d04f69fbccdcf5916cb668", "98813c8870bd227cb607e97a296195e673829e66f6c18434e852f36719fe823e", "5ff5c13d156c6c20c0018848eb761cc24a1739b1a2964e279e1841d587ce3441", "11caa777f57c824055e6cfec2281deeccea4cc6a9a0cd971ec1b9ea7de49cbca", "3a8e126522f84bb01239c8d1c51bada77fb0e3e76d51ca82245cbed04dcb7739", "860a27fef1b6b537a6be688753599f84f29a2600f462bddb5180f0575cf10bf7", "0bfb8295a95da4b08f084135ce5b221f4e5ea4cb7e63d96410e1b0161f0eb5ec", "684b917015396fe12a0b84845c805f3e07534070e1a0410bd6319f40704fe392", "5809b9f126cc43329050dec45c6ec7215c588ae85a0647a23816a73e2eee7e8b", "21ce0014bae97d4599230abcf322b031d49fee0f48e578f173b317478f0098a2", "79192c7dec85ace4a9cbb6daa82e76105d10e988ffabf1050a0b27e1eddc706b", "9a4545f77055b0320345d7f147adae0552191e0b77ba53fcd82749b5ef45e334", "e154afdc575fcfec7acc74e634eb767a87354b7e4c9277d6218174919f21fd7e", "12c94ad4e5fccd6a8a24229298b1aee2efa0f231fb209aaa4581a5ae970e4636", "cd089347c67b34ab0d80db569233b6f42792d9fbb08eddb769c5d2c06c03b78f", "c95de3ac861cb2435096b17b6a6e96880331ccfe730b15fb14771ce6414fbf36", "b355cc801fd8712315d0247517eb2ff1ffcf90ce66e786f66c0b70b05c3aac13", "ead6b1e3c8ce5380567394714a8d3e71b739a128872a4310fd52ccc0cd015bca", "b2aa10099a3d806f3b5fefc4cf5aade2c91e518a93a03eff4b4bfed37aa98bc1", "ba727d2be80bdb3b47b860b7588a46ac93984db5de47ee999ad946aedc411a3b", "5de5016468e7f8b981bd5f1b04b270eb7c5ba3665481b9f2215607137c5d6ecb", "44a38331d4f01c48fd89cb306be7d40910f61e85c01efa64be56007e168eb704", "876407f1f2289e2212c3f09fbdddd40e4d99331e618fe1fe76e54c0007146cca", "3c12bc0d8d061735b0b03371c4869f9ebb423eb84ba6a80bdddf863601287190", "35426258f74c650aac3cacfe5294871a989306eec1f93c85f34648d3e1e64b57", "24b0f6118578f557278af2deaea6bcff73b7c1fc2c034f0529b804b5a3667f7c", "a853095e6abb3da36dab40eba98107044c9bd706a59569c27df4956af6a2867a", "7bc75c278a522c3f2fe32b83c4e5ac1f002b970424ea9534ecb70519e2ffe1f5", "968a9fabed55c4ffe4df25e7aa61da56e67bb39f407d6c138d8949f0ebd2d654", "c01b876bfce242254ed98ebe8999d5bce9d6aa8a0afcd643f192c9c58ba05697", "0f25ddf33af868397a40586b9b29c759b5f48c5d5ecffd65c8025eae40cd455c", "9b2aa176b8978b1a6ed7c1a7ea238fa59414085797fcc91a2f0bcd4ba2a56b17", "454807437182e5bd112654fa4dd079fa0ec3d701f61075d1671c6300e77cc3a2", "dfb43a5c2c31241a80a316403612fc16007a8bb04652eb3316bbcf1a0f8783ef", "f0c2b72b9e3f3e0dda04e2c94ad826890cb8fa891b519b63a1646fb00690772b", "8fc8c2fb737c13eee55751ce1dc798fa291d428858e1cd862eabd89507dd0f65", "a84481a8966b29dcade6a3e58692ad8868a0b729eeeffa1e25cfc95f7b3912db", "91c8e0ebbee601828719aa29d7664b5d94e3501f3778999c60a975ea74bb00f8", "86862070933c5b4cbe7d1b29e15c728766079109dada7f51ab02b03796ffea61", "2aca32ca5da86a14878e221dd132cf11e9f858a1694eb66c29cd245ed49a81c4", "621a41b83f8e9299fa89f2f5245ccbe34ddf352e1270c6ef094161708f86edcf", "23984583b0ab9321f11a5c054ca891c1b5940ca0ee0174a701ed91d8f7c52d33", "69dc06a85efe0e51884bb0e8215d50ea2d2cd59ff9708079e90434bb2412b217", "96bd0d2f1ff8360f4846e79d20a31b6eab3705f52fd737741bda0568e629acd0", "7df4dd373b3fac18a0ec775c111b47f96484f3270a6d5d9b1455d4337c031b62", "65b585500d0e4f021bf4f625c7f48bfb02d32e9e532ec9cbc0c264247f9c9446", "28e2b11230c728131c2312f86434b934b1e34e985c1601fa17740b7820775fc1", "f1eec6722e3a8a3626a3b9cb45ce9c80fd08bb7e71c38d7b637aa986c6206273", "cd5c00f5aa138760efd51fabfba83c0964c47eaa2e54f95b952b437ed66a5a80", "16557e57e3b29f120e52c5d9c08f07f93340bc79910a29953df8a4fcda6b745e", "683fca73c707ae662b516a2c0e2793e6a764b990af2f2ce8c3151ea75e9379af", "b77d4a94dbc5ce109210288aa0cd3edc83f671ae9a9172495e705ea902ba90e7", "5506fe1e6126cabdbfdeb4cb59bf30bf21edc868046b263d692345649b3fd6c2", "e94b83fb44f81d60f82a9844edb2559563ffc876bc584f4fc4e11049237ac60e", "395cc58f6dc01018cd334bf6ac29b8f5ec3385ec325470b408bc2e8d9af11755", "3463442e45c1c1df952e9760f91b99ea8a0fb604b203c27f03a955fea0381ceb", "41f4c041586f3e7468fa44de1ea745e3d41b9942dc19cf35b5565978449a78dd", "31b31a285469f516015a5045dd8434642b2f55f19373b9e0d5530e843deeccf7", "943b282f0be57bc8c9b5ad4f47aadfc0a439af58522a4495b7cb36e0ad43a6ca", "f1d7d6d9dc97dd43e3b76bc13c6973e31572fa1792335ce0387ca171236838b5", "01cc0fadd0cbb9e8aaa0dd49291e39f3f325030943c8041178738bfb662a716a", "d96ec821e29cbeeb8b9f25f7123c8d5d708159daf8acd12e7a800c72521a4efa", "b5395de909f1cade846176880210f4a560ccd3180f8b70d2d4bf15325f196ddb", "e447d8ecd54443d4674c84cc84763a18b9161c76399eadaa82dd74cf31535064", "8f47c23e998213388a6abc7d3b5754336bd0eacf4eb545b0825abade1ae48feb", "b2b553a0af737c3912207071469517222d3d3704c7c45bed01f3cae1b50c54d4", "ebd2711b2330377b5d7fd2f39a720b896a7eef7d7f0ac2a1d0739002a1511a00", "d62a3142e4c4a2c87e8014012b804805dfa6f7d5da1a270f7c3401479a3b2f51", "0142c36fee839b588918bdadaf8c737f91d61b920dfc581e05335f6f2cbc3310", "e729c42028460ee33d01a15c2e369048bb79f8ddfd70a22dccd43b1c58d41933", "6fd227ca8a63cd5aae1cb590c6d3baccc3518306e22db68095de25f0ccb4b49f", "80ece14b164adb418170ba9feaa4d352cfc6cb1e31e47b3239163d2cdb54eaf8", "04205ac29beea2aad32008fe47c9acc02e3ebc9f66c16db685c8f0976f3562aa", "071d3e6a4659c37fec52601fe99ccb4d2a2480f3a4a7bcd16f12ff21fe84a666", "57f2fce9dc52bccdec3de4763a02e3700d13953003190d560a8ab306b81c1221", "076c6ea3b84d7f2535d034e5371378e9345dee62947ffe4de3185d02a2152340", "0e386ca6f2161a1c64a4072ce7a507e1131edbd90446723d84a41dcddaed4324", "48042f945a825bc8cea4e8fef1da5c85b252054137adb5e123dbefbcc189db93", "410d27dddbea610ff9c4e6354b187fe8a2f7c5b19c5563e2a1bca1a4b4b8c6f1", "453ce5c10b3de7a4fd1b0bd5f96512d05fba41117299d588a4740585fc295590", "677e34874e3dde27ba4a987778de7b1a64b6c63051f3cfc774ebd4c3fc605b7a", "c9bfc40e1be4befc1b44e38b471167667f6b12457d5c82662ef3a0a0e9f66e2e", "4cd169e13f4aca41b158924d9f1b972aa4d167d6d9c116e7094a7a06d96e6387", "aad5a84ac08dcbcd06b4fd5a0c5d2c1af8eb0d6568f17b3d8cc47d064b72a3de", "4d495f70907d93c7c1142990927f1a3d59e3218a34db881714250ea6e9aea84b", "8c43d66f0d23b88c17d19aa01c64ab1d2af7c43704952326129b0dab4453cfcc", "c12581dc707a3a6da47886aca1c2aabb5babcc0e0fb21808c27c6d5a939841db", "2c63aef84a0c812b53e37656cc6d5e8f64f8e4f8552e4e502dbb1aa0319e13c1", "86886a41f2639a791085b6a2be4f2ac4f76d951880eff5cafc722785ab4d64f7", "73bb646c6363f96e1ecc19f5ddf7df417327b9089c1b70a867f799af03cb3d66", "ebe518fccbdf53bfed56fd1f8f3b114b5849a8fb6e14ad7bf3f2a2baf29775c2", "db82684a4b314c554fa6139c4c7ede0245f68b32a885c819efee12ab0c027414", "5a985ff0be58aa5a46a0f4122cb70c7ebb937f7802a33a32d8262e63b3771796", "938ffa6e22fccdc71d6ca1544cece54518b9fb75cac5736a0468420cb9f504b3", "4726ef072888e9d5ad65342790b285c7ff024d60b084c32377eae6faf67db536", "57292f406904048855148e3dc04cdb08ce05a58f174867de688b252e448096f0", "ef8e25e005dda6d6cac7947006e1f688c743efacb7633c34ebbed7f87707a3d7", "b90e5ada245515dc90c2fec028ce8359708a610927c3f9cb92bd93eff2fb59de", "32ded7b174c9528307b8042692bd00480d31db9683c9476a4f50085aa6810893", "532a40b49048d2695ab6ce15572377ea0befb57bf6311e5bc89a3b579561837f", "587782fd3913fdd01f9f475f25e0704ab834d89fac46a0be1d88e54de6b50701", "b91389a5cf8a1c10e890ee4c740fe9994d48e999b59a2c6320397a389ec7a316", "6e737036b6c0c9d72a72c8545cc835d4cf7da70c5ea33f6c6003fb844565354f", "2f239f75caba3909f2b6f059a782c2624a71b591a7e132ef72b4add3c9c2d738", "95d4dd64bcc89d80efe84c9fb5d4a17ac7115d1b38a0ac0262e7687905eb1c4f", "4487d612260e1a6c676d2967cedd84cc5adee2ac845ab2900aa193a1b86fade2", "97edff35d1872b6a95f43606f084de35aef0292cd411541243bf7336a905a938", "9001c5d627af968d68f12200662585921aab14619935c8be4775c457e2a40867", "ba959223c1636c7b0d10b43b78c1821e7af6f6aee1f80337c555a470867c5ad8", "9f8b4937db8172a5e01b31310cb3b74824910f9c52c356c17035d70173794089", "1750c07b09dfc52f0cb0f09f4560095db135127cab4c511c525f560c42025abd", "a51ee98093bf11eb0455cf106b3a4e027135e870e3e5fb212c42d62e190f153f", "35501a82a47804cf7718d6bd2e4bb6fd67d7639984eade0c1232bc2c74588343", "9c3192c2435a9cf815b717ecbc6c539cac03c7f582dbda889b39485895f3e174", "ddf04cdfd5366d08b5886ef736dbf547a403f583cdd7c089f9f3c4239e554210", "2675b30bcda3da6a2cb6837e614ada858c1bddbd42e6c3963eb220c290fbf967", "dbd9134ad3f09406a76eba91323ab3ad2a4fc0bff4975b2cc480bd4403ac7560", "2929520c43b14ce24a94bf56870520ddfe4d29bbcba0d0e1c4624292d8719832", "f71513cd36ec057435881587013b2fea181cb57df1cd9798e9b4bc2b0457e778", "b83971a9cbba7903239a1d2a5907351c61028b952d4dd207dd49f6fcc9abc13c", "c3b7e679bd4d0dab1a2e7938b0d5cd8c28200c5da9534bda97ea0f1ea81c4aaf", "77ccaeb09a35c5a1df5bece681062f6ce9fea08bbc2c2075ae235946e8e1d9d4", "51001f07d1462cd9312b077be915dfd5225b85c3ba760e2a414275aba5fee655", "ab0f6f8f5e58803093fff168c38de2710c2aff8b47661eaa3ae2a337c0e71ecf", "96e9ce518bea74432b7aa4c857b2e2423a4b3f48275fc4b48f87caec87800b87", "60c0b7a0ccbe7792b9332ad6072636d9790ff736e2d83a12f50e7dfec65a2680", "38175abae6191a78d957e3c63121036688cb6b8c46d42d026551ad37a6aeccb1", "48d82a8ce43a65f567584bfe7fb28cf8c84bc725c73413b8768d2e6688ae77f9", "18621d94f2733bf9289e0353f066c53d95ef8dde449b2e160e28232caf17df74", "e86c65449e6b871ac6886526107b8d7bfaca468ef270172576bd9f39fd208aad", "c32bde208f9087259fab6b053db25b1b136b38276942e2420482855a5d7ad17a", "dfb55a5293f934d40ff7c0a6749aad57806e571df185f592044e69e680e995a2", "8c2a1c5eea4c8dad313bbc6beae0c4d94828fcb2a4877b19761e75c74fc10164", "eed8a70bc0d94fdd32629373b50eb9ef830282b42dcb1d8b96fdb9b8a1797df9", "2c4735a60cfae0273c4f309be579a51c6ebbed0200715a826048b1ee568d4934", "f7e56418539529401d0780879ad1266aee0f0354da07486ceab82011a069deef", "aca86fb3d7d9fb64e920ee5ddccfa78227a0a3a3e40bb3b275f114186e488c78", "bd4b2c02f07305164010353383415b08f570fbf3fb297df74a38d6f6e3ae99ab", "589908e264b0c91b1358f1a51f020daf473b7e4d5faf493b3625782866b476ff", "70360b520b95938174c5b0c2400da3b047743e60d837bf567767732d748e991a", "a54ed87456ed361b714da5c56fae7c4cfd92f8ac4a6e8e901a565241a39569dc", "9df7afdf237605066f98cf95611f49f5c5f383a080c86dc3753390c5627efca1", "6281424793e144590ddb68a85972c45272a5ca39227f9d24d0bfe78e2bb82580", "13657e27b82c768942fab407deeb645ecfd958f506a6e02c95d119620cac86ec", "cc67906e35cda000740c83f50b24b92bd04c58f2a0c45580e9a134c284580804", "44e92cefa2c869560d185d18baafa780bf16f148d1a7ea186f05597b18783606", "8ae261dd18679d8e203e7b4c8dd241a51634a84f83855b559f7ba55728d9c9de", "0269bb4c3079709fb80f3aa451a895b639e3b7db83360a14f078f26816979dae", "2faf079e75b3e9e0298fb15ef8c6d53715cba427c8c551e98d44a3c46a67414e", "745a15e40bf06483cf58188b9c7df99e796754dc4bf3eb0547b11fd8016c5c66", "70dbd06038f269ead55d560b7f960d24c7cb3a9c8864fe68c0daebf315cfcc9e", "1dda0994af0142dc5f71646735ed3bbdb4f6eb40955836db16fc7524eff22ed7", "492af127ff75fa55f94ed919386917778ed9c51e4cd193b75d82524c186a1b5d", "5031aec77ba13f73b21e5cf92708f44c0edfd1081c89b4630a0ee3a50b91794b", "859b7197bd1a5d6b8dbca9d6c96321e706708cba23866d44bf3f014deba6a4bf", "3108f998d14696b3e945569ca9b47346b26f8a3700cdd444f545fd0a03968891", "b7cde7af47f0df23419ccba57da19a5ff7645fa160e136d43c827f41b460decc", "18cb7236904f9784d611eb67b53daa31efac1a8a9a7d2ff47dc34255ba276a57", "1670703aaef6d8c722bdacacc31a80dcbac0326dcee64becba1339bcf630e330", "6ae67bdc91167c7efd005be6881b58d24abde9f8c3a71e6aecdb8e6738f3d169", "3efdadf9ad79dd00eeee1d80e40a8297254f249a9dde4b4d94b656d58338fc5f", "d14ad9887a66067658afeb25a64866bf90debccb49cb8213184b807e9f1284aa", "7f2bb055f5dd834bedc5ba9d63b3c83322e4325de7866b2af7ff8692bb2b52ec", "729e0ab27d04bf1c14dc28c42ea56cd7fc1a8207ef207ac34e676577fc32006e", "3aea585e172df036a10a0a3c26ebf4705972eb3efb5b61602231b8a2b2942b19", "a3b01753e934a16eea44aed4a756b7582aa1b469ac462ccfe4c92268705591b4", "d5af668caeda6f6af27a778359ce9196ba091cc04d9f9b3928f8f5203fc3fc88", "a6319eb545257cd4c849e2cca4c6faabea9490eafa3723434800331f222b86fb", "a4f001d05640267e07caac4cad7122771451f3f997caee435965cbd19e64a621", "f852577eacf926a5db6921da93b4a78f00f57e06fc064ac02633976e35d9e00a", "c48da9db46193fcda552476b8c08fe35a73ff1bc1950a41f3b1ec098d2f75a47", "7b26f8d832edc5d6c025be9189216766b58ab27f59e7b253d0ece4d28f51e2d8", "cc5b9121f74988f1bafbe4ebdb7296d2255a4af6f01f6967c7391568c32377ce", "29fe88933391cedc886475d8aa7b68415a7f3e80e153d8837cacbaec3f47d8c1", "392cf2ab942625fad754d738f33732d3172f4213a8606368330f72373ec99c64", "b9ca5c8d1d64334e586ba1f0303d3fe802a03eca9c2aa12d2f57e79836d0b64a", "c47d0f78a14f36ea4a9d1fdca74596a88f93dd9a0e746d97c91a79762420390e", "74a1f274dda992663e03a2a10f29c84d41e2e202bf56e658c1a42ebed46db202", "dfa9dcc132701d8b1f4332e2a6bc7faae3c7cf11ac0909a83c4c7e30fcbe7dcb", "35d4395190d570f8288d255533eca2fd7bb13e720d6e8f5a7113094f97538c5f", "70a16244e7480d092b617242786deee67056d07cb15365fe51d0e8ab1e8932a1", "a26843f48f4f2a218b8f5b219147641ca236a1abd96905d8534350e570b164e2", "5d9eed350175b4d1217b25e671c2f3c9868c8732b6dfa80e62e4a9bc7010dcf6", "72db3913aa066e04662cc170f3363578fa47799b64561d3b9e84598b43ee8c26", "e406db4deb9cc79c8eb7d658c382c2291668d7917d73c652c415f37a3f713b0f", "a0faece933213756d22239d1a066c1730fe58b3e815df52c2de1fca102b03caf", "9d6bc10478d9345260c53c40de93ccd7b1f344dc25e6e4cc8199e1ed9c6dc824", "ff1a79b9d954943147a0b29d67ce6fcae1f9f8d5476c2b8eaf78ac575f95247c", "ba31c30e4a28d5ad22a364042b7155e5f4ee008929f22eceb3fb7371d0c1c2a0", "797bb553ef79e09eb1aa5400a889bcaa513583662c3708614e29b202cfc3b80d", "3df07ae6890b2c332556c247ee91abf341c5dce226e38df09f7010b1c21615f6", "30de2051725d9f0fc371cfa55aaded73b12e0668b1624775b657ae0f41ed8daf", "035e448afdafd5069a783abcd6e268a82f43a52d9ea805c1141d329557d2029f", "1cd59a8ac8c61f8f97cfcd1e43d633f41f0b3b3782e3deb3d0a9d80942b52077", "b1bd938d8288167f4a985abf342f977cfd1c2f1da70c6037c9bdc4295a705726", "418297a2f0c0e5c3d6b2c4d80824e1a909a61fce6c18bc937720eecb1ce3682f", "06031df90b06aa84d58da9de78808f7b2cd7d563f41dbed683e74bcd7884720d", "28961517d508b8e963f98272dcbe636af5f99e6fbf436d14b9b64273b17857a0", "bac113e3e3572e90dad38b0c2b32deb78f9027e59b75db03d0fb86c49c2d6d9d", "26a5e2f817b0596d95c8a82cbbfeec6971da2247ce1cfa52bc5098ebdfd3c084", "ba7bae49a577e15e14568cec5f779c4700c8ecbd21bc8cfbd3aa56eb0948dd27", "90bdd504836627c40d4c14d54da1b3dc5cf5b6b1cacfe2e220d1aa44850f6fba", "02f1553ab9b4f4486fbee6f5735ffe0d9b305feae9a120df2ea311fde4cc6076", "2a9ec46cca5184106d4df225de39422136c6cc995fb9d124bdd640ea45667a13", "28a25bb686696fcfcdeed1a996ff4f8956dd4c41587d599eb78a83ab6b1358c8", "422bb78c5107f8f0a5e1a253347a72894704cc4d8d1f60a49a49f8c5dbaaf298", "74f3c43fcc95c26354129e18241a1e747c78975c4bfbb0b90a2b67c117dd85b5", "8c0f5a2aeb81ef4e5805c1070bfb8667ae185b59705c3cab2aac50363327daed", "87deb9c6b62b237a5f83b7333776baeebb4eaf804ef78b9ca2c62ab92388a697", "42897cf080c2e405a77fd501360a7a86d0a1cb7d573f5fb07e094bb13a942f03", "0d3b80df67851ee640b906d761fd95ad7e47d0186cdcddc59a10a22e011816ed", "dd222577e63a176e688a09834ba7dfbc7d25af9cecda7b130e48a25fec558e2c", "f6f7bd7315404bee4a9611e69fe5d3387de5e4577ac28267d04d69946f42f18c", "03cce690c88d34689a3fa66b6f8c9da75747ed568e63fb20715def88e7228b38", "d9a4eced4646f53c7840f817b4296b5bf16e7b3d5e906953b6302d7b8a848dd9", "319741447aa9b6c819cab13368125a52f3c35d264249d5b4068d2f379010f4d6", "0a0f3eab30a538a23ac52e4f251d383d418bccc96d5975446e093cb424e8c247", "550942f02799dc998561d8695fdafc4554c5a89f12333403cfd7c4c9cb15bbec", "1b0d7536d6774149b4ed8db577268f176e4c1f76e88c9f956d51577d7349cfa6", "5d27bef5a988fb678c4e178b4b1063c4151c5d3780c1dff1ec2ca898f8f8cb5a", "6bb4b71ce2a72c465e83586c39a2c1d2f77a47ecfca14b45af365a4ec29448ca", "938e0c409a837260a9fc27ad5878f3b8936ca0e6219ecd3f9bd4bef6c402acd2", "d8aea1404c3d5fca7289e2512982bda873437b43e7b8b2a912f383340f821c8f", "1f4cd386950035ca3cec81cba5d6a506620863056da90c7dc9a5afe47d0d9dd1", "dac066c881d458341c7db30fde7d9197e498ee577bb4f0e0e48fb859f3790143", "09381cdc27896ab6c73c341673a61927099eaf2d300d3e00ea37ea6cecb262b8", "65f65598a48e7b2e38efa51d454ef1f26be016c6a70181e26bf35921998671ea", "98d991cab4e708f9281d1f56b1a507026a114ab0733ec2dd572bbeaa22fa4887", "1c2a4e2bf0dc9a09e511baff42c297b321cb8da45c18ec50e4c39ca2465d7cd5", "327c7a6d05d522536e61aa1fbe8fa19f781f915e20a66a647ea90abed8879fb4", "cb46cc08d32b5bc7ae9480f30884c7670b8e8694d66d5438e5f8fe81785dcd1c", "537fa4c41690903a48b7a632249144f154c5dc4686f51868df0159a0350a4ea5", "75a5e4322582d7e240de8e8b0ab9ad73b7e283428537338b41b35107dd63ea2c", "1f87054001c06863b66f55b3a897ac0d76f361908900b30e1d8ffa46742bfd16", "22197f4735d51aa39ef48c88c4d60818245fca73b98df8b9669dc434c6ac8796", "a2e14dc37362b89a5b85c57b3b48169adb2e6dd5360b8030de7a0e028a6db3b2", "676f7706eb7a57397f6c9f69de04cb037d3a1045281b8ad8390244b9afc7a2d1", "8defc187fb1f0d7bfea657619f9a020f303f0cede255b473d18817b500b94b75", "be1166434669922a764541789705f9d86af0587241cf3da9e33a7983d048177b", "c5adb9840c2cba41c6e49f9e97c3b78d8d0a1c4af88929e89af205f75f61cebe", "a83b4a5b3282ab0a2dfa4b1620dd0e3ecefd89cd43fcee45a1a6e4760453e9a8", "ae2117b3fadabe7e3d94153da7e68c6d7b371efc20373aa8e1d9326ed9a3b369", "a0b5970a81570a1b2b4d058b32ba5f207273765be398986490ed5e9109d07863", "9ea221fe02ecd3c974957ec24796afb677672fd1ca770a13ec9c3a94135ef06c", "a8316aa74116d533973b74f528dac5bc257a3e9cfdeae39db7d8d32f38085f4e", "efc5250bdfe42346a1d032ef4c7189cfeaf303af28a12b3be074daeea810b171", "9aa7194fdc5f39e9ea59a13d04158913df4c87ed385b32a37f216c17abfc69c1", "a17f4cce7a3aa86d9bd5d51f3c38f235fcc4b086a746030af939997d05e54fe5", "98b049494b468b0c6cdb3cf382283110668d919005678e4e8a5550a892ce133b", "1ff264905c3f040c3fcaa107b7df3c38ec0dc7d59ddf9ff8780d6aff0381da57", "ef6077b9e143f01f8b500e2eb6b6ff02043ec00befeb78ee44db5f00d037bbf9", "ca1af382997fd751c70fa1fea1cdee6ee1d2a22246463ed7867d56e57619aaa5", "be8045324dcbd46d31a1b24be314d5f0ed7bd1d1ca67bf71ba5cc43043d5c9e3", "70455e4b87d4b01585564a77a6a414a53338c05a984de6dcd14d7126306e22af", "5bb2bfe0be18cf76e3f70ab3c6ef2816dd988074d43389a3c4479703d1a61041", "3c95b917d6409a12360186d7c8839b33d6fb9a7f66f2e0e3a887601927d14043", "0259cb83d1129316ee620361341d083c43690ae542e5fec01f887acaf2fb04b9", "9aa9b67c720b3b2fe3eff8732fdc359ab15ed4fe1092e289fc27b7e55a9c5b50", "1151155d7be1017544c0c2b7432ea1f67cf3191baee64771e9364f3bd1da3708", "9c45b3560ce8419825ae84affed5223683fcccfd6e35247d1c03f4b988e8f48d", "a3242aa0a01b82c6d5faf748c22a616b950ecd30ef0f72685aa5860f9320761c", "0f07485d78018a506a69021080b41861f801ddad09666090e53fff3bff0cfa92", "e819c861150099438a5ef2613bbc8e4c854cb8410521e9699fe90500a9127443", "4e78cd42978462aaedb993b6a49a5ba1315519db360522a26add6a17c8adac8e", "b21ef6dd5976ca60b6e335e78e479a655409da184e68c10e0b4010ff9d208c64", "e8bd4c3f3e0a8345ae5b2b5748060b15ef0c7529fc3eff080bec1a9a77584592", "3c8d2c54c7d5d826498d730a289d36f903720b7e2ce1f699ccfa152999b5a0fe", "fb6e025eec367e2bf4b44af67ea674d767b77397d0568528e7fe3aa7574ae730", "9236e92010421a2c1674eb0a8044ac2b215b605c0b94b903f3a2872d0fabd344", "9ea25f2f9472292aba590e298fc5ff15c4cb22608b2f0f2ce1bf26e148920007", "d4d18a3b2db8540a7bf72e0cb14b176919f995e70f0df607489d5adeedb0a932", "e6f6e272b36731484782bcd4844087cf45678a05d8b84819f9d41f5376f0f8ca", "5088a2b878336dd33c3a7c55c09aa70bfb1d34815f031d4b3e92402c7633b400", "3d12743c540c798ec2587301a3fb2b4f0f6e1278e4bb15280c247272ffed0651", "52c17f712792472ca80df50f7b9f96f51a6eb155c872ba9ef460aa6d4e10fe39", "b97f17e90b9fc70044f8789379639e52f97707eac2863a35e9a19376555f52dc", "19701f39368b26bd3c71a2f0630b5e89586f7249431843eb6c890045f7789280", "49ea123cea990f6fb2029e8cbc9ff7ba7e049c32db1f6519306ab980d74d0d38", "fd574068f0c0df88faf7b54341a310446c0ec94931bc459748e11c58435d6ea4", "fdd6cc2c790b22471f03a32b906635b4028debfd691a0a57f847e15061a2904c", "b7a173017905bf55dfe03c1640a4e808dd6a1d6bdaeb27722a7c839766b8465e", "74b799aae53dafe2131b183068d8cf5fa8f2a3006c9bb9944aa493c7491b94cc", "cef9c06a87ada326bb03e6a301f53fe5fe6d68df015b4d72f1965581545c7fd8", "db390feffd9cdd7f8a34acafa77d80889a820c9275095e84b439ff5f05781ceb", "57e17c1b71a226c7bf02687565e92689e5c966f5c864e64d9a621bb6757f4f2f", "b8c8dc2624b8aa73874647bb89be2765fda8223fa7055796a59c7f4d1918e8ff", "08a2553e3004a255c9a4135930bd9f8724423747135c0dfe45747285549e4ea2", "4d4966d172bd8c367d828eb8a14f853999df1394fda96fdcdf5e41d70725ba21", "23888052d915017c4b47b5307d25158fd13daa02bef1d4a2c11bfef79a851470", "52a97f2b532139784f4a6a6250b2e61a3989a2c94534c2434041aefa13af2871", "73c82b469fce6ce8b6b2828441bd31b66784b0994e57b82d331be9e03cdccca8", "cdbb2bec43b864ec0d7caf5def1222c3cbe20c79d97c7642350dab42b5d1af3e", "e047c075c048467400806f61489cc503dfcdffc73d4b9b6bfa470427f95127f2", "82de0f386c63555542e8a34ece6dd42f2a4671d437e00aca7da175e7d18bbc85", "fee469874ca3fb72f0871a24f410284c04311446f4c5f04480d7b3ceb4e78efa", "830d8aa08ae29fa0941efc576cb59975d035139cc27213d0a04a0153e45207d4", "f444da313f6e7bd9e27396f9a95129c83977e1462f86e7a9b5addb1a7ff30580", "fa601478a412743bdf29bcf44ecd5fdedc09792c8e469a7399bc17c64e134585", "cec5ef97aa6a39f3c146c5e3f955bc9028798591d4e38094f38f70e981566d58", "6bbf46cb35bc96854a8fae0e20935f2ed32ab5a940e7891fa7f268d28ce5d549", "955d9741503c2e5244f513e2c2430bf814201a2d7dc74e2e5c9c9aeed401ebc5", "9f2e6590991e25b4fbcacbee5bf7381092cfcd7d4f3e258bf4b41b84102fc179", "647c657c3c930537bc13047cf886869f5a0699fc52496ab30c997e5fea1b3dbd", "9802afd3ddb4d5067fd0db7ead8c66ffb3ad1c29391ce56321c4b8f34174eeb5", "60f782f178f30f3d9321017b2c6591f25a82f957ef1c704c6901fe2fc92ed76f", "109992589b06b8eeba15fc2f6104140fec043b2031c8df3e9025fb094978ddaf", "091adb2a123d0cbeae7dd399a39f4ca4a3b68086410e6c7aef0526bb2ad2fb82", "64143c36d10d8d0659f9431dcf30cec804f4487452d5376639157354bb7ee637", "9602ec038d85b2cc617dbdbbff0a3293ec62048f70b16a6b38702e26b99074a6", "1c6b6508f0f0c772137ed1a53cb559fb1aa4b3690f6e1f6fd3ddbe5b74da7676", "a4df5d4c393b255674bfd64aea4ae82da5175732d39591fa671a233004d2d0bf", "928a67d956422b29189df8c6e88e345ed2cfc8ac941d06f15a7c24cf30bc5296", "79abadbacc8e8bcf8930e8295dbf6626e3c2c71b8c4c6883318dd1c72e03ecba", "ddfc0d445cc013734947279fdf7c6f0d474a622da65db4ab1c0c9cea7f60d0fd", "61ce62f67c3526d4183f74ef0d457216c7ba9913c9a0243944c972cac6dbf42c", "9cbe363f9bc69639efc73b9bc02264e29f7d0f8ea3b1f35ba16640a5767c5db2", "d7a25bfdc1e8bfba013bbcdc8afe41d81511e15cece155e9be7bf1ce81af27c3", "93f9632756d3b0d8bc72c4718dffaac5ef81630d6bd79364b7bbcc9ffbc302d5", "2311829f9842404d9cc2243dd149bdb26d210031ea78dfb066e90381a392e641", "cd08a8a153ded8be5d705390e3bf53cb56d7b8c20e0e08c39adb3689a68b9602", "8d310a900176ade581ad42108605cc6bf867f21cc115e6abbf2a5e083c2bbae5", "43c5cb40e94874eb80ec26b7df732cea255453f511992fd61ddbf4de739f3b35", "a2a9abf1c835b824a9d311105a4c92b3d6ca8eb2761b45da7241f5879d05bcab", "ec48aab645d64498938781156b6daffadc0ec9f3556b7e995c8dbd63299c3121", "05f6c84dd8ff3468d8992d9dfcb4e31597f7a378828cc0108320c009ef16ceaf", "d4d39f9d3724cad98bf1466577b79c4dcdca104ecb489e877fa8f44adb1b2ba2", "b23a123b0bb6c11060658fd14786dd345ad2a2c699e4fdc7c8de79b1eba41fc1", "f27d04707f4b1110ffd978f8610b2f094ac0f24c1dc819b59b70e1f64cd86a99", "42895aa8dc4c0ca50b98c7157fbaafa53fc3d8a5221b660dc86837eed7e6d319", "ea9f13a6e1cbe9c308bf85b50ddc729abe112c46d74b50ef53d0bd7ece84121d", "e8d250858b5de70d138213342a6765948419b81b8e8ed65b3763b20ddf009fdf", "827b1279e3ea50b1b7aeda4a7969cdf18bed45fa018e552190e8341d2b8be2a1", "3584a32e4fa98cc72c35e0050fc00f46462b7286e9d6ad675c340a8d1e56fed2", "196435304b5e92922c3453ad9f31a8d1b2821634ee6a29c07543b05eafd7b061", "a86b7271d28b011a2749b302fcdbbf712f89d9f3efa24b9a169e97e67a57e594", "d40ed1342bca6c536e736f1fa15aa5f5a01274b4208ac4690a4f8c293dd40b0c", "513256a2ae5c50af825420724fadd88aa0a77d93f64e1425f768f33bc56bf862", "83381a3fb9ec95f2fccc410ae48e0581ee4f492881cd0c20c90cf19823ffca7e", "0d51b0210f527afde630887455f5d231425f8a8aab5d8567e5ccd49441f5effb", "c584a68f8f6a5d8841d9b51fa9cff1a3aee73b1b4f8c8f378843c79ba5ce5902", "b5396ef2974c2a1040b8e8ff023a82ed4ddbff2b69e5569249d139ec01dafaef", "e52c0b2f5da5c4c5f68f4c1b7e3dc81e9572bcb6299d3386d54bf881c43dcec4", "ba60878ab1ffd5e5b85d843ba049d669ec4d0094330147c3942a62f0394c32e5", "e412b797b242a5619823b6b33008f45bb0b11bac0ff365b4f8c73c9f3fe6e590", "50933f5388c97812aff9aa52db014d71556383c63c6b1b7ce294195c8efcb540", "643ee4638b7d9c626522f9178bce2a53a875453252c46ee3ed4d524ad2710a4e", "e72b8739dbff60185cfe3da8783fd9af56b7da9974610428a11adaf5c433b2c7", "48c3cb8b5c7a90728fbc104f8b191a98119f8a2777c00f8c1000244013745527", "34845f23b0bcf4e5e7fac5f82c059cd08d9bd7cabb11edbd62fdf1b40df95758", "33bcac68cb4ae201b3d3fd356c62feac888ea3f7e0f59ff0dfa2fef97f1eb558", "778d833969b28ccda7711e0f6e37345fa598ac1a9fd1c6a497dcfbb0d2a9d590", "5fca36d19c656d347e71c9ca43df0d701852d9811b758d63b3ae6522dd4c0b68", "74f0e0b61425240202486eb26a74e53bdf8460203352f1c1adf698be9c01dda5", "d2b4e304a065b74641f42966a43398a96e85c14cb209ff06d18e6fdd8a30e1bd", "df6401c07b51c72f6ea2654aa3069fb6bf0d8a3adbf00d926d534400d88733b0", "3850acc410d21b19110d9f229c63d67e36e2484915693f21569b627b0f3395bb", "6143ef6a8f8edfb6b40ad2314c0f9595fbed1f55fac3b8abbacd72f691da7780", "b14ae396d6da8ee43a3eaf5e9a06333ce6515cbf1819bb5283d73a68cd39d2c2", "2ccb1721e1ed7add382cf8838f7cd82106232c7b0bb7fbbc5f36291936fc8f52", "cbde7da6d0dbf518da6923c7d82749def1260eb6632f03a7e3eaa62cb3a4eecf", "9a9df0550f1629c3cc3c539ec83ca7e815ab8c9319ceb91f42b6b9dfc3384ede", "f48737960c6bfd1b4631cd39048b55cad33bd0fa925a8ae094456466e16b7791", "2514869fcc6ff50736da7f509dcc55cfe8372f82beb46529d757c0ad98fca10e", "b21124fa2ab9868f3e7375cebd5cf95a48d0d62ed6fb62ef0e0f08f7337bb212", "84835fd51e9bd4624f4b6feaf2387bf3652f0b03efd56cde086079f86bcf9cc2", "868492cf4941bc0fd0ca8c37a30008fabf58e56bb3b41f7bd91e09b43914618d", "00a8ba1a607be27447cfd6f60447a22ff6e603e347eaad21604bf56cfd3b1434", "e50a1c9ab7655b55cda75ff82bc1d28ea48cc7fd292e5f7c72e0f48acee712de", "249df64d683697b530c6013692fba966655c6d4e38ba40fd05a282f60570ee67", "1e66d4f9bf24724b6ebeeba7f2ccce22cc039cba53b7e7fa76723f1dbb934e34", "db6767231847109ee8ae86b459f0303e08e2fcf5b4165faf7edc33c66909735a", "406ee377180093d25cc204105aaa3030473ab112f209ae1dd608ebe115a3f95b", "0763bf2c13cdd4525a95f123d5a42ddcc9b3aad27c90dfac1f19fe2cc643f636", "3cb4c58f6597a2e937c8bcc870bbef98fe4a2ef16089c94a0afcd0ecbbca140b", "1a448036689115f5ad50e0587d114cd77901f23a07070b4d18ae816256d8811e", "4bc718cc25242feeced0c3f07c5459d30e5ecd91011237dd869a2b1d32c390b9", "127d4282b45be11fe780f20db6c1737192912449c0ba6b44ac499d9fcf546a48", "2882d864f8aadec1babadf7ea312ca3774fd0202a4702779415a7296501e5828", "2c1a8fb6d739f4ebfd01044c2ca11b484de6933d33c6d120c5bf36475ab7b457", "d4224f53e199e315ffba0bb317dcf7743d764642d93770e8f6eff12506df888a", "b8d8b26045f477d58aa21e5bd835883ae1a7bf47e416032080750e80ea7b008a", "fad3f5f3c9d29a2165efdd3e33f0aae9e58365b379f0ac61f41ff8912f7e9281", "c05aa5280e7bb5dc66265a8862932aeb268162c25ac2be8fca44949f94ec1ee7", "af2c85d7085cbd5ff2760f744d22e1e5be0bb8db8817deaa14c06ba9e4cdf516", "00305a938c19feb580e7945aaf55f217d5089185176561c5896d3643551c1aa9", "8ac01d950862d0598424e3488ede8e9a285dd068c1d401759ecfa3c97f9bdc85", "33f3b9159541a44f2198e6e7bff59160bb52f81c35c9f80433992edb5ed0a340", "31244c0e5b1f7c934f92aefaab2e06b0c2b88c98576777d3e5c514a6b8ba97ad", "72ed3556b3a25c229bb436b6bf809173540368bcc434c74548373c043f4f8602", "00947670a458adcae6c83f223cc0b2b05cc1debeed514ea4011044ce375c8eab", "123376bfe0702b06b98915e38ad3c8d3d8d270f2c81db595922c298d980a7991", "b9ea637bee6f3f3bee40fb76dd375b6419fcce5fbab8523785d04b1c4956570f", "601b25e3e686fcc9c3470bdbf4fd2af9d008ea1858cef028180e3f62df0fca7b", "6d5a1265a95ee04afd7df5c9aee4341f31de35b9e87f2fc9e02d2fd7e0d5fa2d", "77bef4f6fde9b94b5397e63d1690c6bcd553ca53b58c2bfcdf92726590246317", "27f110882479c6cf64c0bb38d121e389d5ff17db4b216597c75151b78b24b2be", "3d1d9cc9b494b22ab1df806d7b1e9745d132dd6d72ba4726f55af9210f3df4b7", "84d60c1d787bc5d15a952183acad447856c0501c2bd5809145f8d8582c97decf", "b79fa13459e7f875488cf30ccd2f0431cbe8dffc671880c10cd72d7e2be7e8cd", "061c36fb310210ab07b22f39178b7f451d5142a395ececa1ec783af9c52b730b", "fa16976c19becae31248c8477ff0e746c4e28ddcea5ee36408c05be86a142471", "82235891577986898debf0cc0bab31fa765e925d01a27c27ec694103320d82a3", "39989431d3ac81a61b0311181d499018fb4cddfb74b1afe4a9260b5841135989", "a846acdc0cf349a8d2b352d3dfa8784893f5038c05277d327341d3ef7de41bce", "f3cd88ff101e9dcaa9e05998db425b590dc45dadfcd8b8a6bc0ac7e932372055", "a159443648d0796956f92ec4efc5aa44af0cc2fb7ba97de7e6a8e0dd16638530", "9e381ca3bd9488a656e965de17a44487f8c0da8896ebf9c0af4c0146ce034951", "4cfafb85f2faa88a88034c4e04b7a37be20eff7e02d3e21bdb79d5aa7de833df", "eeae101eeff05cb6a0dee3bd70b7999858b898b8c0cc7fa96a5e9235d1377381", "786ad41ea86eda551d0bfd3e702622e118b21e619c604772befe546e55d4cedc", "2c2f151ad2b9d7bb8f52dc4b060d194bcc63848754d0d2983def1eb992f194dc", "530b5035473e95e2bf117e3ba2d88d6de1e648f8672baa0c9dcb83e80ef47580", "b34801289f8a80277b7d5fdb602ed3df305d9e915138761eb20cdd42b338509f", "eff8301ccf9032fb1398c62896f8502a564889242c9cce7cfddf1b9b87dc9189", "1babe594d5c84b3e67237b6abcf14b9a091368c587958eccedd4ab0367601a6f", "b2e8b56a474d41acb1a53646d825bec845cb12c7b96dff588d6d1051136dae11", "7b400ad7fa14af9182259b51e810e16029c947f2509fb129ebe111fdd977af3a", "842d63a701a80a9799357ac704f2288ab62af3a62d476fd740c0f8f5c35a46b6", "dd146653c3aabc3747df891c3a6685d24e9cfe4d61e52f5c7fc7df6f079d59ee", "2564c5ffb78c4c132cf8c6dc06591661f2d7ee12004af6ec078af8aca04b42aa", "8c01eb1dcc1e13892a782e9826288711f28ca7c716bb9756e49b41c8d9946694", "f68743f290c5002b746d912702c1084cee82bdd3c323200dc0710381d98a41c1", "292a6383fd16ec5afa4cffbf7a6fcc8c6553d4cbd2574886f623b00bf12b1e4b", "4980e074baa3623551a56263d46933f5fca5465615467ea914fcf6e389e5eb6b", "4cf461bc4b7f8e1104cb225bae1f3be5dc70ea47a3879257d6652b42ee302a6c", "79f626c481d62c454a9a8e5d008141befb190c0f4e78c0f9796cdfd8b490c2d0", "8b4ab8a45964bdb5ab237c0e014c840e224ab1ef50cf2afe79f8810613de8c9d", "6daef9ecc84a1d29833c0edbfd38663b0e5b76f6ae1d5a22cb081984be8a1ba1", "7cf7620117fda4ba2e7e1392a39c2c0467e3b90ef96ab021f90708e46df97e94", "44f6020ce6f1831ef60cb293f456a5ed770aa92b1837fb571ecbf00963e77249", "b53bc8f19e29660d7c2c9622fc080eb3839eee4b601df47eb3ac20aff8ef8343", "114f8884785cb1ea54087bf3d19418129fbac44f8c496677778714743e678c72", "640e38abc942b35d60027a7ca1671ef96da9dbda8d3aac61917189e0f1613a1f", "23bc1dfe86d5be148155bcb7aea39b8cb68a887a07c7159a8832d7fa8af8d449", "8ad3f2e44ac576c4a9c364fe497b840bae3a5673a29e69f0806208499332a001", "ba11731e009801147b11770a0822e2f1e6cab3923726ed79efb3ed5675289c05", "409e700d67c2541afa301f2c09a4a98de150ff30662f25dcce0bec82da44a1bb", "74aebd9823146c25c615aff0cac7a2a7b43a3678fd4acdba428bc874c2de2351", "1ab29e97945c3ead550846ae8af77e6f02d77d24fa8d6af4a866c45568055be2", "729944aa7565a697548f162e0ec9f39a634fec17615a4b1b65c7b68d06da8ec7", "dbff2d93d089c5fc366cb89c702f99022ccc53ceb39418e2a9921b1f9d895c95", "170f0177e2fd6e2ad5e96bf1c7d5fe8443f824ca80c51cb19fe985020bac4dc6", "44321c4c2e53ab3faa16443e0dd56d0bb18ad444224c09a686285528c04333fd", "2af9827f953129f8eec520d1409be4d9747fe2213e877ccb06a82e9bfae761bb", "65831a1f6d27ecf91d452140be9219d010695af0fcb2ef3f19764a4f6b3e07f9", "103f4a32f26764273b7ab1abed25b768e7994a6bcfe4c029d2eb5a30c4e506ed", "545d4fd5dcc11f7c29a6ba552562cf4d23890761c76ff86d6940dc707368a0ad", "4ff9f091da95e9e8892bbe017a8fe29a05955c5c62992a78e23d3bfa4b3c7d15", "8e82f5c6062204966bfff0f299b26b5921358e22e0880a5130004280c418827f", "1a6df2e84c39918881ec151d620cc74007c0d122020f6c501dcaff8822f46891", "01ff674c4dc5d40f0a53318e4a210f418dd2e504077f80e640360db4d2470be0", "fb4b597769166e58a3b28a698f18ad0bd4c1e24d6c0e3cf58cb800b131f4fea5", "dbef3658df7ce530752ca69e5248cbf2832c1c458f0b85918f2a4f3666d7b301", "9b651ab03463dbfb3e7dff410e758430fe535d409805506018bb3f9ba98d726f", "0795034bae75b616aa3d94df004f4b80717c593aae42e0eeea2bda508fd091c6", "52d8998c0c3ea0a42e6271a43660f24f17e6201dcbe28a4e1374dd20758327b9", "a04159ad9cdb943b39160af9eba203f3aeff9bbfd933843bf6cc32f40bbc1f54", "cf250507d4d9f066221a2c5ce190da42e2c8e9afce5a539f09305af5074b759f", "5fca2bf5cbda4284eb2a9aa26b55f54d43e28d0efb97e429482a11b66cbc7f8f", "a740d86574c321a0d3ffec5124431c9a2e52882f85520f296bdb230778e74201", "5543633ba06069b459f10a9174dff488575830c86bd32c1da6724847791ea055", "8cb684f24f0a95ad5f4376aa8f0d9bdda6e413bf04a3c8821a547fdf46dd1938", "b167590ad1040def2161bb854d08fc62b8e4ff4a2d60376c1692c87cb2008e7b", "a00f55c70f539a98a23b51888c892f2b5a9b86328ec99cd56a11f0e5d8d4d49c", "73dc98bc6b3862a513320e0e4cd61f5021b30170a2d054abbb62e87036f4ea08", "ac0f7cc6fbc94a64b50565a929ed6aebd4c6c36000dd40b4f826052b60e98103", "e24d3edf80ad414a6e5ffca904a259c6a28f1058c0488a524908d1ca8a2faa26", "38d020a513200b0a6d7bad5fe1e87e39efc7f80b940698ba23a78bbe2cde0fda", "ffb2bdb644990f4751b4795b94784b5e3c00a5d40afa2b110822eb7dd0cf2d63", "40a6543d5faecc7fd797d8aaf091d5e4ddf5f075e7f4798b36b6ff2669afbfca", "07ee87b5c221a21104881b0a6255c2354abfeca80be635803a387a3ef9032f3b", "d3fe1eefcaa0d03434e6759f8b48fc50f4223edec547c94bf072d49427e2f418", "0ce4d7ed2eb07f798588df1df044d9e124604f0178ca8941e189854daf64f26c", "4e5657ffdeb3b88cee74452cd24a8d78ea33013f600d0a6e97c56eef47c36819", "8e5a2d6f8b4d0878a438d7b33ed8bb7c32294968f71ebf45ab51ba45bc3836e3", "0f81dcd7f649bbfdd0db6fc69ae5f5a7d89b99388e7d20312705ba07d16a4ab8", "1cc3486005fa6151d957d0cb6e2599df2680055949b81d4dab85562622ded07d", "78c8021936527768d5cd7e1dcc30ce55ab13ceb6a1209996a829e3cff8e7239d", "ab1747694e6e07051b6739e3df2916e09d7cd8a135753c9136a8dbba0449e83a", "25d6f0d435679e7d84147da65006a48a5a0f893ed2e956518bbcd6b98f40d368", "3554c7682f565a20b336c40129b5f7182239f2b0b1169f39f8421f25b9ad52cd", "51b263e67a4421f6b858eb3cafe303af0b3339e0b0509eb068fe3092d394f530", "2bdcbc0df01dbdab2c91c4658bb9b160fe3efbb5dfecdd85ab525dc21033d90a", "aa0105f9628907cdeebaa743c45a458553942c3e089d64a02bdcaef293581337", "d4636ae50f908fb11cfa1f338314260f587f26c29c86cd682e5003fccb554efa", "31ae9547640c8ebad28019e8eb66cf608074d5c1a95aefa065db97da4c1e1044", "a228c94293d05874a00c3aa46ee128a41d10405c28e5bed3f7e7f548243fafd2", "a7d5f3e4630be48f88cfe45147b94b9010718e55d6eaae6462a41aac52e866c3", "56d4a383be9efe8694a572a143649be7bf89b1eb12842438162532827f7bf101", "79f7177cf2655951fe0fe7c98cd1cca252e7eafc0b81066aab0841f7cd7895f5", "abc1746768383ad59c647846b13dbdf51d50f9a5f2c50fac9f676531ed6d08a6", "a1ad8a55e14acf37cd4eb5085405b62a53948065dcd3bbf299477d03b1d8cc6f", "c731487e9086642d4e92ecbada3dc31b72049583d446d65bda3a09b4370cafdb", "729c914190c753c6ab1f648ed04889baba5adc43e05102587672a7a0051b279d", "3fcbf09cd64d4070062dd2eaf9ff595d3e1fefaea6996ab134e9f394e0814f56", "2efc8bdc74b41138f0075e2603ec227f7265d3eb6e7ca16a7e1696aa83cc3635", "cf05b470683e4090959a5e6222aabb1026d60907f9df98256ed0dc62103eff79", "cae8a98b1c421ba34af46610134a71153d525636c02cccad8e0362b7109d7410", "cbf00526ae885899747bad4c395b9f2c02e62bbf39fcee82565fecb1224bc311", "b6ddac871381353848dbb438f0b7ef14fca4eb39fbda7b4eb1747ea454b3155a", "375b66c16668308f1e768c09bc2dbb0def9dd04d2f90c42c49453f558220a338", "a2387da7be7ec4a0ce7ef03cb1bd701330e5e950be120854efac13d903367248", "21f4efbd857d838626a5b6eb935c1d8dc3a0a6c8defd23928c8018c4956663c1", "ac96b176999b37719fe3a67231b811a7a435ee7b5e807fd1430803a29cab70ff", "9c06f32a7f016a0e702b928f7de9a82297498400654109ec3a17a1c2531a36d0", "fa932de504e54776e5b8fe75a2aa7067cff79865b766882542608eb31de1f3af", "d994c1c85ab3611ad12fbbd4ee7e7afb30ff9ce3c67ca619d9786553b0383668", "2e5789ccd625cf20f42a72de7cdc246ab92a1cd85ee619570549a8effa476ff9", "ec4145c429fecc6b5109d5a4e1434c4418925fc65f53bda6cd06620dbd2d1b69", "0978239a7a14bb768e1ca71e1d40e37a102091ad01a75f5f92c5da900761c79d", "3382546aefe321d644bd3626c7b767bbf940df0cebfd3917c05f69c7973136cc", "227e8c8045928af96e794585a87d6869c3ced7dab3689c5565cec54e168641a9", "c0a3f1b8c27d0234fc64fd8d1ff9f6d3ca157b03033e505bd443f1b7bba62f7e", "2e848b33465df0fa0a2b75d23c4df4f02824f431e78e80c0221ff5aa61348a91", "14656b6da232af334beffd02ffb86992637993ce4aa530acf8bbc2081c5dd2eb", "1697567eea595c835310638672cc7ff2067a568198731128280bf4167b2e45ee", "749a784a544085ed3fe56e3ce9643d0e13aab8f3480f2fdfe7c16e15ef08d0b3", "0b2b27579b615e086959fb35f7741791615e25c611f8ab7851c83bdfeda7d7c9", "e444de3a6fc90b1d2626987fe98c956c1e0db2008cdbe6d863ad410e9fe0a8a3", "89a757ea85e9d24b3e584538cded1e5db3a90bb01066af609d3401d1bb5b205f", "b00b5a1ccbc1ec142c5ef063daa88aaac1d3e52af12256cd892803aa348c3f30", "0ea22dee4f62ac35e5b45a3beeff82c8c32231193bcc33ba7575916dacbdebde", "5c428762fa847e9a97fce0f306c7f0d8c4b4abdf9defcb0df0dafec41590ebb8", "8eacd0d7d08645ad8366807a5cc9f91a4b22fd52ab4d8c74efaeb9fba398f24d", "648ed141936c9497702be348e260b9a4aa9ff5dadc6b654381c9e54160a07f4b", "682cc4ae34101c80a98fe4a674ef0b16d11ce70b56b3a7fc5b191b360deeaecd", "2b82b8fa930e14bcc38f1b9bf6a99f3987b32c7e74363d20acf6bd05057cfb5e", "1d2c04136aa4ce34040a9756ba9f16af6a3fad26b7a9669a62c3563d66a4d4a5", "04ab01586e7e4615656127d95cd558e318457ed1641c2229b75ed676f21ae1d5", "a7a5c84706284a3c98121e35e89e3361c39ab8b5ce26c3e479cdb4c2f30aaea9", "d12b3299cd334b9899ce855a088577d8d757dc32125921f2ee561daa94814b7b", "48714a6b92c6e98e3406ee38539721a3ba60254ace52c741925222955a89a8bb", "27597f719f1a11522733a0db69462fd7d28f0a64d6cb508af5dbfee291b52f81", "44c2fc25551c204419d798aafacde9e75b4aed663d47c0cca8c5c3482b7660ac", "9cfc7a76eafe717ecd56501bc16aa644bac189cab58dbb90bbb0cf3a4e3053ef", "029223d300c7186ab0c823474f67590a86e7d08a9d1ed39588307def876ad59b", "533054cb85955768daaedd98ccd79495e4726b2e5e7d345a3cc70beb19538a57", "60e7f410dd3c32e1c88638ca4e758db9a2a8f7e52e2faee358fdbf5dd3fce27e", "3ed8f47b67c5cc36b0e6745a29251d0470795cb14f0ad9b30170c0e5c8efcbe6", "1f889c28d68e869bf711e214dbe739acc35780e8b19ef9576dede8e2e91bdb9d", "dbf00c8bd10f5ae12f38c625c8af8089cd28ff92f34a1d949dbdc20d7a80d797", "960ef9daa1b246bb656aed819cbe898dc14ca8e558070c9468f840487c05db92", "fe1b43ac2709550840c682ecc23d2699e9b3fcf55851999d9f09b02370aad502", "9f58ad99bdc049a7cc29f7bc482629302d56b32ba3b4a703223945c8a61f4254", "af61383d241fa4cee95f8065527537a237914d9b1494ac8fd3ed476a604882af", "503e10b0bd880beb400e91fce69c4fc9f36e3c816ae86b7b8d9729d00d08efc7", "beb9c475c020f4af8659aa27ef0d1dd143479029a8ef2f605adae61bd693c9ce", "73b93de4843e323d7db0726e0bc301ff0194b9656bb40bd3baae073b9a4df96b", "3f3a78847d9964cae0df94acbd73ba24eb042f44e5a473b1dc665a4db518dcbd", "240d37aeb82815e4a61db5729ca10d069d9554e3f209eecd881d12719a47dab6", "87f8197177364e5b345abc75771b0418890afaa0c109e2f6da58df071868c7de", "9d0f1a386ab8b2192f4531281d50df5d354a96afca98b9122198982e0120d384", "0bd411fccce089fbbd2eb04da0cecc3f030d036a44b78f37352816bd2bec9c1d", "a5587eb1bb907b021e206cf17beaaeeff2c34c22a9857c0ead14d68f62b1818c", "ed96c8097a4fa7debe2db8b1aff9baea5ebad839b60b7ac878fc93dd704f9633", "c244897280ea22de3494642c6a8219500b884ccc77802b953f71cf12de445e28", "e11b64f780d2e2314fe969a74a86129b8cdaf4d223376843b94f4e64e9be7eec", "1a7771432e6782bf9a5ef436874bb9aa44a5f46d1a5a7aa785dd1fb2311d9d58", "215be42fb8c3511dbcbccd1634895857d48d2f26de9f9f167ffa86f141819298", "5635725b8e48404be37a8c9db3274195cd7e36a651c65d09ee8419c571d1d233", "3bbe9d510574073e795b4f843f272a1900f31510f9ad36a522525845c90075ee", "1b19a47569f1803ecc66d1d5163c4c6e7ab9f7e99abe3e8bcf55f8cdbb00ef7a", "c155578db721fb204f9759119f8ff004d78ba068869c938d9ce0a57e650e085c", "017d7f31830417c7a0ef240d7837ef9cf047ed0a8414eb085da37fe2cddbdf64", "78ea7551cf28cb954259a28ec1340ee66d715f02c5eb7fec48145298581464f1", "b89ee6474841186f5afab538f9ca17b4171c303d5dcc89247b79ce38389bc0da", "f15ceaf2a19e8eb599bac5959aba3518688d4791321e618b5ff4af1700fc969f", "6c0be8eac8a473b665f89bc3a310c033c093f5b062527a227921b072aa3123be", "60950a25415add062c9bd5427cf5e0eb75d6fd7363af9d44656831d04cdcf7fe", "c8ee6f1b5cafc14571642946e8d8e56191c3a9a020e5322ec30a698258c24a17", "fd5a24fb185292c845fb8759d924a72f24c18758fe9ac5e0df99d1365e0657a4", "85db138de6940bcd58f37836e431c6d0dda1722d21f7fe2e519d08ec8d990d7b", "13a18fb4b02a808771e8a5eb2a64829bf27c7e6fb82b2adf8d44a920fa6a5900", "cf37460c8ad19a604cd4d1475e8258ddbf72e3163d07bad676a0db39248f298d", "16aaf7854629a4612442c7c7b67836990ce60a78b95bb0221646cb9d27454e2a", "f3ff2a33d32daff5a2606ad41d8b9fa469fed175ab2d12cba2432d2cec320bcd", "3f84dcab7582376089e959b42b47ed237ad52f5e633093bf7fcbff6164b74cbd", "1776d3f2ca165cc20e0736e7ba69ce320b1e19575245e0e78bf628bf8a3b4c90", "4b815273385785fe9e57dbe6bbab75423b6302f8daef245c12bc4b8572696893", "f9daf148d2ece99869e00ed44ffc1a740792569a36d6dc21a94388453c31a08b", "0a7f0cc9bc54b816a21785f84414bdb99f34a49a3e33e5fa1d105ba026540627", "05ec349ece9f47e92ec0bada62dc00a7896abe818b213914b95d3cc301afa0cf", "3f652f63459aba4684390a90687e117bfd79e09b42542733acb734adbb0a01cf", "d7be18e61d11c4e5757f2ad5fb6b8eb70ab1f621f7785d048baec87e3c81ddb7", "cb4ef5ac7ff2c34808e9398ff7e313cfb5b73e8b3cf9c0c3ab8059983159213c", "c1f66f86c3dc26b2212cd7536bd40bde14015a19108d997e24d0f5b1532c5201", "2e8766d4dd56646f8fca1cc12fe66785bd90f42d27074c71e3380732f5616558", "feb95b15d26976b6b31bd488430da464d87102d5b35cec8bb578cffc91bc7933", "bef956f6a785e9937e4e3bad0b1468c428534fc06658738d5e02c1a604c77003", "fb471f8b762add49e6d91eb46cc018a6990ca7bf1fb15d26aec90f6ba968f6cd", "d4f35e4a4e006546af1bf09f5e49b5dda60ae5dd526b85ba92d871f4f09df77b", "795fda42bece1d711437fe504f78e940f309c89830bdb5e9dd46afe3fbb1b150", "abaf0bc879b70ace0a82af4b9d4f32085ddc7c5d920a673c47e83199959b4de6", "ae69a784b18524bf95e7b2349cd1c36709eb810b0168e7e140a7a411443a02dd", "7858fa7acf40bbc2168ebf05e3389ae646d1fd4567b17470506596baa5e00ea9", "d9f1d5f5ba2a228915342e41510bcdaac533e10025531eb9a1960b93ae667332", "5a0def567978daf9e17209cf27f261256f11d0f8cc946c888ba3bd15e56c786a", "589c40f1e0e442e1e227c1d45ddbd799c41cc38d025ae871bbbad98e0b65d2c4", "d25e897ed507bc4dcbbf349cc2de3d2240ad6bede49c89fb07c9b5dcc138363c", "b480a7829783c502490abec998b2d0253aeeee68e54bc165a5f1e98cb6a9f4c5", "ae8c6d400c2d517eb69379c486e1ad35497e692292bbe495f0d01b4d4e48e265", "27fe2f66e35f873b8094d7e2ced46e55811f5a936f9019e5e2db41b7ae5e819b", "1d767698a7e6a1d6adfb55c1584880350f2c4e80f40e51776bd33a6a2e47ba8a", "70114481a06394db7de45673ff702a2ca4047d2715d780884f3f841a493790b3", "404487dd890566585291dbf1a22cbbb7fd70e4870b36f39ee7c710320aa0c270", "b908e1a132f73bc705594db6e08b82fb277a87456142f6e6145fa4701d7de09c", "7f0734a0c77fbb88b5a5a4d49f995bad567f0a676cc9326c3267211d06ffffe7", "204e168e47177bf41e3066b1ffa5f0779d98fdc7a0ff8ac5399f1c3abd6998cd", "fae75f8b1c0302a15813cdacc724fb9c9d06d6ac7c6a358b1f1c33a9df3da5c3", "c18e90a57bd273f5d27751fe81ea9302f5604f24c2a2a9d306e2b0b26ed65cdc", "dc084d1ec5c777f8cb78fa955903adb7bcc68b0d18cd2de66f9c32acfe9e9948", "4fbad69a041e89833b72a21907459d2a9985bef82d05f70a8740f4d1abbac471", "f0d752ca1604efdc9102728c70fc2198ed466b21acdafe6a234f7124cdc3c531", "96a291d08e64c21d74c94982a2d1a146ca25ef24b4c2ffcdb3a8bcd77288072b", "d84f7a140461dc63b72d66dc97af315127f8260a6176159f7120ad15e0ffbb42", "e323b02b16317a133f695b892900cbed463c146310f13847cf52f5e8a1556403", "56f9986c62059e091f741f5febd25cd26400acfd51302e09e853c49815345372", "4a91c13e08448237509eefdc09ed41470f72309aeb0f3577bfbdaf2f45b359ca", "3f1214f03f2bb53d779d05f2a3a647d0bc2550b5540ef159c2917cbab8abe006", "c00d7a898094e86d4659ecd1ebead956c2d74969a9c7ea05b2ef5daf456cbfde", "c9f7b7bd863e12133688f089abc3846578a8c50f8fe95d33ffae1472cd61d396", "9c4cb359614595f16ba7a76a3a5f7a78205c32a23653a935400f147206eb4a2e", "f81f1b1b6ec3af3a09c79607ff09a025162ddfc14cf85ddaf4ed678599031bcb", "07518a7b6771f27678761c04c584da6475af520f2358b0886ac0f792e5b07e79", "3d8edf9ff36d26b12f22af02685c72a8f9106295c7cd06cfe74fd59967501ef9", "957afb2e2abda010d44ee4eda67a2b70b61c56594a31964f860b26a28cb8454f", "f136ce60520308496e1802b6de253f4911afe61e910358b2ead474a9cf48ee6c", "7c90e7fd57edfe1fd3504153c5fc31342a7b354e93038b45140b67fb6fd18e65", "629c3a127f091ebee42b4d487d029bd4c3fa2ec72dbecc715e6c8c9d2671b736", "41e8646e02f9bb0537b627ae5f269154b03d916fc490d38abbcfc3ebf6d9dda4", "72d66600ed0cc1faa6d91c2a0da81bd90d4538cee893aae4bb0cc14eeb4dc280", "81889ef1c6d2c81067e366ab7185eb2199be8789f114ddd6a3b693ef7821bbec", "8adb60319e326ca0afa70e7f8ce7209bef89e1ec820a5d70f13d606add534ab6", "ddcebfd51afd77e78f06d5a5dccbfb4d6dc61977c47ac9b1a2f6402940d9a156", "b4cc18127051cfd93b1a5eb0358153c03f1d44b841a41cf3c2a7a23a14dec4f4", "a3d44b5e13a0c0e6eb22da6e8811d4995d495d4d780e840ee85c83f2b1656082", "eb69269adfc48cad8200b8e31807e9454ec615b8d33b67e7191cead52549007a", "cc6bed8de65dc9b905e2aa95ad5fd57bb82ee21c49968cf30a6cb4b002be5f6d", "0ee85d0f8f0f5bfb77f957de73fcb2da0ff2691b2971ea681432a67ae5c7c378", "d8a2af3e7a30804574e74ed97275804fcc22c19607ea30251f7fcecfc86c8cd4", "be4f45e912a7cc5a174d6cd1c058412042308381f9882d2a74c43cef9a93e51c", "b2137011b2206e9737392b735787c1861d5df47690b5682cbd432fcac4c05198", "f4fcc63e7a123783b643adbf0b97580b789def70d8ce5af5955b35b263f4a4fe", "1cdf85f46a7dd1937cd43c941f1b555d582f36d3091097231f86602c73c84c7d", "76cd77e06f946eab3f59cdccd3a3e20395f04d5e61ebc5ae6cfebbf72d96214a", "f080f232fbf74a104a25ff2df6958e0008662596f81cfb84cd72c2a940c9b5fd", "70a13b34f284353ecae70355403e6297fbab263f207707860ec22dc8a2da4c94", "2d1bceb4417eabef500af978c975f18ab1b01b12946ff411832af267652f5d49", "74847cb2b631547a13df246f10f21053e1d412b4bcc83d2a28285033c75a2839", "0df6e0d42f19ca95d31d9b762fb58b9ee4ef0a2037cab32e49509c575c6ed19b", "e9b6acc84e087163ed1ea23f7b7aa0fa4ea37f15473a47af6618d7f30e8f56a7", "3578384eae5e7a10731d6de0972072f1f568a764ee9a2c2c6152eee141fdd3d7", "69653aa6632c7fb7c69a8129861e9f3226b726a8804471165642481b598dd099", "a296c05fca5e44afc5c2cd583cbde4a1791bdb7a8461c6676b97ea63c11fe393", "077900cf366702fe8add4f0265cc52273b343a14218ea59ab26cd628a38240fa", "a63d694c0e6728166e578d90061d24146d56ccda4ef281c41ce6076ad51727bc", "1623e53bff3af6346b27b38cfc0d98f6f2ec80830789f88bbccfbecb4ce1162c", "ce5c3ddd1852bb75590b6d8db16b4e6264a8993a3aad89f1731753565d5e54fb", "3dc87d48cddba8c9aea71e8307e9d803925c9e4c4f55d7730d3e651dbfc7ba45", "1cd04f320cca7fe33c2f43dd9e0098cda82edf20162a67320e68ebaf3fd74fe5", "8d63274c4a44170e5008d2d1b790d5f468269abfa91a54c329152433a30665b9", "89ff3946f2111436afd2b41932c475a0d09223e23b6b9e9a9ccf164d3cbe0b11", "db63caf3eda1222a308deb317a0bc8f1deb95a6b3b0108f71d2d16691244927b", "3d1ba03634ffaeb5d906032273191fe2595bd655a70dd8c22680fa4929012c6f", "0d355563eac60a85c52b4b2a54c21ee7610819a9a3b30e69a9a37b5655b9b5db", "373a44ab3936104a3d9d26a246d2365127c1726c34d2f1d7e87d7d7f6058f248", "16022145fe055769433d4c3cd9639ce0f8f668e157bf9711e2c7bd7907178df4", "6b34e7d77649a72887fa46cb34618d813a32fbb77e4ebdd6691527eacf5fd84c", "df915fc7ca49225b34f2d419554d2594c8b2ffd834b2bb92f49397fcff381eac", "6002c0ef73c781b20d7d4d9e01322f8efa8aa78e5e9792bce29a9169c7032f57", "3a0debbc0ee42304a9edb10db770d0b8180c403971f42dad8832cc16e395c11c", "6d76b23d46aae2e574ec2947c490f2ead9acf9592e417069e72050721224fba4", "593602ee2803bcdd743fce93962f672cb877edc7d009be65c02a562b8604a74c", "64759e44d4e426d1c147b405330e2fe1ed1afe168b8db60a87c935cf07ea10f6", "d8f1eea3b2c56c9bdeeea5cc57d5fb38cda7c2dcef9276ed5602d27b9788c194", "0da1328dfa5efb29034215279a87bf026e70aa7ceb2793e8c0ba9354580d552b", "8bf631c56ecb7ab31c0d30bf31dd28a62877402cd6825d0ecc9c71e26f4be643", "ae29941b70abb79f690de45e32c8b55f8114b30cae4376e991b963d4e03d970d", "0b87ec546259a15a8c8752634c3ef219459c382d383f155f219c04d9d5bd7f01", "87605721bbed02e5f279a29dbf5fb857a5e1d41ffbc50689ec4e1ad1ed3f2b76", "64d33c169662adb9ae01cc1a902b8725ea84162226d860b05b22c1cf8b716b88", "dd3e22b9aaf98f165f20c449618ebf776727386daf5695e68847462a1573f1fa", "2eed687fa82a0df68fb2a1ccd9c7e0679f5ada28b831b105718dbd0580c0aeb6", "3748437a03b2e086825a1b26b9a363495cb04ee3b5c6125f16fa7153d388b38d", "d6f69cb9ff2388175b1e549df23171ea6cf0f181c52902e90740dec0fef941b5", "81e173033c052c2a8b6c2ce928c7d9e7f7b956e9744156c8b40cf815f093de69", "627027e95f078f86d70df8b97d509bd556c6397693025367ae4b43edc9b6fdf2", "9c8bee1ae58091342dac7901e5846df4acbbc409656457b03e1702eeabbfc8f5", "ee387d8e66f5bf75dfdcdeb97d28b4dbbcb1302bf20d6bf8465b7b41832550ad", "681f0145ff4dd8a84e42b02ca5bdf4bbe8adfdff11e3ae57673740a4f98f0c67", "9f7d29a27a80e64603c98125d6f77e23afac3ae85ab0fbbe91e74e498fa69c89", "f23c72f39810dfa196ddac4a2b30fc97f3e05cfd67d91ef2e6ab063ee29483a9", "cb02c55cbe1a20d200bd53e718c78f9f2307d0476082bb425d4476a70ef47172", "2c56d7a46e2e989c71d754a9ed2ed22285adb9bc7ea0ce85e7ad0146798836e0", "161f8ede4832a65d9d082699e93299189916a9feae06703aabba7aa7100c8078", "c14f24845530dbca3372c7d7453441113682d76ca7c5ee93a86f8705dfa6754b", "98e2302a8c27aff16705eac3c9b4861e0d670571ca493dd0077280785d1d32a3", "1af7252bf32de08559d47dc9273c82a7e6cf89c2ad0d755084116bdc30e2dcb9", "b662f05da0258a7218659df10926cb716fc6d092654ebdf9d8a0efcab72f311e", "ad8807bdc9c0db6fff8ba8963af51f14ed809ff5cff5944d27b1923bc5cec68e", "4502bbe76bba11effb1f91a822732bb4d1c6cbd20a12722cf7cf2276bcb224ef", "bd100da2cd60b60a2923299e505c6c0fd23cfdeebefbcec8119567fee2b8d5ac", "2725060e6d944dceab24729b82d3a64275ebd82cb42ab330af43f53cefa27893", "9cad96ee381a6d63d841569e475eeff6dee67836e2d05113a8f18aee590673b2", "c22c8e48d846ad43fc8319c4d3ed8c4af31ea7c3e079595cbb557b78e50f0a60", "24a9bcf359c2345fdc35812a10f9f08229d11f17c5951120cda1264adb2e6d71", "54658722a2c31e13616e4a38a817927c01d2df37830dab7e76ec16e7ec93e298", "fdf9d5820ce67e076d78db09766a5827c6d14678d1336c8f936608d80ae83d72", "f3c55939c47563aecd9a0be2fd16c8d839331c811403ea22d47a8dedb636f389", "9a62ce2c9a3238370ab983857b27a6ebba407540c6a55b8d3e62fb012b9177d5", "32ea29fa721d7727b0ad77f534bba0ccd4f08b16b1c809c60da2e83c37cd052f", "0c8eab2d814623966122a83e079ae8629897d405fc471fe70eb8ecf63d53a6a4", "b5f81d6be6c5ed881db8e195b850c3ebfa2cb455d0a1d14df79740eebe5d549e", "ff39acb8667a42faa265d97a90fa7d5802c6a581dfa6bc868fc6e953b4fe3b10", "cd1a9a932859370e971587fa26255782a1aee9a1efeafd17badd1aca3c822363", "780034cf738e520971387345b73f42cd13770dc8cf68948ec9e8e1f6a6327f61", "0d97a70b467fbf4af625a6b539035b19e86d011782bb7a9ce538bb89d81438f5", "ca8dcf9e3454d6c2a346a01372c798cf2cf8c49c38f9581d705c42e4f1e7c4b4", "0c21834cdce637a85f931e8d2d961573d1dba0ab7bee93189f74c6331995c914", "c8aa251601172c9479b4ab2c1382a2d6608b547cf6b7a4a04a75a91fde4c08b3", "14d36f3db5b2cfac7a99df066016eba59a21ef651e991d631c04acb11d1d2b51", "89006b74bc61637b0808bf786df16039d0f5a26d1cde1348de0f33718d47e75c", "098621c303cb1b9dda387a0ee66ecd267172a70defc1b403887ea74c53d5b911", "f9428c1dc527138be5c9ddbfeed43077d06f2826b75edf9218e7b90df8b5ec29", "245270fc3442e19475818ca0d5cd32a4728a25b5c4f2231d571eafa281e61e18", "753e79f5b9edd2e49c30c17d3d5050a2c0265027abdf8e661281d22e6cacb701", "7ac9b5239a33b2689c63739de793dfbbd0955c044fe062bab28f7b9e72af4755", "ba6c405725d69b2c74661f3e4259242b054d13f197db5700d1d7728110e56955", "a7ff3309d156a8d4af88c92e5959c98617e0c1b95a10caa544fd761f93715b80", "4185a1fd84ac173ac31493ea80b4a6d38d37325e8d82d07ee31bbd7f5c661e17", "78826fde40d9fed3355c37bcaaf0656a4236d58404a892d1da402955698e2904", "9f591f6bb853601a315de1edebc0927bde202e6cdacacace8dd32bc824a8a094", "3ae950afe6ce59737c943cd90dc8f100de10de1ee952b2d295514c4f710aa7d2", "a75089fa658b1206f03622608239f2de628b4a4693548c864d6096e2cef76490", "efa7ea258d706b04547b8d4a791b1113fc77a4e5547c8a308a89bcbbf8161e56", "f0c8cd991b168fa30685d9adb508e9aeb4f2b63dc08a153b814b0cf1f989183b", "6f1946a94c3138276073dcfe0d0d48d3cff0452993b34965a8fefe90161f0fcd", "2bc40489956125fa47c9cff896091977b8dd0b7a0e0150f614592b11a2e4d1ff", "b2f96fc311567ddbef1bf0fc487f973145f717f283883606ee03b4384da74003", "afb571e0e140ddda917b23d993474493d61a8414b0bd191092b6780bed309756", "687a64c739ccc3941a0eb74554bcd0135e0063922933ff892c7b90b88e21c7b8", "5ddc34627e55a68c4fd82c789c10d7fecf3e380b458ecd18eb8c5ae041c0b288", "ee7584bbd58e279c2667ffc07c1c4977654fc948a63e33633a563c757f0dd9fd", "3b7fb2e668fbef730803f10eea0e6cd9a2819eee7c1c1418431d1dc683def7f2", "b4e18431bfedbd98c924a64497c60ca9e4a82f22084fa1ad24c09f79b2ea6a94", "a5073a937e8b5cbbabb8915cfd2f2fe7307e4e334d5f434077995815475f0df2", "455b0de46808bf01d625c22f0cea27120780c8c69c0c11cf837e98823faf58ff", "a2b26681847ad348da10f7b578cae28087a3f5aabc5f84de188ae7ba9dc754f4", "f03694a80d8dcf0b98d4c4ae69a797218cff7688f80ea97e627e817ad36f3795", "006670166e382b2bf369907cb2b4834d58ccdc55a4bbd6494e8f9c129f5140e6", "ba02ab95f8cdf7e40f03a629e47a0f7d5b77096549f17a158c73e2b96c6cf0ed", "e1180c4ae2e094ff0ef2dd8107e5f2b02bebfad6501b18965b75ce8689efea2a", "a8114db88256707afdb0f589c4e375a7b165380a0f8c2795c0c0dc0d02f5684c", "a8ff66f47c414f56d8129e33a45a0bd9b9d1a640a3a3454d3496ba3a800b2d1f", "f36ca0f95e603f806380dce52d91036d8e3a5545e1dd7620a19196397b91359b", "1c207b576a1e9e765209ac6756c7948fa3f252a4687696d0f8e831f14ca52b92", "cc5eb95f7759dfb6cc55027d49a5fe9c52f3006568cd97a0c544638be7a887ee", "4e15d5885837d4e5e79bff21930dcacba97d2bac39e506896e005fd55aad7e67", "5e2e62808fbe25793a6917dfbfd06029ea30eee0892116fe6ea4696fcf62ef53", "334d575dcfb7f6b606866af045d0a378f53447ef51d5b3d1afd83d78c0aee1eb", "591c6dc98541b9fa044ab89f78856374c3f42ca5f8021bfa0e119d8a04a28646", "c502d6853c8eb8a2657e069659c1f3b06878498d1b1a15f771fffaf886a1ae52", "2d4b16c2b6cee606af3c02ae8d6a86560e2393306fed2ac0b72456a8e35e24b6", "b2ee8ad11dbd4ddbca245b403ada57354b5df94a9de54bdf574bf0eb41645c89", "a895e7d8adaec8c44b603648f36774980707d30ede4f5dbaf2bd3d2e3d4e90b4", "1e76fe8a5aa1b516db5d04f3496e69170d3a6910aea79ad7554e2527b81b6b5a", "1576d0f08a566bc422049efcdd942ba455e61a1bb2d6e1ad470e098899128f75", "ffc42cbcc82b0b23c5616301e90aa6ed76f485cd63506ba52097a42b5c17420e", "27fa1edc6938b7d3658c5c9d894136857fc0be8fa743924a86ee4baf583599bf", "4c8a502fb162a9580502f4f2618be83041782f245c6023e1d6c3ecd7bbf2cbd2", "5b72391f63f61ba48fbf8fd308ca6afb7d72b9545d1812538f2e4d1414c6fb1d", "1968aab09560c49509dc7cdac8c5c919629a3da0a39d7628b172d5e7bde99c20", "97656482e3f4c9dbd01cf1fd91f0deb0b319c15a89b5deec6a57fac647a81753", "d1392d6f39252c12b76aca6762fd95086785433913e5960b3c14a708401c2897", "c11244439c754d91aa30a2fcddeef5a0be7e300b94a5c98967785f112cdbcfff", "21c529765b6a1048c8c946578be14e63750eeae28521fd845bf7a3ae669f203b", "c2f22169832b5de185aaa5642f125738f164001083438328d2541c15a7f986af", "293583e0b2b86f041204e4ddc9546ca74431407f88ce36665337a5602dbe3bbd", "1c270bcff184b5efcdec7f630e707c3e7c90a519302233fdc08aa744d4cc0f9f", "88a9d5a81d358a14cd92c14d669903032c93371915725d764fb01c7c1673d4e0", "c733a54fa8d1ef07070c52ce77898eb93f148b13cdd1b6fa69884dae4b62144c", "acc7546cee77ad0a641bd33253869e0459325db8e6e3a9c7e3812916939e5345", "edb6a177be83d61f8e67db1b3837db0316d0205cc7303c242c697fb3c2a1af25", "8e1e002d811734ae8033333794c2bdbe826f1c69f4dd6197e595e75837a3ca64", "316f26c9d7b2dc523838fd4d8a102e7b817a44d00a4f31dcd30bd6529ca3070b", "0ae34d23335c3138e2ad4a282b3bdb89542bdc29a4df69d202ac41f140e15aa9", "6c6d48776be2e5a30e91af97bd6b0bc5a5eb76a5fd713adc399f8664918cee9f", "dfd7c371eef529314fa853918ed4fac86e473d5bfcd9dbe261e57201d70c082f", "0046ae85e6230a07ef27a9c7c75dc6f6ccb7742433cf8be17343ea8666512259", "dd9fe83a560f0897bd19f23474fe744c8eade026cdb1f048e84f3459e0f19303", "3e6a71ec2a652defe81127e60e22728c5c2b6b7ebd3f8946e347d662ff3a868b", "a4229eb078f80905f012a474545e0e2786f98bf7fb2073dcead7ec73c65fbe9b", "7dcad9638f5473ae40af1a5d9334ca763a09c66812806f67e75bb44e457f87c3", "374ff61877eb866ee324a87077eb71d0a269e9845847e55a5e10fe5f3c77aade", "ef6f393a0d140250e071d3b82f5086c13bb429266cf944bae8cdaa28834cef8b", "9651ad41b55c6e8d6abb345d4ea06e4399cf2902d2c1cf13ebbfba0b7140c8bc", "9d0540e58a6445fd868ea65c40185a7da7858524f419797084a602427ace7477", "5d812312bfa56dced2d010ddbd98b79ec946a4c13fc545088c80d037e4df3c3b", "c75d28a33c292a50e293d4e88f25421bc03c83fdbafaba4f526b8c6a7e5c2e2e", "53cc98e7b41fa8cf94ae5ddb9807fcf8c73c209d910c892f266621fa05782ece", "f6b589decfffc6c33957cd061404dea6482435abcabbad3485266cf4a8e7fc05", "e4e03d0c467c2420923815fdef774f530d07c0c415e9975bed75db2ce4227dbf", "7178a3cf86b9b27023e576a0f112ddbd3e240289bf8c4256ec384962207d749d", "58c29327189acf5670bf364f2c9023439eab2dff643a4ff36f3d35b43263111e", "d9b365bae902827f415288ab30e5e75d93038ffc1466356d6f5280863f18dad2", "ffd371a7a95b47d197bc947e0e1c3cd50a96657ca14116fad6fb7ec96aec3bf1", "10ab513a9aa33ce2ea4cf293dd0c435b5aad5a1adff65604dd3f07cfa1f340ee", "40863aa43e50ba80bdafdba66ae053896370421d48f59c2aa962ec5e2914bd96", "0363498ed651cf53bd469fd0dd8ffdcee6c6b4641a67bf52fd177ee7e9e81324", "7804a9ccc78fcc0e6b6583e2fe28a32d3b409a08dc48061233f8faf88dbcfa03", "68ae59987180df7089fe2566c5d2a61d554b267332a24dc44ffba97c1ab1b596", "f2c29ca8dd0b0429df3fe25fe3e36e6fdef1170dbed8baa30cde80f13cd093f5", "06d4400c68d16ce0b1b70f8fef726fdf633af85eac4e285694db95c0f8e503cd", "8db9481d31cd20f8ebf15b2ac559ee46796f0da83b8a94139ab998e2be19f035", "4c4a93fcff164e070a9eac32c8b7a582a00c6d32f8dd146cc603520d91fb11dd", "3d70cb493fee1f8575dc7da9c7627d31ebf42c9842275f772ce6f0d42e06db0a", "9f28537ea916ceebf76f1a42544c43e13e9075929228f32190d9ba4f5bb5c9b0", "673af69eacb58312c01c9b4e93167bf8e5bec2ccb4450ab833baee81cdbbd95b", "0d0b61e12e81bed69380c9b8eb23a2384a48bb13a4b7808a21ebdb00960e7e4c", "284b4b1d0f126cc76b743eed1d255b181a4ea45839ef0c1dd2749ce5ae83270c", "70cbb1998efc52d6b6aecca67551e42bb44eb6dd6e400241d2e2bab34ef9c1f5", "a47582681ac364f031f9d19c42e0b68edc0749c5b3da9581009b5187b8b503f4", "808c8d746109d74eae54b97f45ab7b9ed24f32835cf8a1ec9d7d46c3fae5178b", "ab0e3e550b11a95ebe15edb506a534d70e4bdfbbc9172b251668cb8eaffa5c7b", "8d24d23ec2012ff57024b1241dd401eea2ec104645e5dd4088b32546fd8ff904", "523fc99da5bd881da326c94b303a852c0796792c1f3abfc1fdc7590c9a1ad80a", "bef023158f2dfff9af92f2aa64e7da3087afe08b2cd5bed4d6a0933e46efd411", "bdb056bd0ae30d8b926688b56a6e06029905ecb5b25922fe4f6f2004d4adfa11", "94a65dc8805bbee393a49a95ce8c95574ab280d6cfcc4a1490cec8352754c6a4", "50410fb63b9759e697bbb5c62d39820ce5d1f76ae9697e064578a15e0621b792", "90bc57b7055d84741c13f3a7707770de07ac2118015e3f0d08ac9ca3a4a6e177", "4b703ad6aaf1cbbd6f4fcaeb9745fa82f6fb055611d7164c572892b0fb786114", "0ab836aa1a9ab4467708652e8dbec2885119358e37b32f51b46d45f33c88046c", "1a118c7d922133ccd430b9f9857b62f8f2ce4df7d648a197f6edd3fefc07cecd", "40e846cc774ddf6392d673f69ce95245690f25786770051ba5ad49461310b0df", "5aadcafbcf0b1b4723d39c5d4048a8d9f3889a3f68aab66cac0ea4f0ef7d549d", "acdd2f2a548cd325fc06b49c257bfbc9b09c016ab0859cb947aac64c4570f6e9", "0b3ab537044f2e6142ff425079d25fcd87e0dd8187f03bf0dfc479142d8b9abd", "497c6521a301865863f7dfcd03316ae0db690e98546116c14df05d98e8cdc893", "ccdf5949457b2394df193f21d8cacd4971942ea3a1467e2ab13fc0cf38a2aca6", "b38079f35e81d62e2ec89a5511537abd020e0d49f47cfeacb1fdf0000e3898c3", "b5477b70b3e6f62fc281e349303e8e160a5cbf6af135bf3c991955b3cb963039", "64e8bcf3fdb18248ead8b6c5a23b156d76cbc6ab5789815a2b45c365ab20d353", "86c981eecb0af6e8ada8e68a9ba9a6cb93d0ed527a366121ab0dcf9f44d2a38d", "93ff8bbd4dced9f09d343b2227099d63a28c121389dda386c8b58acac7e020aa", "b9b7cc4a4e8b9f5a1ec1116d378e3f90ab3e8e4605d4cdc95b3e4b7df2815a1c", "f2f37eaae0ce72d792c65a906b6c7334c2377c3c31e454063305e7e63e5329e0", "cdfcf71c42e3d8d056cab0fbf3625c1b13704870709a4e0850006447f128efc0", "83566f6ad1536d4aa2543258bdee98989807ffa133d36af3a26672708ead8410", "68b89c27a8254d5fa39096943bd9bb0074e950fac7e686209c0113df088ae054", "0e8c8d00c7e71968371f4597da934aeaedc4142586c6454790fff7a4e61af30e", "0bc7e2ff2af89d45812349f03973406f27a4475c44e71589c4121a9cae9cf37e", "53738bebafb5a06ce8140b83ef922a31a05521c07c42cb09fbcf6619bf959697", "809f6e691647916082cde741c82df020254de10148b4b712744f1db345bc2694", "82238f89893476756a48eaa42cffb4fcf07c8cf4cdbe12a1c43145d2b67aac07", "ee995fdc7633e803741fffcad712a48aeafef16e5a91aba899e4295bcfa3b577", "b65b0489ecfa62b9725b7a4c4150caf0f01350de9cfd613c90c60d0fa4875ff2", "7988a77872e593e831989c6ca5e5e6861b63e1c2a42030d684b51fb88ab73004", "914ea37de5dc3b2f9035cdb7fb80e6e692a0a5934756beb6d8e2ea8eee7a3895", "d9c28dc8bc385283650fb2aeb1efe10caf848c39de37a78dbe6f47b8f3bd8b51", "49a2581f6ebc753d70dc30d3b093882153fef2d0825252354e5beb1b35eb90aa", "7791d37475e1e15bb9b817b180811d784963d2398c5e736a851af2ef8e622e77", "3957f179aa7676eadd2c312cd6096f84b7a0424bc99f05c8997bac9fed057ae5", "9d954ab5224ffd2e0301ff9b33ef834d019596a6c3f56fb634ccc9779b9c694f", "e6235eda52b721bcc3b997bc8da554f1998b5c7ff43cb86c2d7f1915150c4ded", "c0684e197ace1cb57ab553203b16fbccce5c993b876b90499e96d94ce308b956", "70cb7be7ca2d01bb41c09c06fefc04e8d6dbfcdbd9b8df4bd38caa3c7fbb6001", "96235ac39c397550e28b63f63a4bebf549215c5e72cc78488efeef131b0cdcf8", "f3bc2994745fcbbc792d905ce1858978814bcec9a5a0a3eea4913bb87939378e", "caf6345a1bc6013c428933fcf151ee366a11ee41070c3de2a3e5036a65145194", "ce92dd8170fc721b8bb69c261cd868b82a2d1ccc556bef3999128a3c20bd7c5a", "45e73df58de1b26bdc1b842b5a951da84381708cd15b40eab87ad44641777c6f", "1a57c8e01d94f7455719c85c662f76580b9f4f530aabbecee9c5abe00fd7def4", "c92b4679c9376df3e41d79131f42961fddcdf99afd2c476168daf9657f769373", "2a2893a114df2630e4b32c47bd60612b4f3d9b04891e944af55fd2767d260314", "98dfd86f3bb1b56d0e5b3d0a9b3227642b09ee0a2ae78f19eb504edd1bd91ba1", "2bca879ad4553c1406e38ab072cda33740cf1681f18e7cf548ce040528fa5d05", "5c3039135e50309be3292559fc0f0d6a5de7ab2803c83f206c8cfcc06683b54e", "7b46b23f8ca2c45baf6124165030a1ee5fc27f1ae3d1226defb2574177cf728f", "b37b504ccbcc5ae9f8b787fcc8da194fdda3a25b94fbf217444c13fa4a0863d5", "36d5d669f4afaf603a54902269087a0f65f89962f87ba03be56b552bf04ce81f", "f57f94affbe464d876235351bd20660ad5896e5f5bd38978d64346564a089754", "4637eacec37dc577f7d0c780ce46a57de6da9b5173f4d0626963af480b95213b", "e22295a0995837f730cf99e9465b0e5c41c1f4a99456f6b27d26d66b8ef2c4bf", "33d01fca1bb71c53d131b757afe6d97342006694ae752c17747a461717f42f8d", "ed239b46bcf7f8a66b92c15135488e1249f668625c6fd0a08a0f49c733806de0", "324c9a8fbc527d9e9357595b1b3509847847f340cd557b9305e78fa2ba963be4", "2fc5f4089b8b6375a41bb70257be3281cdd32778db05663c55f96cbeb976ef1c", "691fc9f8e0e0fd9c0a0f42f17f33ea83c3462e35d777dd54734108bf273b5a4f", "e21e3a565655f1f58ebdb421c94110e19a55030777dbbe455e350868020a574a", "2c3e5c5791cb68bb2177332f5b79c8f7d1cf4a577a903acf225a0d11e45aa5c5", "5707100bd5a978ef7fe1def6ba895ad388466a4db13679a899c93bcb802d3a7f", "fb537a7e26384ea9867ad9ac845067553c1461f5c75a5bd50df1afe40b063b1c", "afea4fc11996d2552a83a4b7bec586c9dbf3346cf2b3ee7a862b8f6ccf163522", "67a83eb66b438519cd92e6962566f3d1277395d2edfcecdb06565e33b9b4200e", "a763a731e9fd04d5ef02aef4e7cdc1726a34c7a048cd78c45ddf9f05c52773be", "c992b26e5d9f56c3f1615fe30fd5d4a70d639e192583e5792909baad8695e90f", "5f63a2abf7fde874a260f469f56f7392c715f43581fa0e0ad99522dde7c047da", "2d92ebb998b264b0c7fe1d9dc94c8f3ac171f31a38867eefd8687216342ad4ac", "36758fd2cddfa3f6c1658a649508727ede3db00c36b5a619260212b50b3e5da7", "19237f8184a40216542e1f326527f7e512ada4ff9923380f9a7a7e73a0c4aba1", "3f2d551638a07d4c6b03265f131adae2639d1600a9f31a337d5561bc22c41af6", "212a3841885d5890d53c698bfc2ee6114c13ed4636483f65bf9f43e2a23c2dc7", "30c6c4fede61dd964588586338cacee4e0ef8977b556b4fc104fcb6120d45d3e", "413981cdcd8428b9e76a34010c95f810ed5f39ee66edfcda92ab0ad94f030871", "c70a24bad26cd871d82aa4563199ce82ef8d00cebc48a1cd698ee1933ac8b6a1", "d228077b8f08942f4f5c445f5431f6a388d8dec122471f8c24a56ac158c90742", "6d25f50ee65fc7f46a86e1742f30afc9b9536b65762f75d9bfd1f9ca30df1d75", "2a7ac6f4b98849eb4d6962c424e91537967350ccb60c5cad40400d46fb0dc3d6", "002721d6c430ad953c9125dac7b4235a3f5edf80309b23fe9e197d0ef12ab0e2", "5464573c76aa26e98ba45180d7783bf83a1ec7939c8fd8a210d635225ea1ef42", "18395b65b1a46358ec085bafcc873706fb482866f54e02e042522ca09ff0452b", "f4ff0049dc8e5a4f06c6274a1bcdbf8b5f8b841f921a264ea5bff329378fd620", "19bdc09f26645d82ea05cd1fa0ffaa68885c66530b3f0eb05caa55b88aee4efa", "6e749013aca97a5ef3b156da4dc621bfefa7e0186e5e4780c31332f9c62ac7f7", "83800ecc6922e2a6ec0c34c1736a12f2dfcd94eb9f27c6948a5b28d961bc4ae9", "86b6fe2935f0206083c952c07ea38c25388955eb8a806c10b69d3e52d6ec26e5", "c7db870f8b09b9498d39b22d828b60a806f7a1de694c43d6bd29f3d76a11677d", "b0a5809735c83af8e2a3eeb93da682bce95a699392c0c4abc8d39188563e381f", "63af21f2f1f82d3120e4d8d98e7fda2d9f39d102c57d9c4111d07079a9ffcd47", "ad654b3ed5a11b9a2a52fbb8dda47e91a72e4b7bac3a4ad75c074786f14c046f", "6d9c4a44bf22648c07881e2e92a81ffe002c0177d9c7892416ce01ed1f693872", "16f279dbb7b3f6c3d4f190b36fe2283efd5fe4669a8f70d209eeed96bf55907c", "f79a83867614dc4d2e47353f53cb5a833582446329dbe4d5e8df941b0926dcb5", "0cebcc9ea3729487c1b20adb8eafc6fb1398710ff6179a7fdafb1985e5f4a8e8", "5a53e473fda88a9fd818defdc2c8e68bcea0c5aeded0c1910d6004b0e77ace89", "f97965894c4a296fca42905242a27228e5a9a0150d31a55e65d637dcb9e60ac1", "ec72e9e2fe2f4ab9db10b7075012c9e7cd2a4ec02b4c3b76df17f6eb27348ca2", "a4e92900f9f5490b66e21fb66c0ae094d106eed5366a85418a86a8a3f8f87a28", "225f9b50f64a97b9eadb625662b1a3e1b400eb86cee50fec8c62260027b4d390", "7cd4971b0e5453d210c097904480403bd53c689c19d52e4c6a37925d14e4272d", "3edaf61be8b6cfa06e1d42d7abd2df32033bf63cd14df8bb3ce337e62a822f16", "89fd8d0e59d8d757b7b8a2c3a2b826e799c028df166b6897a42f08f2284d3bdd", "0aa2fcdd4e83a4395cb5f514e1ef61ad4bb517d7c60f81bea030d5191c3c79b7", "80a275ddf6caa4bef4039860d4c5b0c4bd1009953c19ec2c63294ad2c5c56d1d", "e85d450859d702a0473363070a6e56d5021ebd1111232f2af28a60963acdac16", "54d48012bd8af661baae940fb6f0d10348137cbb13c650626f42051ede55ec8f", "bdb3a9bed24420afc6eb80930694b4afe0992318e49428156acdba5762c69e16", "cd277985e4b4c30a1999e5bf7bf7d1cc903640a04678a93efaac1f9bb5482dea", "d1319c6862feb76be11c089c753f62873519ec29a0c83b186efe57f50c4e342b", "1662d8e6db309700071a801a3d066ce97f942abce241c8085f3c023258927eb9", "e179e018705eb4a49ffa4e5271ddaa4fe1273029b521aea7a69f8f3b764ae017", "0e7347cdb154f6d96fc8f9eb8991d4149fbb21aa3270c21fa5df61ca140a4fe1", "34f182c2f44fab5ac9403543493be5006814b2379e0e6b7603d9e0fe76390367", "5d710a970ba007bffbecdf12d1c920fbda1f57023719d506825e0895a2affc49", "b99e0f318386f90df96c1d1cd4dc5bbe4726410f327ecc108108ad898e450eb5", "7eb9ae1f66a6bdc4482175d031bd6af270fe4ff8ed1138200d6eb49e13c0b8e8", "c508f259179f67bb6e05f2b9c5c5ea751f3a013eb925c6bfcc2a2624b962e059", "f3d0dab6f1d30ce74c97b89f551ce0820bebad2bc1cbf4a449b11d5408cbc140", "c116f6b0a0852a30c8a913f9e0f1680ff1be06165e19eac4d00c4e426ca9b6b3", "25df122cffe53ab88ecb94abae69e0a1d4323eadb7537c5e4894c0e082d58529", "a30d97485d4162e910b12effc549374221217c216b0a9487e5a07ff1fca835b8", "5dffc63818983f6a7db2ab65d621819be9f9edac58df38571887cba22aaaf1cf", "f042fb4eb01dde4b285f2df328f191d20621b66d7630d7691e7c69d9dcc04aaa", "d4190e2bf10aa9800a1c2395c0c4a38737c21f8bc42dffb23addf762ff309aa6", "4745eb0e771c9f2144ffd4abf39e63cf6d0ebe122df5f32ae399cc15fe3f7011", "806c6fabb4059c51865f723ae619e0c55718f973680ce7eb84c49b935f59ff02", "3352add492d3a7fa9ee046040a3f7795ec375af875c87edfdb0bc876ba14fb3b", "27dacac03594cae3db57550410bd0f8d166863992895548f6ab782a8332462c6", "1708396a0792c2a33b8174dd950c4a59ff06e969db873eaf2a7d82453e233b99", "5680174e172ddbe6943cede98f8d854dabb66ba65e3349889cd6262cdf462a80", "4960f0a4c46286d62e5bae021da9236ed0258f6c4c779e1797a9e66a47803f0a", "06af18499315d7dd1c8d16533f0e13465d606fea2946115f23735f3fe2f6d882", "73b0ee02de1c3c8a9b2bb8a9c48705c94df76c9c2d68a222c8493848c75327ad", "42044a69f91d56cf8b993166dc1c724ec7d311eff01c8255987cf563d58fa5a2", "187382209cf9b45c1df5655801a651463854a6495a7aa303887d65ad0e5b915f", "3e44b609a8f97ea0b412abf88d7748edfa62b7ceaa174bae008e508b1b133e7e", "d7b1c0b1bb02a6411eeb888ae26bef44c20364113bcfc1a4a3410396cb52b950", "5534bafcac199f54a48fa713c6f7ce0568abb11b341e38b4a968bddbffffa507", "84044786d9f286e241174796073fa47ce25c154616ba27bcca69fee1482942e1", "45eb4756d3895fffeb913bfe149746f56e184f4c336dad29f6f81fc2a3c0168f", "b583374fc47629a3f17476f4c9c751e851b7c4881eda50e4bead35afb77808b5", "4a99c32e81aa36e824bc4be78495458020b1faa47d558e7263f2c0477a16e6d8", "888b7d3a32f4566f21407c251b753b3890604001db91f88d45773bd8a53b2541", "53eb65e5b425e7acd56ee6234ebf3d40d8fc45a3dab9968ef4273cee307c38a9", "4bec2659f865dfae69862e128e710680f6114866b3478de257aa5ac596a66555", "543cbc31d271c10cabc9417a4d4b6dce2dac73c20ff29bfffbbe55584e5329a1", "4970e6469f1ace57971103d1cb2324b595ff12e34504ef8249971c76296bf578", "010810a21205384741812fe98489cd7369d9f6fd9e6818b11dea07c78a9073b1", "6114e32fefd54c1c2352ddf9327727bb6a34a9d8b3b7d01ce59c6e0d32700c7f", "ecc7248b7093678e7e0ae58333dcef0eaa18e3af261b2d1722d29acacce2b8f5", "0dc74b6f19b2bbf2f0e7f511440d4dbbc67952050bd1d962516b683ff6f9ec9b", "fb8447ff1d5200c3acc768992705d2108c37d61b0451c7474304803e76cc09e2", "f7f222b44c49d2d927fc2e345d64e2f0ed5f9a602758fc5f5ccc73d3b087f8bc", "295fcc7e7fcb601b3e79c1fe403f920b622bde0f4975419c3641c4d432de8f50", "e016f042fea1d93fcd4b2326b3ef6051e293b4abd066b3fa5c430ee7773e443c", "7c8347faa1ad96169f5650a1d138cb10bfb60dcf861d5e2dfce6a986997d2dab", "060928467611f28b99eaf284bc6c09d6760904ab5a6f9e072a44915a646e3ec8", "ba582c64b17221c46d27aaf6ce1e2818562639b321666c9513c1e85727a623e6", "e73793b5e2f33f60887c6ab428339d40d21fcf75530640977215a18db34fd7b4", "0ea32380009a639b705fda94d93ff032d88c3126503c0d153bd0f104b039bf60", "13bc02f7f971910299b8c61d1a16782726f22f63b31b2c0c34faece873f4418e", "a99b3ff6413262f46cf9a44c3fd5d0424109a6373e2580fe97938c3dc04e60df", "72b149e7ff672ec6b23352493cbcac166062282911e46d2b7ae5228d5814b720", "58d67077a2b7c836dbc19457eef1b1e1f734370a800388bdfb1012840fb7a240", "32beefd48538abe6eed6ae137199e03e05229d124628205cce7deb53f16f8f16", "3e466fb18e2a437292f00acf9f6e662fdc6e0b7cb9c0606e613f81dea3393e39", "9e537b504916eb6e9838f13eccf0c753869351778201c0813ee35cc19205409c", "404c0560dbcd46d1aa9cd76246654bd01f62ecafd40ad2b364c426f849941c5e", "89e5cbab667b81f08eeee6203be0af9cbe9dc0655af3272b0cb3fa722116c200", "2fac933a1b980ba75339703bd02f055199d057355a8dbe94eda724b79c2ac534", "c0200b5442f41779316e0e250b7bd011e12551b2babc96c9228f3187fbd17eb3", "f3269d2e80bfa7e80397a8d32815f8fb8fc0f8dc01dd1c75cd57028a23e5d462", "d6be8612904259aa6ff43ff30a2bbeba9d58e02f479f56480a8affc2cc9bee64", "a67a26fdd90d624fff7e501a2a946681134e32e3afe3094a0c3776229e7db123", "43234eef33f6bad45358374d23ded2731a35c12f472cce58d05e6d9ee56c9535", "f0217ee0507b13f56f8417d0c92e3c76026da461c22dbb7fdb653442dcf65ef5", "d9572135cdc5ba7afbf9871de3ffb68a1ca933e71b80e8766e678bde59ad2b52", "9d32d8b859188827a48fbbc7660900fa51bdb1bbf3dca2ecac1392a1cbbf4757", "daedaf79fde7f4e49a736f5b81f8b6f505884a073c5aad83997b93bb9685ee52", "fe7b3ac50841778d1283fd836996b1865f45392d53b95f3bef90ff657a49c498", "b89b62e4130fe4d40232744fb0182d477047acd40d32bcd15fb6181ddc890a6a", "0ae8786dcd5bffb824b81fa038b10c9127b811664e0d9655d537d95377d6d93c", "8608661859b838a7e8ec16e15db1114aa9db6b141877851e09439c591b46d830", "f5351c6f978f600be1a71c95abb638bdda6a7f6587e3f66d53bda682c7aa631f", "b6bcd591af74caa9970d39e0747bf20b56590878cc5b76da411525fd34b71cab", "bff91200c32ad862bfee68ac1fac4b85a5e6dbba4fd00a7d09e217cd226ce777", "40e5ebfabd309ba228262431317a2ffa268074cdf83556682d5f5e8c77660c5f", "c379dedb960b327f684e794ec212b11fd1eb8f20a6847676554be85aa4527dd2", "e405b5be582345aec0595f1a8a4aac6f938b539426fc7910d1271f3e2d1ba81d", "e27a84e97deb5450a38bffa685d0461dd90e2fc9c42aa1261da9d3b9fc8fa0b0", "c8b7e2506c4a067bacda36ed1bba81327b18a08df3fd373be25690754b9d8439", "5b8d011d0493a5217b74d086f4b8db0bb38cb357c76b1d59441af36806ead1f5", "4ad67654188a9c920bf0bfe25d22c433035d876e28f79a7c09c5649ae7b970eb", "2a0abcd054b303b2077ba72f2681a7832712b526b145b62c601741efecb360db", "bff88f3f33650251f8b9240b1bd94621460baf5d7b224030ff9619a6c708c56a", "d8846d0b025e2eb7eb528eabb478902ad5990d507837cff5c90b1113addf4c75", "e57728788dee9191e55c5588236680bec3f0d2cb8791da18064a6cb341b5b7a5", "f291bfd6644103b66aaa5208ecfb536a28d6209462f98493847ba6454896a369", "8b0a1b5d290d1069f771d50369e662c5f3c777c2ec3efee722d1a0ea58c6d9f8", "cdc255d80343d5967d7418ad4edb8dc99ac7138c1621bb8beb0869dafce44cb3", "cf363923e12340b2e95d7397df7775e3d6d98539001d8262048c67539be6a7c4", "aa8e17f4657e2aa01025d8c99112d7002fdb1abb086cecb23d428081c87de6dc", "59faa9c953bfd7f7d5bbfd363c25ed4089fbcce464b2958c9aedcd5729d4883b", "fd0e1bdf4b5130bfaff244ebd4654e4e0df288abf7673df010bb909286f93ce2", "f354946364f1449f4cb93847742ad2c2ec82163ccd7fb4e0d5687fccf1a2a018", "8be151375abca57a5df2d52428068eff6f82dad14d5bfd08a699f8e747ddcf99", "14a1cb09f11e6401ca5b119808a3176f893db83a0c23fdf9c393ac78139ba429", "1043a8492b8a8b6a8b9355669a29fc3f2e1e01df59741458bfd3014420df60c8", "338caae1b0d36e70fb8bbfb3e230a25fc9eab8a1c5b727e1313d61174c878411", "8e1509bd3f536a9e263d5bbd5cb5d892aa0a860c104f0ac7af74493b9d164bd6", "de5f3b69cd11a453b41b1595ee919dc2175ef867541c66571e6e71abba2661e4", "653934f935d080105495891b1889aaf0403223077af687feab1570d03cc08d29", "0cfc8f472eb4c7e30b17ecf91ba335ac1b479a01154e442d33fd0ef3c0e5dc4d", "fbc10b32be63288c096a64a70c75dfc76f162707be9f3b09675eeb08d98a4f52", "d76bf859e647ec2d77a7e5b5f726e8eeef59c6ab7fc1bb01c981b5cde26f3eb3", "64fe376e3defceb8149411cc4cdffdf3dac15aedb2ae45263a0b94877c8b9ac4", "3faacaf41e61750af0ac6df1b5a79927dba509d293a7fa2fa9e76bd3a574fd3c", "a7a80a4cd46db9010cfe1fa8859d658d7b4534832e7b44fddee51c53d6be6408", "c0268812c0e6cad694d5632f819b5623383fbc3e551122cad33b82536f733791", "a5a2a39a433131759be0f1f6339c4730de3d401c54c71813066def40e6cfb046", "61f4ea199859377dd681fd26610068f87e99081866cbf9aeaaaa1163e68fd950", "65e2e5e77b37be178505f7f40de4e64fd4e86acb9c6236ffec62392e8184692f", "bc82892fc9c6dc5d7bbf16ba4b2bea2cb9666815bf3f680f72be395384a299e7", "db5139acccf8dc1294eeb56fae06397f17a040e093d307a9e7b0d62ad6b42ae2", "43e63ea9672a65432e1b1c21baac7741c9a5f1d6c4e60ae0b4618587415c5a9f", "75e8ad0712bf9f279d89b252e7fc17ee0add1587df3f355568999fda4dfb0a2a", "83491196e6dfdec6dc2d09e12380cf55fca8acd4ed8af12012e41f3ac2270978", "b31d6592a4bedfc5e5d93565a4824f2917326566070ea981e45bdaadaf3022ba", "ad3b86deac6998141aaaf372f299bc1c39e8bbee4807cb2b6cab7cff32749815", "e2ea5f557fea88d002756c080dff0350e2ae9c15dbbd423a2be45d660107813b", "7750f2575cf347fc1b24fdd5b149eba76a438109f7ae02a515e2451179b2c98e", "c34cafe9369b18ed88c2936cd7cfaa2dad9ff105a9c3a53e49da5e7ad4ae4b4d", "c7542b4b36dab508ea0de2e1957d451160fb3616c4c81ab967d2aaa97cc0d8c8", "9da5cd367d3dc450b2c76dfa1ea0ad1e52db56eb7426fa031f2d08d919eb39d6", "340a3d854262aaf7a8a6bf005c21ae7ef62d58d052c1d108e7e09e708ac3f0d1", "dc2baad94c21cf7e37a4208a6dddd74bcc84aec852eb308a39ce9f81f6fb883c", "d21cb6a6f34d9a66c167c4939619a8823be213ceac2bf401721495628d2ea3ff", "55f3144838496089eb2af67adccd4b27340155cf2b1cc885427f4c7d4e7a8666", "86ac6e18b9931bd435b38f96d97aed092e1fa8be47089f00bc44b6f7897e64ff", "b4044a883dfb2eb9f4baa42d259f87d5ab39821470f977548a435cc65897a162", "d75f0fca387134162a37b5037c5006c3e25c991fd5c0d3eecaed3e75df90b30a", "4ef8fd941ecc624d1f13ec8c0004744cf907bf91f0a25ea0986294b81d5e45ea", "015e5322f9f2153091b70b0341912ea37a0da3ed20cfe9b8356c1ce882c00900", "65f0ffa646fdd7a98f1dde849611f19b2f443703a11ff5a61568b0ba7f85b0ef", "d9515617ba3fddf4595e395e0e033e9eae484810a478be85bb0eb3851000459b", "e3858e031fe47a5edc3ec572173de5ea77e9ed292968af2c6ff2fbd98e5d7996", "4fcaaf279411aa84d92f548b1dfc05458af2afe9ff577221e4b1d82a2e37368b", "269b84393f62de52b612e2f9922a67d06e523e27d4d2fe6d3aa68caed7a2a190", "4d179db7af1ec1b6094dd55ce21d26a54e395f23cc3428c0de6ef171d6b015ea", "1a508533186b12799e418ae46978c8bb8bc88fbd8a478fbea38b86987d197ce1", "ca4e5990f8a59ddaa61ea319c9ecba88cf321558b8735fc262aaa172185801b1", "0d48ac9f64fd82bf2e95ffb1eb9f1f73a8dc778417672fbdff374e5093a35f23", "c2b88c4f59cea3fd60369fc386ac89d22f6998a69b24f4c8ab7fee63247851a9", "75fa241c04b786f0f2670e0b1e45134aa76445efb26280cf6dfd926f0e77446a", "b6b80a7ed9aa4d50ec56812cd5a04fa290591976b0adce14e6657815764d1645", "c29d8b54a265d59ba2e8eb1bed27450e411ee34ccfda853d3a83c1da2fb75b3c", "180681a90fddc13a6f216b87128055a0947736248d967a5170149a50ec8020f8", "f65b08dc2c498a0f01adf70e45c5ba21205e259186f928305961718fd086e08b", "43e8f556219e8e6a7508a2c5ae19d6de0cda7b9f6e893bc19bb68e361c37c786", "367709af13a857bd2b97701b27c88a7c430a0e791a76c72896b575e017d8d9d6", "c9207c31bf4517e18513602801a0780242fdb91c1ef85924c2ad4ded7bbf1ada", "9e48f7bd1d77dc7269d121584eb914303aacf25a336d42914300659e0f67871a", "8a2b8b728756feef55e9c9bacc138eacf609589afb4422ba2ec2bf9aaaa6b0fb", "5440c68bcfe6a804c5865c3bbf033033bcabe29e20dbd9f36f5968e2eb0bef02", "432af6a45d6f2a44d5d6de8c82c4b43ebfc8b289b08866d0c4b4dbfe7337b31f", "4fb77ac98b549ebda2ba41cf0ee99b55c23386dde4cb505ccc497c4337b243be", "3f1af916ee3982bb79c31921da5c90a315c9719ef93d87be323bdfb13c6e2770", "4268889b9776502d948382bc1c9e065793104a2ed0e8aa75b2153b62b4ccc097", "e14719c99770cf507552d3d64eb822c8c7a6c4d12c769d6cecb6e6e05db85e47", "70adecdd90fccabd0f39e9d41dc19c6ba9afd11ddb7f09c6ca9c3e568b9e7194", "c9a94d170bbcb06d9170badf89f2f3533daf8e15b633dbe7ea1d02c62fd2d847", "538c3cff924df23105e51cb100c844f356d0d05d06e3aacb7c30f98c91292f72", "bee2c32fb72004ceb24d207bd890ba8fb4126848d2a7bb02ba580c2669f7d27d", "98db2db86a3da56f16411bf6c2e27f2755afd38673bccc15af8991fca283cd8b", "fd8f89cfc412008ec0752fabaec3ac72d6c89ad81286980e8138edf6ff4cd992", "009704c84f0954d45036969fd15c7293048156ff97a76d9c72a08248a4dcd725", "593b8d1e74c299da61950db52fd3b08f44d6cf972ec05a5c5914da9f230cacc5", "e8a6d9cff900567aef290b62a57d8d5528b7468adbe2ee0bcef8ac47e2dc1d7c", "9fbba3e66b12c7c926b88afb5b4a9eb03d1afaac94f673d45639ce9d4dd51416", "b7f9c83320d1b04ecb9b4f714da462b7bb4e4ab7cf3625a5f0bb497f5405a038", "4da28a828ab79336ff2e766d3f32e3a5ad11af8203c4428d97ce5c0054aaeca6", "d1d9ee683589c16d6d043f383ec2023953c482f9c32704fe1a461ba17da05ea2", "0706b6349613201f5bbb9c6125c48306ff53d4688f64dd994405abad1872d450", "b22580d4aeda8ed6d73c59bf74efd26c3edbdeb0865c0c4b6ca61db39fc6fcdd", "978e4abd23ead67962bb223e372c8873f283f2d6bc3b0b0ef6a21fdedbf48420", "d37e209428acd60797e1e77636bdda5204c56af262d487469b6eb069dc5ba0d9", "44622d438823091e0823695e5c08b633b3f0c46af0286989798e27530a20273a", "8902b51c808d5143cf6e368faa11e4e86ff0d373cef041553662da373376ff59", "8250faa8be69d0ccbc2df66b1046d1ccd6750503855943542b6610a9a6e9cfc2", "e75d7f1982478da0379f975f964410f4e5645f954ace65f0ba0eeb1ba7d7b190", "5836da561d17e30faac4342fc555878d144b1108f27112af7f425aaf90f42efb", "b0d06739420bc6d96ccbae8336bb9b6a28adcac61f1f5712915ef42456222332", "c8839deeb39bf4e9743d617cf5efc29e9a59f39d681128baa4e900203acab6bc", "9fca90ccfc4d102cb60b2a6d992c9086a71b1f742dd805cb40b945e598bd255f", "b08651ed30172874bdb63711d32ef549b43861bae4cee530da74b7874d0deffb", "f59d3938a18249d47eae4be568d3098688df1c5eee393a913203af87f92ab871", "68b30e55a656422b4f7757e887a7356781f17ec91acd25d2f062bb9012741423", "ba79b09ddea8bbdbe7723a906c367b4a51cd8aa47fbe2836c169ec28b4e51af4", "51b2803fc4d01eb5e9f011c74c5e6b294327f44052e9e56fd0b75475b3f2167b", "2a40ad807c8ec22752fd4886570008b62762d208a5ea24140813808b64792c48", "f2abe05e84099e996c1f9a2be789b77259322c5b28a1a24ec418038e77a7c252", "e39996b22b171c30c0d9d7f3f9b89c8cdde606af69dbf6936ab50d4a8540a43c", "6782c67e3849c9ce43967ee303d29b12545af84fea12c5cc4cf1f973214eb2d1", "3477e62c947ab134c3242522425c234318e22998b4f6d7b08422427e36d01004", "c2020358b71b1f043bff47e117027bc8112d4dd0d65131063e667da9e0974357", "5e3c95247d735f46b45940288d0e8c0016ee553c4939aa4192ba7e52cbe63b63", "f3ef5179680400a2a83fa5b01d823bc3906d68ffd29ef18923262472afb8c685", "5a2f1f9be05ce5402fc0728614f98e6c5d8a30a7008fd7114d2e32f128b99468", "80489be62cf13a2efe0f72ae08422eb8b9a033bb24783bb075e5a030b12f4d12", "01aa376514be84131de256c9fd1f3cfa05edd4408a332e699c2f0512e8653203", "6a59eb72f291d9209aa9ee2580a977707b28e3714d04859352826b7003759f1a", "1ed1699d9c8af25571a1280b6f5251cf690d0005bbc222829ed1b5c8368fb7d0", "2b8966e5eafc875e7df9b828674d7adfca2225a5c5458efe5d3490932c0011be", "d0f30db6d5b92d763aa39c910bfd007d8ce08f58cabdfdb67e38b12478851a81", "2b5370d6abbb3e0c0cf3d9187e5173d7784622b770dfba6c33b8d672e22e12c9", "7a874cc8981afc43943b02be3428c2150ca2d94dc2735904be475872fd48bf4b", "ab8bc740762787a90716c3f1fee072e57031a1525d52ce20214a984e793307b1", "40983e94cc324c141ba33a7cc5682f3f187d832dd665a2503c4101ce3710b2d1", "ea73153725b2ef43b2e10a05b7426aa8e241284b1702214e8dd9cd04b38df68d", "4ab724b8efa9a325df30695daea6894d5da08aaef739f20e716619f4e595885e", "cceb8bbf3b3bbef90da4b219fe547ad6a3edd9dcd2ae48066f2511a8769e286b", "b8c442596d32a409e8fa7b4401d52cc8cd2e82ac216d374933dd9013535b443b", "0a7d2aaff8434564372ad339e2ed316650f490f9932afbc9cfb5f9726edd227d", "117e018ab57319440ca476a5799a3eb87eb7738a793fde1b95c34d32cbeb4522", "7c84152e37659e4be0e0806e11fa7ab154e5dde6bba50409c8c475f480016120", "4408ece10877a6ac3f4320941617b72c27fe122bf0a0b94932bec6f7f6c5953f", "5b425b6d0c9bdb4fe93fdcb1314b2ecf3cafb77cadea5a3fbc1a377c04c77aa3", "2352dff4400aeaefaaaa61cf37512d2076e3f5bea92d2ad51aa99f630ef25a67", "08c9db753634d99a25264104c5b816ebc15b95e0d2f84855d32e52aa90aa5aa7", "91d5571d7b2e0566426cef2498a5690d32e30268c0a3fc17d81e4d3acdaf65f4", "71b408acc816438a0acf055260a433b5b0fca4a71e627e54ed7dc96079846c44", "4c925a3c7a5c74d7ddc2095fd3c303fe9af708cc54ec1992f89719a45dd2e98e", "60f56a735c8f2f31efd7580c90234e9fc622efcae366849c63a796bf80006a12", "43961c4f8130c54f32b45f9ee39fe88faab957a734501e7b49e7d7ac8f81ba91", "5a503cee0a815b1fcc4ee6000b8d88e7fa176f7fff7ebf9abe82379a9b87037c", "b19e6f323d3ce96402d8ced832944a02728d9df0674a9a7bd8e18dc8896de94c", "a743c955a7b559a34cd8907b9eb7a40d86f8f15a58e90b91c9fd87414a91b3ef", "b40cb00eaa805c0d27e86cc289e34dd354d820453382954ed2ac24b27d38c2d4", "e6016c78523ce714a360f77ad95b39bb8a724277430e6d2ea5a2130334011727", "e8b448a80c197809e559b30fbff6a7a99d1bae7409ec00c766a129ab70e47f5f", "4b42f9bb88185504e200703c9fa8dfbaf850978a60827cfe7688c434c502de0f", "d48a1aaa1f36222f4acbaaa8218e249d5774acf8abea087c9e2ee9e21dfb2ab1", "cd11b4f441f834863a99988fbecdf8b19be665edfd19ad4db62e9d290a98bd02", "2d6152c003c48f8f6a1c2693dbb5cc5528e7e164a16beb798c772dc85bf2ee21", "0f9af43eaaeadb7118498e562e45be1ee1e9b7f3787cbec3aeadf671a2c3138b", "e87a2dab8e4945b8ad5fb7866efc8dc76a990638822542050506d1d0ce78fcb9", "190a2cb2ea8d06d989d23ff075bcf61b236841a27975f89bdc085cff823e55b5", "9b09d9ad2f3a069a4c9b33e77a833fdd6605a2095e8062f8b79a5fe197dda466", "06dd4f3da3273bd8fe869a976006745235347ab53612247d3e0428fe152787a6", "8dd9a7dcd863f7a8fe98ed2f452615a74560ab7ab964ff161834a6a6d5b21b4e", "f68bdbccd9955c40848cd3acd5133f991becbcfbcf167e5d2018633229d1c0ee", "d1990ee38345d528f0115a99aad45cf41d3a579ee1be601bee3820f181819f4a", "b09339818aa6b2bd5bf955109969d4ed43830a672c479cf34bca1661e31eacf1", "c5dc68711d6a27092ee6db8a779fb1972d769a4d571b759e6bca257493b1031e", "6f7e4d57051949b2abee3b329b299d5a6f555d06cdd83811fdc7d47531ff7179", "45862ace8f36c0a3a6d4326817f0f80f3041622e85e055e2eb89dbd20d0df324", "b57841327c49f6c475534d0cd18ff578958790ec3c819fa5b97d8971252138e6", "e83615f0779683ae32d0f019b20cbf2da935403f509bbb9d2856dc6201b613bb", "be524d2863d41baa171561328c9435163eca92d6e085ebbc29a4e1e3cc6753ca", "9dd3c020ae3e8be0f6fcc97e6fb0e8c76ce9694dd5ca8a2e8a122862f552a421", "a7e5ca5d0be1d24c69f4992a3c1a8f6acee7929afb2538045cf737a5da62898b", "0cdda68b16cf1e43b41e2d2eedd6547972eeb5491930f9057a3c07743219c1db", "5c83bb522e9a09d6c81af19b7802ea30ad22484b2ef0c609ade92089e7cc7248", "078a6ea5a4b2be65c7c423f7ad5e4ad909248729b08264b8f880ac5d90f009f3", "47a73b39d4c6c631d148b9cc31dd43311d20d91592a9ed38d87579491cd9d855", "7c625f9d16a27bd30064682fc896a15c4b504819233610fc4a88cccd271059a4", "5f4c8d2cc5c67a0c393493474e74f770f8c09751cf4d712f0c906d9d3903fcc0", "60a628f0347932c8679436a3990fe3dcf4d02fb9c24fe4fa9754717c176591e0", "2fb12765c5e1eb877c55f574c7dc61a4123ebf7c7e72cec7d7e83420fa578853", "2ef3b7fb03472c1f5a850b40e9b35d9a35d87f05292c1d0d43e863d7e7ec6b4d", "16c54fff31b4da393130f6eb18111392a96e85421fcd1e928e17ae6359172221", "56ba9c544d0ca5de806803a36a1a19f53ba914f286d92bce307f91eca1bf5652", "e8df51a49ab47130db5332e1dd3f1ddafcc2ce80150ae3c37eb100f5627b6bf7", "3df4f7f14f87f1ea6df31b9b8269cbdcac2d8590a89a2753d7bb11fb8ec576ce", "ed2560a20088fa40572837ba321394fb3665cc60c15b19a2fd07333101636953", "a5ecff5434cd0aaa835073066abb2b9f9e493dc4cb7b26983f93c94016c09297", "af3ef059dd49490d483b8b9a99b245695483aaedbbab25bd1a54852a26b28802", "39d2d8d4da53e0c373a1e39b4847821317f10d9fff8b7ac598b59b7e79e2be6f", "b1b6815684cc275278a6a3b0a7de9d0c7d4216f8f1b8c8f1d075be64f70b79f4", "fb2abc840ce8866537feb12531f420dc89ca9de12b4e192e1ef7cbe765cc4816", "c7b6c8d3d4ec9457b4caf29f6a6198f893c51263d73d0b12e8bcf5630fea1e7f", "aa5ae0d35bbba924165abccb826604c80f6ad55781c49e6016bd8207196f66bf", "650d0eedab56b6492743e7c5692651e8aad37d1a9939963141a67482a686e9c3", "22d0b3451a44adb8ef87a116097e3ac46b5f8345ebf0e5dcec960d2d55a72d93", "e3110bee29e6162f431aa68c170d622f819bc4e289f6c3e1d695cc444c8dc171", "92fc6ae91caffeefc1e16e816a0ef299e17c63a968d41bb91b7a6f587d34f8f2", "76d986dbb1668f0069867df25251328e1aa15e6f31233eacc856e61b5d328e6c", "560b821428968d6304aa517c6b0df4469059a097171e7180c0bdc1de4c8c2dfb", "199db247cd1e61526d67823aa89c7d3e9a849a1c48983902f4e732d37491ac95", "f3000de6fbdf5997bcd5067bddbebd4c1057346a69164446e4a2fd0fe575461d", "a36d62775f7abac51834f25572e05a0238de20394f0b8a5cc1f33b47984c4a02", "b6df530ded76cd3cac5eb5f6516b7b5aad5ee43beb0876c8f1eddc38f4e173af", "a939753b3d570927cc8d90e512239cfb6e52d81b5d56ea80eb4d0c46572d9ffb", "915cf3bab38606e7266a5f7c2179ad469b07b134765900ff6ca2a5ab83fbe80c", "c084076c1d75861928f6a28f566527ad2913a2bf829489f57dfc8947c368c50c", "b71e574bfd980be24d08395d32430a000953a021556ffc4d7693190c00e74e77", "4cb8e212261c1ec6fbc52df8cac337d6f5d189537645f7d5a7f911db882db716", "533abcd8780f59049a8462ab7ef505f5ccf1d342150c30dbab5949fb084cdf21", "db533c3913044c03977baf092f0156071c2628208d14d81872162436b87123fa", "ca8ac0dbf15bef994221f78c0248b9a6408ead1166e623c6db7652a16c016c06", "0990b3a317a95d36b6b6ff1fc6736fea01529a39c0fe06e49b7fd564080b6df4", "787469298f138d1c490251895a85d6080e52aa1df375643d195dbe7e87847949", "68a371372ba0f489c8ab8672e257f265a418e50c6c969bbec4b24105850c371b", "f8ba30581f3cf31050db47b7a43a5551d13b9ce7001c896bb79409f4f1d0a31f", "23a5c21151808ad600e97139099b79c3e1ce23ac1252db87b2d4cb88359cde4a", "9886c12c93ec0ea5d14478fa4a9a38c4a1025f8b9d595deb371d6aff79f93b04", "4e4f81cf1628b6f43db1db218773db5f7a405311aa7ee5ae2072148a867a1437", "a019556336364cf6a38501be26e917b0aa2cc2c37c137fc269659aa44a3e5ee8", "7c6b6a1324fc40c2373c6215ad699f723b826f02397eb6f6326c1a5ed558a115", "bd21001934e50a47ade3d713cec8dec036d54da0a976ed3b690ac080a7bc9ac4", "4db0292758deb6ab35aac12fd6387276b2f32cdc859a15642f01931c845fb0ef", "5431a87a0cd32b11db5ced545effb22f220ffc69a60ac552844db86bc7998e84", "c6f343782af6f6ad784f9f85c1123fba0b82ac07119a61ac39ed2fbd92fc0a90", "c412d2dea34ebbda964b17cc12c1da70e7dc428c92eaf494e17100e9ac65ffa4", "e9b947aba6755de52a67725be3849e3383e187099aeb1bef5315d22609368b23", "0b2d1949bead9e9995b717a821f6e5dc3136857b178638350a16c1a32149c6ff", "dffb51c4bc98c9f0c07ce18a88877d48947706cf57f56cc6a29ce82cf2f74c07", "97dbf9a48f3c92fd4674b20ed6f635bbd92af003de523feb5ecc4758169e5857", "cf701be33d1b3abd3357a74ab2f7f03fa78f7ebe0362994256020fb1fad75251", "fb26930bfdbbdd6f69be65c3c01536e09a30cedb747b69719035e31636e47937", "5725b8ebf2345fe7e660579ae94b84e251259487da4428a5f1f0cfec19db0639", "61b92f8043e5a035b2144fad7b1df3ca7130c56cabbe0dd2757dd737719719fc", "35a2f85adbd0b6a818d84a16d8ccbc0947bda389b6cf43ce6ee9aa9b4aea19f2", "69dbaa6d8a1d44259bf095b55311dd39ce028ab20de30ca49b1a173d6171109e", "3b68203efda022be691480952c5132129d514b2cdceb0d3a8f137595be7f1c25", "388d3dd82eecf369794186b42c964871575c03fa9772d57d31280d678f87a636", "6b493f049d19b3d1e268babf0211d48abd018c912787a913ff71457d54ac3606", "53261340605f5e63ecea85eabc5716f31be1d16d1c91c04f3a090773b288e62f", "7bc9e1a6b36320bf97e60da91091c0ea848653a56cfda13f129e42719623c500", "7347ad263d90e20635eca6fe1bc89df06a4ec273ad50e1ef78a27fb9fcffca13", "fd286c0a1d9e4a0e0aaf97b7f2da4b219e385d7a9afc4982698574d72ae49daf", "0f42f9f37bf77fc47e1c75e0206654e0059703f2b7dd261f91719e49e586e7ad", "5c1eb8efa7c26ebb6a3e2cb19148783df0b7d5dac0e80b3c793ecb556166a88a", "0fd0ace6df8a7ba03aa6d52f78c3e58a4720a3852ad936bba80e08bf7c61a287", "020d473e1c9504366a2204d566b1ca6c968320e30382129f95a40c739cba7f19", "ff7051698eaa84a3ffc25d5dbcf923933a1a59730db33e8161698160a090a45d", "df0b1d015cf77e47512cda3d49be662782e52715fb747cd0f73934109a066ff1", "930edae2fb341f18849c9b8aace01d5ed2cfaa013f59647cb542daf33ee60db6", "acd5d0212d8d1bed17253050038a481d968cbb8007c5c69f35d328cc887723c1", "17f76ba6af39c2d64b95554ba27b12818e60284d166a9da60a3110091c1dc3ec", "e03914821b7b6185e239eae45598d504558175443c4f34b700c2b329beaf14cc", "cbde6cf03818faf19d93a082a509c3601a6b043a66a222d389cd44d4a91d38cc", "c42abe41dfa793e60e2ab797e626bd8a5904e03633b61c513c9f80c2be9ef0d0", "b47f9040a5561c94bb5c11ac8042f34d80e144a3f5a8b7c0e47d7aa3c10812ec", "07f44825dbef5d2c5fb089411e2eb2d4f7e7eeef6697852084acc7b1f48aa77e", "ab143316522be7e11b267b89677251a5a1d48ce7c90ee27a6c66e1857d71e576", "3e03c42ebff10fddf113e731d91c96cba59d8d29acb8f6e63e0fd171657414d2", "12a073e1548bd7551d477f3ffaa790d42105596f7c161a623650f1a053c6f053", "4882fb1b192fe817b836fff3baf788d89442f75d3ae7a529297febc3ea896779", "a3b5c64eb6d70663ce13bad27c28cfe46ecbf721aa12d667f3903e155f37471f", "19283ceafa4e91731909817f264f997836d529c523881913fef99c04c23f636a", "2c9ebde51c783478616c534f8cf30c1d9bcba627e82873678054f8c05f72cd20", "6addbacf1779166778a472eafa5388de1e51765c9264db7f44297808f30cc940", "33c39d4cf80eddc5b93cbf11f5cf6de02023709b71c3388dfffd485becf93de5", "73d7856eb00d8f0eef1cc6ebab299384aba68e5e7c90e4526c4a33a3f7b9725b", "f45968304cd3eaaf430b7744dac3bd2c287c51ab1418e02973fb2f6bfd3d7847", "1e18a797ff5a58a2a3251358d7ea2e84895a939dd63fb5a3c77753f324b9c86e", "3ff531919376e2ad060436f9d27129b7ef17fb8ff29cfce1ef3726833aed96dd", "92a1626588c06d5a3d74a59f23e506460f99323c09d35bf5d49bd73450803f50", "be288f4cfe34bc80521860940d76e5a42c85f68ca190a4ad71dcdc18c4198103", "9339b6786bf2c8c1dd4830c384e03dedac22e92bc1aa9cdc3449c674bef72ca6", "1b22a0e578c641613e3602764129e027e101e2d423d9fde2a6718a7dbd726eb7", "c6be938d80860b8ccc96ba087fdb2a00d980808a61dc79483710ba87f1529dde", "4bbb241fdc1feccd155ac9feb2ab91cbe714030cab20dfbf34318ae72ecd4a6c", "706c4c5215f54df3c0c256e9d6c54de897716618824d1fc630d00d3af059352c", "93e883284fa263b442a033252e84dd637a6943f49f9db224855327139dc8417c", "689dc122cf1c3b550ac11e0041b45844b794a45c31a2896a4238242422b23819", "1aeed96414641bbf27a32c1a94b5bc224947f87bb915a53dd2362a5baaac9ba0", "0c0f53761b2c3f168b01cb9cc05894cb86ee53a02ff0c5fd5f160a8d0d15ae76", "da8b72cfb9146b496da6719d87da1c52f295086935e1f15da60a86b24bf29b97", "2389058fa5e0174f217260522f49d07b76c7758b0d3f7296809104cf78561b40", "0a59439df43ceb691a13038b87b7ed5ed2d05f7acddeb2cc502d6df537b71311", "ad9989dc2e5e4d1a473e2f30f9581ad5dd161f68765adb6d2e70c8effb23f3ff", "466309e21fe5c8555a231e5214596e196ad44683a8e8376e453daf42b8085d9c", "a6ceea7c560556cdba4d7b433400688ffeffcbf27bc7d05ea507dd2d4ce948c2", "b77e4ed4bee931d43571d6f22f0ae253ae2dc63871c5e4845c6676c7dd3f0eb7", "7ebef185856fed824ebc3f38b79f82746b2983f8106c2ca6a8b64e410040de10", "e9a0458703175d02b8fce2b8ca87d2a6062270e97499130aa81aea621b42567d", "ae17cd0fa9460c9caf2c158e1ac809d0baa510933aca2413c316840ca42d69dd", "0d485a3ddf329e8b8dd47b569c7ba6faf17d4dbe280521a520ece56136ecc218", "20241e5f5bea83a9efe54520cb4e18b2bbda3eb83b0875f44c62994cc2f4a481", "ecd706d3f483600f37f3b2b268cf38033db1290e0359a089e7dd44d35300eb39", "326a9ece9955f2f872f0f6e401ff4281f1992d9f22f247ecaf25a44f5661c732", "36f0d608c831ea7365b0ab0f2d78d44f9b6cf0a3edda625d02a0e8db1250c644", "fb476cab0554ccbd17ef87ab086fb70310f1b468e61050e4c47a9c003f71a88f", "eae0d52bc60c959f73cbf3ff7a84f1005b935e3d71b64dd076f23851b61e19df", "c8320f5862f6c97350570d41ac318ab729aac137043d0ca73f467eca670fd2cd", "ad83f844f80d1bdc54559399d55f09160e3041f63bd85f9482ef0e0159e576eb", "faca90225e0b75e9ecdb380a4f45937016f843f188f48a956b24601dbe2e7eeb", "da4e04a00f8b7a2724c60b78a8df4caf6d3f65a8f5b8a86561ceb9933eb87a72", "c17975d1893a8b62915a085e714f9c6f85d9442f7916ddec6a822090c8dc655b", "7b7f3cb7bf35478e8dab8f33acc8746aa6ed70189e0daa8e893783deb55fc50d", "d0311b9d76278b80d7f55b8c4bacaa8dca293cccea20a784ea9fe254abe93b5a", "91d99863528e63d01fd353457a910ad683d11614458708b31fae2454fa224b5b", "b0ae1e07f65c9dd764db153aa46cf42f68d780e4b28e642a4559ec90e8e3cc39", "43fea848ab8ea34e591ac9c9f98783b3f83a812a9bef6339e81bd380d4d0b0d9", "80695fc224bc3d9f16e1be9078e62d91b1769c4147dc44421531a213b4a69460", "ebb6cfe7e39f666efb4e256af94b5b21aac14902ef3c23e6788ffb32d16da24c", "ef5b6beeb6cf57ad290d3be9fe6790221fe4685d99ced85082f66cea6b2e2d96", "a4556671f393544c118880d5e2b6e0b6a9d571325e35972c8bfa5ae70a9aec8a", "0df55165d1eb0fdd4b62a25222e060b21a4e5be7b8388e29380b86b2940efdad", "19b60ec413d47f58a62173098d1591609281e701dd079656a09512e8684badaf", "52e4284b527671369be86b4b20545217254f85faaa8abe39953b59fa1557442d", "8eb1a4325c5783a09e0febbc365313f3c4d35a2c1618ee6532572ab2ef1124e3", "48a251c051cc0c8b051b806600f00342ab81e3aa111e066e74adc044502379f9", "97fefae91a85838a8b93a4a8cc0edadc2e50b43c1ac0e36a259a40fdf8a4e213", "aa1342bfc905f3f255c44aa09df477228c41977c060fb5f936fc6b4838c5be7a", "b9e6594d64492899962352ee5c918c3ade3efdf92e16bd4320e0da27ab3ce2ae", "1a5db6b7d6da5386f76ef77cd6ddc99ff67de917819afa746dc3c5378a95f30c", "bf64bc337a886d5d799d839f03eee210acab95f613a17db30165d3e249d07e87", "37b794fdf56c4ab8d2b4d00506ae67f02060625d55adf6c208cd2f53b6787cb8", "7df41b919abd69e7acee85a552ed81023aad7a4f1773b35f104af8d253e9020e", "71be6114d2cd31bea00baa69981edc59bfaa7891ed5849178f3711f37e5a9223", "7e8908c6f9e14300d44c2254d022578f689d8c0cab56ad73ab97c748a71e7371", "06a70fc0c9e0e0a3a67dfec26eb5367836dc932f20f65770cd27511f76a4ef7f", "5f902ed069cac194a12c903fd9231b3b9b73ae499e47206179a5db78053b7d48", "c4587b59006d177ecb76f64a083c8bafc926b243a6e9ee6ef12bf0f3fae367ff", "eeff57364b4cee2e43ed7811728c6e0dc155c94bd8630567981c00e7983c202f", "d9ed39b27fc2cd3e1c3bdda317c856557795363bac22e5475f58614be9da5f0a", "5fe8295650a3ca6dceb6adda98a9b2a52c8ff5aa2b879dbe74dc479c14df783e", "bb74a5396ca5059aee5f6973f760285858dc7ee84f34631100b641d8f48b89b3", "bc357b63fb90baaff808482eb645d5523323bf52d98c3fe493ac8eaaa4773677", "2d052d15ac1ce4eae8e7988c586779ca83b7f20134899d1a72bc05bc94c0b35c", "ec20f72f981ef2d1397d3f05c0cdb32110e4c7bb9b876a9aa8296f5daeee6cc4", "039cb433d2315ab0011d4f1b3d040ec7e1f1006fc3278b96e9a8e0491d1a9d60", "2dcdb4800462a1c11c0e832d04a1c49d9f62103f2da332286c48fe94b456b92e", "4a8b6e2279a7392cefb1e7da03b42371a678f84c856de77cf13ff9c0891d9b00", "57bcdcfc0ded16c30a50204f409dfc81df4ad4b1fe673d99920d9f79a397d8b7", "0261b6d4b9c1c5a585ab93951761c05ae9cd62c56359dd821486d2b1fbbb3177", "2a71c8ea5108d9a459c6ccb1a614cc2546ddbd85efa1eb39ab3ce0a504cdb916", "251698409786d137dbce1f4490f83fecedaf384809eaea793c3e688bbf61811f", "2ace8689de6c19ba00afddca95b6c4d32b9929390c628b9339a77ed21dd9ec97", "10e81239fd71cd6fc6a7b858986c7c4e1d064811ffa0cedff96ec34e3fa9f454", "1981916f528ccbc3547bd0daed092031c4045e1d1426398f88298f7d29e61f8b", "271cf2cafb0c86c1058d1247771cf90cd398916ee1eb4988b19765673a2c03e6", "9d086afd05abd5ed8e554891229752b2bd98bb124d83e5c517c727a6e41750fa", "5f2c7ea24040a74f3badd941fc602bb8ba2c2f3dc8a6f12bf3565579587b5ac9", "0cd14ff3e26eb0253503592d3c2231f067c0d34c9a08478b3ccb6f9708e63bb3", "7d8c41eb7c106d34679fda959f40538e268441214561488988384d52bc4959bb", "ad844d292ee314dcfe7b9673493aa46fc09437a3215984514f7d6e25516d82e1", "1a2a86d0c46010632d2cc42225c28e81d33831a762904c07fc165696e0b21f56", "dd5549881dea36dc21d79af4fe8fd523ea7198354b09f11d45cdbc16f2f1a593", "f163f190fa2603da18b5c4d6a8ce38135027e1e27765786dda3d4aea2a9cb80b", "6e09fafb8b6e87d6189f46e244bfac72ac097f881fd3e20548bc9b2b77a06494", "050e25827579544b11a0659b33779e36091a9386e10529de15661476f621b4be", "2e106b4ee4214443a32a625a8050bfbe23c994d5d11f7c06604d67449dc4b65c", "f46f7dc3ed0045f94584f0638fed6b4a1428e757d0286e64a7d09b90bd379f44", "4a2c43aa7fa22812393b64ef4735c4ce9dad96b2324d06204d17cd489d7ce412", "98862e2f2fbafaf00755c99a60aa0476cb449041ee71556e1e7c6442e149e51b", "4c118375e7aac9cd504042c81c94f58f123924bcc2dbdd07efdf3ac283bd06ec", "bebddec9428e7802423acb00e58d998f5daa5a26bfdae57697deb463e9e86feb", "53b03c24b8c7b3c56e56ee1e708df3eeb032bf383d7cb1b2d3fd0bb11cb984b2", "784badbf46476520b5c6635401f74e99ef7c7a003a393aa1fd57867f185dd721", "2f3caaeb46d182b613605bcb8bedd3831bfd1ea4e7a041c4f76e0d4718aa9eef", "1b3aa9204c47e2d2ba2657e13382926d2ead35d868353551eaf9a66a70c669ec", "c9f2a7d878c3f80d7627ae2b832007dababd27fd2fc13709901faebcb14b2932", "5a39dc81cb0b6518f00f5c66ac659dbd72f881a78e0c0b13dc88ade430abb90f", "2f0ee5fedfa55f94832fb2744a80af32bdbf7708ba65a3e0d08b446358da1499", "1d07c7dda8607fe8e06cefe30123fb4a38302ca4e091f5ee9df4013778e13fb3", "3fabeb2e7e8cb221b62d4e11ded6d5eaa1db1380b7639c943f60a1c5c30cad09", "51a1fd08466d6b37cbe7a6bab184c21ca50c9feb5938283d58d89fdc1035fc9f", "0708c2dc87f7ffaecd46d3c7dac910700bbdd5f9331f262819ec9fc90545d3c8", "2d8f59f27fbf1306ba8453c032a2d8bc6a18ad2d8f3fec4ec260af16f6213dde", "3a7455c90f216f2692b108f4c907cde0f64872ed13e6f75b44e5f857695ad824", "5f1fe505ad82e5de86f16977be619103b511b0ca09393daed964ec61962cb942", "3decaf9907eda934c124f603d3252929ccb9b99aeacf745018f2cd612ba3dcdb", "4d232fa8d81cb6abd1fb6806b45c069b7fa7011248f55d1873daa335312dddab", "55000d6b9fd4132be58fdfcc87b55b28dbb2bc259c33d50e03a9d470e503553a", "225d9a9f991b12fab890ccf06ee654afad4878a3a8c0bb3ddfdd54af3ba74ee3", "40df7f285dccf966031f1e8815bec7473a748f37c9405ad98b0ccd40c87f986d", "c4156b9659801913909aa5955548725ed2a251e9d3b3a587786094dc299a8f61", "5dc3a95d6f96b946237a9977b4c1e05b24799729f03c191b084c6118106fd712", "118bf0b7868f02b1154198107b4a86873ef471153967ec7bb11341caf70c4355", "1ad3a5310730b0b698512c8c7d3e7a8552f75b5c7eec4546860bfdc622f75e7d", "fb74a1c13b1eb19423dd805a4d85ee771ecf52e3956b51b0409cc5bbeec34569", "7405d158d51c83cfb8dabb3201f692e3bc089f020cae6b62a2af2c88dd8f03ed", "08f20e5a8dea1f3217c990bc112fe510ca5aacdefabd5a2a6958339abb88ad7a", "dec3f7bbee141e55a68d1d164e891d9bf832cab148061a1551475fe33c1bc868", "0a311678a6266de62ceb20154e6ba5ba5560507d58d8c5798474967b4924651c", "b4f48fd17a7cd9e0b26e90a8adfa2f9a150d47e9a203cb89df114585645c87b6", "26a5c76a25d02b0feb4b22e549ac88447abb8fe7c86196a73292f13d8eea61aa", "2f41b58911b04c3418bcf76dfcc500d03a55fbf1749ee83a4e981fce4e32eb4a", "411a18b6785d5cabf9b666a9a70cdfc5a1e29228f92f80b9f8d613face0195f1", "b17d0a2cb46dcc365e065267bbc2cc36e92e20bc0ce24d144089d69282e6fa19", "30ede26b25bcc2e6cc42f248386c61499ae477d4fb392ee289238c40c88ab5ab", "f1bbaafdc5f0e00a5dad95c9ddf659747c74d093e1cba8a0e72f1db1d5cd904e", "09e411ef140daba69cfdc2c3c32fd84cd572a842f53388124b51aa2eb1e40fa5", "2c408b685afb2574e9fe2a212e92c638090e851026ac80c9a639daf234fdb984", "a342b54ed7092264595569a37a5e5140a48d5117f62833de3dc1923516d5b917", "b90af846ef17cbdfdc06399f2d6790194fd2d781babbcb2c3ba005031a278650", "16c65a8054f7c7c6beedb172498972f2c3dcf0e8da240cc8f120dcee7439c95f", "8979da949593c80f9164828107f04602d70ca494947d6ca7722180ca85c8c0d2", "eb4ef64a1eb138e6ec7414b3d841d24e61d6aca94a870d3568f89bfeec28ce5b", "8db828055ca1154a1c1b60b992299b2a3cc9f9ff217e15a329b642c8d5515344", "5813ff09a79cd74b6fb3307c277caf7e80f3506afb677eeec65555b7fdb8bccb", "e15883831714acb3d5c08a3898ddc6280114f1b41c450f6e93a27bb36e7c6766", "95ee3e0acc204a6bd5f5b484e907056695cf5ace25449fabe87f25d61b1262f1", "8eb0d5da9c247c962eba9081b9b58413b8f7aaec03df2813c77ce44573a3ab1f", "afb841db4f6c64fcfda654cf058f0a883166b4066fba6be6df5dad564da30515", "68fce267894ffd76f551a169c9508e53810bb12e773015aa4c547a56a5806fee", "6e614d1afb783e6b45301b2fa03788a1fe27f2808cd2b513eabeb1226e6241dd", "6bb0cdb7d8686d79abb5453c3f5045c1acc2e268b3f2b32444e60796a18d4c12", "9b99c863068f24297df3431025ec6564b66f2b9f64c1678b528a1dbc4bf71b16", "204b6f2f3ec5bd0f1907fdb460e4ed6fb0d25de5cc12f777a1ce10aacbed40c4", "615fba5e47ab0d959fbcef39996936da656e2615b954f03b61fbfaa8e1a4f500", "529895a7de063cf6e2497d30d849a8df3c4f7339e22a486044cbb3e7496fec22", "b7fd2e4c0b845850f044f32c5d5123af9d5eaaa693d4350c4ca8758bfb857b19", "059e015cff4b33f019921f9242533cb45cd65e507ed882205367b746b27f4442", "1b79153a3a25bc82c7f52a577c140d85854d76b3268e332b5871a4de4eaaa47e", "b9730c36bf7402a5d06c8226dc11ebec9c0a4bd6a23762a6e9e78d1b996a4630", "d22427bf91dccfacba55357d4a8038f797eeff2c4dab56220cb00d9ae897b783", "da19f42f6dc60fcc3d075d6f38671949ce2dad31b37496a638d341757822e92d", "78132589eb98ac63e53a329f7cee32584dd447bb9fbbbc01e27245ca29c23a23", "e467ea63a727b9c36e666d435664875c822f94f047f60ac0d89f2733bd4d1f01", "f4f89149b1a5779dfdfa3a9b7dc5b88791deb32c20db6d611fa013b9a2eade6b", "7b40c196aef97aa032f8a1ba0b88aed12baf4331acacae6513e8f4fbb102dc98", "dc87f4206941dfd0431dbae606358b03741e52c9c9830017847042f99caa1a89", "293c650a8f2b442da199ba6dc31cbc7616c09bdfcb685d216fe5f6964ebdcc19", "cf3736739c87082a71653540be254cad9dd2b80c788910ff51833053de0f6833", "b7904a9d282ee147c41a87ab1de0c68f6fe6e8681b728a50b07dbf82ab61990f", "ff43760bacfbd8a86b77ee50524df729bfc322d221bf39d73fbdcc5172be25cf", "94b19511a901d6c9863b4e698bd3203bb45f459a706f17d5fd0217b7d4d2e880", "5fb42d90123e7d17bdf84717dba17f8d6e2e4cb9856ebcb5dbf6892fd227d4f8", "d403da452541afc98ea45671522db8605d28a1373baa96279149d70fec56e8db", "c515c1f3132d7124546c2149d2f96bf8899954ed28db737d81149cbd9f84ba87", "7559f506a7dfdd3ac7f13dbc616629b56b88f8e43e6039205182b17136e45e6d", "6b3f153c83caaa5f7bff608f4fbc514feee1ad49652691393b26e60a3860ac49", "b25dc960443d800d107491ed43a224db6df66c12b02b7dbd3415ad4cf38c1f25", "a70e10b5d457c0c10ae765d7696e96d1721bbd0557386cd00db27f7dd61c8039", "c12df355cfaa94c9154a29848e53dfb2d1bcc7b68cb1506d067f5feebeca2134", "c9a697b7434305777c8068af8b5bfd654d74bc5ad82220f84fe16e1cc9cb2173", "261dab494a2e8adcbdfa76b171a1dfeae0a70cfee528d781883537c35ad37546", "df2aababde59eec1b7b499858984c1204557f599659f05f6671d1d66d2273d68", "36bbadcddfe80758e7b91dc8bbd2d2cfca89aa1c50ad41a706c99bd192c1042f", "bbbd1e0d041cf1b340f9b0873d876ead1b76c60f593e8ba82e2d700309ea5b4c", "07708bd4113b5e2773ac0d65323a793e5dcc366b1260eb55f6ed80f6fb3eece5", "b7fd39d21af1c3ff30225230a86cb382680bab72cd83c081495df252bbd31dca", "a01f7348d23cfc9c72d4c6c8d41d00f25331a9f6b28f704e314f46b9a5fe8836", "e14b6869725e9f7c8b4d0fbd88d1cbf9a969e800bddeb3b426ab13a9e1c6873f", "ad16ff69baf5690783aba8de17d09a92af4fe62a985e33c0969ed734d09bede2", "d3edfb7f2ee7cd654793fce245666efe24655095b9098152093b3e5a12cc41f7", "50cdf981025f02190aef3c09b5aded26472fe5b155c689acd1600b6f163b0aef", "d944eee476fcd32ecf4d85d5796e17ec2adca8f9f6ce1c1f66687e2d99a29f2c", "6eae57da9514dd54a3f5920e1891529982d88c17e7ad6f6d8d24c731e1507992", "ba0b8bdba07211878e29c71e21bb5aba5186e50fd45b4303f846897b8c409ae5", "16828f8c425552366cedc41a7ca7f0df1c5e5a9dc543bfd9b0df65021d087a48", "338222d8ae91833de9008c65cf519b1d021c6072d09cfc08f78d002300b6dbf3", "c0a24805f980cbf60892cd89af249fb06c079c694e3cd84f0cba7f21f9e6fc9b", "fbdde53f5541ec1feec1a381409d5ec9c6baffe97ca0c7e06f24e841d2b1161a", "1752a73a37c14d5080efc1ec13bb1dccb9bcc0281a4d95cc2ef4b853ecfa6c31", "fd2e0c2b50b472b90d7f4bd119085224219ee533a99922ebd8cb0f2cbee9cd7e", "3a1d28fe96af222b8bcbbd2e937ad0d1f4128c7de8c7ae4ddf7015b07a1f6bc8", "7919fe4c1265bc194272f2d3e0a0a0dd4853b9f318baf6287484549b01404b68", "10f6bf39d6329af3916a571ea4ae1de70cc23a9818a866be45c267284d3abfd5", "cb0c691d7266460c4af283861919c3ee427c09831e70161c0b7485b3f420c051", "69d7916a1618b94a9794dbfffbdafe155f921b57b40c6a55e8ca17405d1183b0", "0c59dc8c3caf16b480847e086cc53f4bcc55c0ad0b2d6954f943eedab457c86b", "8accbc6c5c4abd38dd2574cf0a84286709bb377aeae9d50668b2145190ff94eb", "66213a6bb4469587379b204233f5c4cb9213c9443c6ac8a8f5748f339223bcf8", "1512294a5bacf0e03dd013bd22c0469b02c6a56ae6ab03d089d1b59f9bf47ba9", "a5ed327b1392f514a7ca393657194e0cc1f5f454aefdba63e867a3905c9f3ba6", "af21c0215b6b801617c9b590a5bbca4874f5a23e7fff46e2fc380b4e501b1b42", "48d97a310cffb3c3f576b5615ca7d30491461980e9e6ddba01e9ab8b69c6fb87", "c23b5db245f1cc4791a6a7f57dcbd3a72750431e1a67f5f783668c8a2825a0ea", "ea2c2b9190a3a2e7bca55d33bdd1566863284587cbcfcdad74a617a571d006da", "f00c701d6e9eb10e8ef79276cdc154e8ba8c4422f1d08ff330ef3f55d054d337", "43a9d6c9ab48dc22ca3c9cf8250db069e7513537e53cd632424035f96371b52a", "9668811e88849fe80a78b79fe33a05252ec3274a8c4c924609b8c85281ccd46b", "f2f93449bf57bbd79c852a412dc55922802044e40a10d5b70b940a585ee720ee", "d20bda52ea5a7e785ab94177f1d90f5688d21b3968326e9909c8d26cfe160b6c", "1eee37e54171be9e11fdae188b2edfb0bc024b5f94de55dda4b175596d449bde", "0af11c745a8c4891e888eed30309edc37748d712e154a078d4bdd5b13cf220b1", "15982ded9a62a5482a3acc1ad4c33159fe6c42f09aa14365a292d1f8e4434861", "429e21c28b9f0e415e2211ff953a01b408b9399dd2b67d0cbf212653aa9e3de5", "9b21c3118ea6bd778beb58728a3e319c2bdc18fe9bb2218024e4d7d537758988", "730d819c74a968d95a749664b659fece7f28f85ebb9e860542969b1f83f7135c", "07734cbfaf9de00aa8bfdda5f205dd887fd7df72535ab729d873a5ea23080c8c", "472f6c62614c64e30fa642fe8370b2108fc6c624bfc3652ddcabdc943b93d12e", "41161aea39995afac088fa514c8df9905a21984920ab7ed9f5ef52f603932f4a", "ff0ac19b15cf71021ba255bb88b9b48b8d813446364defcbd3648719c0ab4a4c", "d9836a3268981bfe94ad1f77f2b3ced20b7079f09025391357de906d03c40e83", "7e55b991f5f34ac4389f5574bb493fe43493e65668918329489fcd9e473eadad", "d32bc70e6246bb9345bb5efb2ffb68f6173a0b675a8cd4c7ca74b354adaa2909", "b9d8bbf671e794da22b3d2318c9ba690448e3a41f406b903f638b5025f7564d8", "b28a5816f46942f4270bc625ec876659d37c5e40aaa913a6223e49e7576235d2", "43781bb2014fa51a94bb3498c99623b76eb963f48238f9b1df9b6f31322c0970", "8dc87e8f4df3ae436fae06c170909b87542352d349384b9c7027e950b402f65a", "339cbb45be7f44b72f31f96503860c5a25c5f2abde498a93561fb59b433f293f", "f2e6d476a7d47acc13d2eabd4d309398684ca739f8bce57eb55b1e79f3d1e519", "56af0198847aa027beeb25867b66c211c78fddbf74d32c1d833d87c778120fac", "9ac6f60c776459541ec6bc8801fb2fd02e36585debfcf3212fb0b1614ae2f6cd", "e1792f3d1d3d161adf761720889612dd3cc96eedbbe2a432a03f7539b0cf405b", "0618cceaafb6f8e91a6c592127ea2b5b0cb1194c3210c3d643cbd25e047a2c5c", "c7deb398d09de0de32c114870e0843d7700252917eb69fb0546830437308e970", "e0ac7eb0b844399d04bdf65c93459a19b00c9a23bfbee05b3deca40a05b9d389", "23a16f8f604e45d067ae5a3b94755fd327505b4a0959844aab30ff5808f79b46", "488b6589b506e1a4501b2485091e717411867900783807af78f87dff7a46cf0c", "56c965124e66ae2c716bf67050bdb320f38385280e7a7c6cd51bd7f7ce43d32b", "19edef6e3e69990ec222877913340628049da39409aab79c93af2b6948a93d58", "128eab2b73e6a6e9c535e15b22559826c3e9d678859d92653a5b0611acd12d52", "b60504a4e6fb685fefeb7053d02d89bff2c41c86795c4061a89d0c3685da8e84", "6038bf6c7728e0927950e6865113a34a6646cf0ec0a2d15e1f1015b87ed6b091", "1bc443a013d98a82943adba3b89cbdbbb38d8aabbc0d4df57d218717d50f50c1", "9765ae2f7bd51d2631470a84f4acb6d9669f3e211ba7b3d1480b80a0cb53dea5", "cdbb6c307084183baa8b44cd6a93f014687b2e8f6aaae063fec6eb2c61d3a331", "d386012578fa5b91e761a714209d38301129c8ca4d1d393549a4801a9b1e0094", "05387de7db27a628101147c5e01cf481a68866c5f4be570f35a50e5a96dd8976", "ad2775261f5a12d7fcaea9666b48dac6ffec096d643df0bdb53dab400abc9fa9", "c95adaffc299856ba5bdceb376860a43c0a55383ccda166614af9333986f18b5", "2db34fa42ab7e9970883aa5744fd4ae926463a3acbd35ecabd5854f369bf3f5e", "068881adabd87a5d568f27064212ab1bb362583ab9fcae18fdb03dbc0f3185aa", "9ef7cd94ebb5f2b74db7933a06459ad972f43f21260ce84baf26904eae9090a6", "99afd610f6087a27df4c16d1faa3e80af5dba4194e7aad1347dc282f493951d8", "d036a9a86f34c9eda2f4d54a8f9df4c470c0f97695c4e5dc9de60e85af56a1e2", "7f0137290a2f6b51638f1a439091c26c66ddd7afc9a8525c86d0490952957f5e", "a755f2fa40c875c9592313dfad65fbe58d17940dd1fd5ffc38f9520f91b8fa63", "6690697131f9aeea3f3a74f83c6e34475cf3c1d6c63e1555174ad875a908ece5", "26f83c084041837eafe3647ce38404a2e24b2c3f5a870fbc57ee2f75fe863156", "aa90255d432e68be319e26ab5b1423400d2013117121636cb27ec494a887ce49", "72a7f09acd5ab6283df40bd92802a67c66c5308f661e98f3c12b2dd3c26817ce", "de85e7574117c4c773bec442121ac01cdcdecd533946624f5956258644eed440", "51e4500dcd4477c425cf9276a556041162c6d9978d56f394d32a10c963f3049e", "7a37ec2c99e082dac260c89e7fb72c23a1f958c31e50624217391cb31b715ef4", "1611fa2786e97a786d6f0a9eed8bf4b9a30a2158c6b9722eba150b4d53398e1e", "0ce07e0ba171681afaa50f91d3ba9e1c1801f6c9d49d7d695d2bee3ca563dab2", "4a9cfeba7938b7c64cd17a04e6191e9ee3b07eb39720f76794518b264817eaed", "ba2e9a35c933057f7775202da766bd3686c4268f32d9287d8cd3e0a371002d76", "41e92e37ed2717cac094610c3da3c64079d81b0f18adfbfbcdc46860082d05ba", "1dd6a4446b8615ea23597f2f1fb4f01e8bb999c5cd098099694dd2d9fba09e71", "a32552daccda15299cf311e0bb4c7ef3378f303997e5b2f3892cf3265c9aafd0", "4a17194413577d14d26f1c1fce778081c7cedee904af0ed3a25abbde34774885", "2d5b0ed95502bae6f4bd6738def6edf4e7e351f879b8c034646fa7421d0bf675", "0c32676576aa6862d224cbc313ee6576fdcfb71c8041e83a789380c58413354e", "f1c53b8e6989c4f0d55a5a08239393a9b8a5517244d8f04577300048f9e21e87", "4c6e479e828fbd26116908338cf72758557d523d190b7cbe3c33cdb00f91f281", "fcbab6fae7d8bacee71d82f2c1ab679c48a85ea750247f93478baafe4d8682f9", "f79fced898dfdd08f18178825490803c4203a029faf29cbf08d8f1602f032430", "d2f0731c4ff11f4cb6234e6f22717d0a2ae395409329cac53785269a7c26ec3a", "535b3030171da4c461763c488d7da9e89c8cfd7c1c2dadbd360bb99edeb9b0aa", "9f5e861a8376f92be1917f3157180c119f5b2bea66ef40bdfa77ec8f6136df7b", "9a7f91c1a05612ddc81567d6637a6279b614dc9fba3cd0322777f437f6cf11ee", "3e1474061b17403e96e750b3ad725b570d4ca96f98f583e0cd5dd26b84877cbe", "c046e99c6ceb99a1ee02f92bf5099e2c44a5adebd5290dee742cc5ae9da7076f", "0736d3d6b42c0b68cea5a9c774183db0d7ac138e6303036e46da245dda405f44", "2677862a927266eedf5f926a1844495ed7f31f671dac9f58996ae17c637ca140", "df622da8693db1d4245400e8bdf8a28190c1d29c27d30046f9fd1178a7554c67", "b0adea932e628a977282825083c96a26a276dc13e623380a45a590fccd543be1", "1c54ee5a29b8ed8013b00cdcbdd654272965ce4be0e38d7afb413e65cc8525e3", "62b605565cc85abfa0861daebbdb0b13d58732e59bc1163d9ee5b411fc6f7af3", "7b7226d49d687fd471e0eae0f54d9529f330d58b40a255aa871ccd36c8b048c4", "9ea175109678095977395a2337781a4b7a0bad3984d030b6bb0223772487d27e", "949862062b71287fb7eba6eb72efed9a06402d4372e8d4c32de15961298b9455", "4200d4862ab89d7e11f465dbb15e722eea2ead1b6eadcf55eb76cdee2dcaaeb2", "daeb4b3ae41eab84db5c30d4032541872bd9910f36c2f3708467b640f3d56217", "8340ac58b1ea529e8f4f0bcf297dc402d89f412252deb830d9e6ea626ec2221b", "b1a09ab896bccb3a2b2dd487d97392e5a3de1f2a8937cb30091a5be8320e43d6", "772812821e2409ab4b668507b3cf42fe3bef220d4970081db69cfbb992c54a0b", "af59ff44fe6084dcb0f148dd58429a66985c8f445d58bf7d734ee5d6cf80002c", "308def2d531cbe674b75dcc421bc3a5ef9d1ab5c8df737243643b2692a7280a6", "e207877fa88deb5ffae9b19ebc61d0ee6453d6c7bf911aa01263030cfa64f8a2", "eea9b387577ce6c76eae8f5d2d4fac9de61dbfe4b03382024a752c7f90a8e366", "ebd0fa6d638bbf5ef8948054b2c2424d490b16dcf19ba35801c25cb388a4004f", "0f41ea73a5debb480585af132f3910f3c7b98a577fd595882121631431af470a", "4dd11303be6ed6afbdc8a9017827c6fbf2fa8ea263117a9f08f09284559bd3a2", "77dce608339c3e4933ebda49d99d52c3eba9e585f81bb6b94de1eeb6c4f19aff", "e6bca493413498ac5b2ecb083cd17687e02f2fbfad5da93d4c31a02c9eb72c81", "4b7eaef4ba7578f43422618c729ce5b1d362a11c437f4d9693da8eee9bbe6b01", "0fffe2e60e034ee0092da0c22f560bcdce5553fc95eaf8478c3aed2d9713dcf1", "d7dc0f79e6077711fbd11be2c49a57d984dfe43e2357de902f694f561cce6691", "51cfd0c3aa1b96da6be92c65ef7dc25ac5f10236b515403cb7f8492791f3bbc3", "309d74e89ffd04cc8f050dfc4be50085f197f6c23ac5f84c22f79a2729ca62b1", "a139b028838d489dce5fa08da18ba5ea10969860dd813eb64c755f9f8a0c856e", "2987cd385ac6ee4a84b0c2c472fea3828306b7addd11cdd28aa416ad9950a9f2", "97e9199855dfed3d4fc6a8746ed9dee32586d73066e024e8a96bb124a187b3c6", "d5aca4fca7529a7917cd26c7710c20eefad94ab118b592db8fa22a4c258e99ff", "08a67a8a0f262f70e4039e10091a296fcc196e9520d5ac37f836ab109205181c", "e71586f3b63c70b6d65672a7d84781aa67ce0d70f41e4240f56066ab67d1baeb", "f2bfba19ad8573d2c7d48527ab2cc275f91fe08d82829908013f53dacb9478e1", "8af272ab08b9367911a97394a580c59d6e6ffe763aadc619edef7c3b827bc927", "8980fd4836c9ff27cfd5a999fa5a535ca557e32adce854752addef70c4144aa3", "5d976c7296257e3a0b8411bfba3f372f8d35bd7e73ed92bc26af88e322177178", "a01565d4915e7fb6689db3f1fb7fbddfc9e8647381c115e1c0a7b1490e8f755b", "a8fcedb1c3ed358fc5305bdc8b618bc0f354781472eccbb8960c8ca3a0f3233c", "094ac7a83a427bfab8eff10ecbce65c26670bacd70c941f623ff0298d354edc3", "d7b2b22315b3ee15e124dcf4560d3bea585842f4163daf0b879a8b0c55390637", "e6e8072a24ab7bffa9ce6e9a359c33b210e8b66172e1d35a5c8ed28871c40029", "39c1bcabe1c30d0798d8bbc275d83a503299b08fa2935552892ce03bad2c0bc9", "2ce057410a13bb152f276afa305eb94e0e31c5dd82a2eb828d0a01710a276756", "86b8f99ed5240df548dcd85fd87fb2dbc78e21e117524eacebe7ed88d7340a8f", "0ace53d368852d27daea0ec59bef8f1d5088ceda03719add6a02bc70e3aac785", "48c7e89b19636c77e186a093b1f2946ddd692f964ba6f2d2ed136b8c2f490566", "6d9e0dcbe46da467509a5a8a2aa709a31d47795f9f3bdb3a01812ced98dddd5c", "1526564dfcf5b6ae528444ee7a260771bbf30aa846da37d07dafb1d743c9f68f", "2987aef1d875722ea6f1684883eefb0ad566fd0017b7ef6094a1752e2ba68550", "22bc33eea0b2fdfd447021a90c90d10d24652add142991676418a72e8151682c", "0d72148b5f75fe9f6e36c5f042244bb5e35a27b62777db7ca1e1072eee9a8e48", "ef71137c514cfa65fa5fda9b517e3c267a9c7a7a7fcd4b9177dad57d0fc2add5", "11efa0f3f84cd47c1cb0c2d4634f317202ce00e52fa18468910a68cb317326fa", "750711ec221178fb1ee7549333d5dfa060283226953f9096782c24cf78771345", "9d621cbeb49423a46c56581dd621246766d6c1d2e885f38cd36ca18f88c6966e", "e459b29d49a394e84000903ccad0edde2b83096f73e93d144cf8a4fd041d37bc", "902e39fc44a6a9a712c9d42e0b98a08f793f9eb468ab13c120c87bf6309b68f6", "5fd3dd562fb5d0c97a66fc5d6f2d047b7c12e9518b95d6d4b96d3cc649e893c4", "ae5a35203af76d78f8d4c506b18fb4e1c67e5798706d7a1b98912e9fbf6669ed", "8806e940bc2274296217b392b69987b4772bac5aa5a96980a848c1ec769bb8d5", "bad155b7d45404ede0f07382e8d74d344dbbfe462c8b3658dc6ead106d418e9a", "fcf3012d4e101fd7affd972b1768ea8200fddce6e0fb7e403e4fd9ba3f01bac0", "8ce68b64c7b5675e0663e81e61c4b4379cc5f8845dbdf191031b591a0e10914e", "ec2253aabaa2731500b94ca5b60c8226e405ea23831e87882fa127cacbed1e70", "8333c77cd6b63b5e538dde44a5f1c37822c5e1259d7c6674ebc98d17431720af", "abecc9a68c658a5c31008c6c594d581d36fee313f8ec2aaac469f2fdf4525569", "e4b493bfaeeb85f35f83e84a318b3a1df7df1497ba1b03b498099e747956ef52", "8dda479f521d6dfee106e861380824d6d06c770d1472a189bcf251a1bf0a0f55", "e38a654a52e216ff4a200af142e4a8b9c38c448876b70b84dfc9de5211ca7024", "12b0bf0288ad6eaad0392192143f5765bddc84d7c99c3ce7e33711083251e878", "98055e28a5af0dbe2cdc674820e18c92a38ac89cd2b6d3e2f87a589e1f054eab", "8e05d03fef5e1e2f69f9d4fac674d82e351e34106ad29073ae9490e9ffc15b25", "bcbb675310f133824ce336a3c43f36f8f6bc1dc9be8efbfe3e7270fa0e7eb5af", "20af3852b4aef5ea3fabd3847cd03c064cd822b30b5c1652b91b414d08704fb8", "cc18a3362023966193c072630da0afe74cc08d9eb767866d85c557e6a6f26387", "950e603915e7fcedf0dc158daff822db034c0a240f7cdc5063bbb428d1408414", "12658fe8bebcd857c22f584c8e31d6172a87f089e1d883130b7dcb4c1600518b", "661d8c02f86e16355681f3a682aa0efea86a985ad29e2b64b343f5315a9268b2", "617a333e2cd2482f83715845421a1e25506724d4737f7bf8dbe9f3faa5a94aa9", "1cf208a9abaff984c259300f9345c92683eadd83d11a6a4024ee47b3b4d1d045", "db15ccc93275a34f2728c92076086f0f4c7b2068fab2b009adf7f0d48bdb888a", "befb08a1da6b7c3136dca3d29c7c0c853c2d91644e55e4303cfc8be64f699538", "ca3755a1d62e3b4a74fc458daa9a7faa3316fe7f6fb40a62282e9128882d4675", "4fe123bbaa5d874195f63e85aea06ab08355e0e57f2204308439917ffb080a92", "cae10b8938dd5806cfe5ea1944b39296a0a73b5957a82f308d9141558b21c6eb", "124dfeb77b60b21d782aeb2e4998ef15ca8755a3809fc3420b1f4a7125a1f4f5", "406e044140ce58e8cdf36d57a41892fe4b15a16871f8318afb4ba0ce43365b5a", "59f62af4c197b3ab5b58998677a39f42ae62738fb962f775529889cd7db10925", "7eaa2867fa01e79b9e64e17f41df246f099a3f1ec05f9feef690274f55b00182", "3c0125bf287ec0efa250f7dfdc4f784a4b11475e7bdc5ecccbf7c6dc591d0284", "06b9701560e87fcad9f9f9eb761b9b78bed1eb979bcbc252b9ebaaa465319a2b", "64bf409c31578efb2717df97ff8125c218e5b2740cce771186288de418110e2c", "91adc1e2ecabaa94988334b107b23a78af49d6cd6a8a7fa45dd0a3de7e7a5bb5", "99ae7e7cbf973d9eee35901a95212ced0cacccdea07eac0d88b5cd29e980b956", "563e70183d98c899d0f0fca96634f77ec89ad4bacb3f52ed2f736555149779e0", "7f01f980bfd6c3c60f3628d61afd9bc5c92f50998b3ebb0813db0487d2c23f56", "aaa5cfc4028fa4a0b2f1303372ab35e5c4e4a6d5816bd6b819926e8949a4bd73", "52968b2efd496a5de2dcf26a6502e8c6c74dd1249a40723a17e84bd331dae9b6", "9137b4da3041a7e4a3b88deffe35f371c0d8f746867c9959eca986d4a24034eb", "1d81a4be4ab49d3baa09a94794061d770bd224d3701fe00b76680297ca819bee", "628cc2eb26c7278894ed8ec317b4c60afe8ad5fda359f151300e1501d6b27091", "cc9378c99c54db8ea7cfa4261e74349b30e53fea0232dfc65e595419b7311c78", "3f3a959ed7bd378b9ea2822b166760ececc99ff65c340e9a99b550b4e233bc38", "234aeab4fff850bdd013574828def84a96ebf53a59187fae764d691c1e16fc9b", "b065e4e7d29530028fe92e1f48fd4944cfbcd4a4bb1aeedab43866b694f0fba5", "5df39fea0e235a747476259f34f8b66d739f9d7bf47f50c19891222fb66ed6f3", "67fef34becf3a89191220819e985761682583e9e2fac7fcce2181843e567b13c", "587293d74305af4ad1bcc2d88f6ac16c47ba265e3ac5ffa5f0f6235ea8cac952", "36a9a03e9fbc0237bd52ecf7fa23626d8ac83e91d54cc0471cc9277929582879", "78a673152ae87540f2b3a38ba47ec5bd5cf047da62cd6be3682a723bc87ee1a9", "8b48afe535024d84514d81fdea58934ca0f23e031565d7f74d05ec7a7d946801", "d81ee7e407ad1311d68f0b53994e6fb68131c596735329f76cb4d18c4ddbfb77", "16be4607f8bee1e191857372b0263ed401bfa173f2752736fbe50abb7e58da98", "d05083dd5e6d5e0a2c320a1752c724d3a13428b9dbd2833fc67c86628f6eb1c3", "0b2f6370271a17242d09d0292a1e0344d2806cc89e8e6e125c72ed47317171c9", "aa1332229c78544ada666a1e7cc54fb5fa31c586370de5388bfadd86176b2250", "d605e3d0ca62ce111f73d2ea48c5fbb56c5d47c2bc28eb68c398515703119072", "9e0549f039e6c530dc1432adcaa40a3ee2d69329fe1a2245c6c0461c16931eaa", "cb2f3789ae09d724f9eddb3f104e755ed2ddc3f5bac87aeb91f76fa53784e881", "6e3b3835f989decf5441e8c524aa95b6b312d5732d614fe24d80f9dd39bad1c5", "318440cfef57053d806d6f9c03c1331947018cf2f479b71d9f5ff4d1bf940ae9", "51050b2569885e0a61fc2487c8428e6fdb8861727de7e8d97f7901e6f583acc7", "02e37462d082a033c382c04ec6d90c629bd96cd0379eac6399a718d9988bf3b9", "3515eaa553cf9f35d85fdeb367eb3eb930a79dcdefcdaf2e6eb00c550deea9f5", "1321c47c060f371589bf9a1dc6557b9b49434a4ad6ad15f6749a2bf71e26ce14", "627cf526b8c336e3a3d8c3e82e5503fea6338f14a438e8de6bb3dc5674a10da6", "7cd3b2289dc1190b6ea21b9d011ec5574fa251d222af63a52bebefecbd89d7c1", "9bb3ad4efd34c6839bf4b641d1f745d8ce60c829f22b773de0fedd566c3ca60d", "679c477e999ae78bde65ce99acb6c2bacbcea8214ba4b7fd477ae91b1d21792d", "bd3ec90f50cdbfa74372cfcee0f017fe7342935eb93d9367ca277dff7b02eaff", "6a73b3ac5c74db3e940df13ea5e049432e2488b3997767dfd700e9aeb34f9cfa", "a642e0ef2b4c17cbacb868ec0ca7d43ae9cefee5e0dc29e59e561b44aff05615", "1a77398f0d8673a9fccd3342338f6e5fc1e96800beebe04f4aba48afdd41f6a3", "d2bf9e00bf6050ad68e7a3ea1261b3c9f9b6394d53da2f9f1712199ff5fa96ac", "d17c0276250825f6c8ab121c999c61cc892874488a4bc95a104dc0382e511aaa", "7be2cb478a857b81957d7169a01c6692a254e7b029b42995b6c262e6d30f0038", "2af54e9f62193195b0b927462e63a661c5abe69fff22037e047257dd41089646", "120849c155437bbec39e71267d3320eae464e949c7ed1e812c91f3c5ead6ba1d", "4d77309ed2522ec89b7e8e0f0189cfe9124babae465007ab5c905a9541d63a4b", "4eebf5a0cca448832d9a5224a39250ecac4a18c650baafe2d8804241c274dfc1", "5d29b8c14ac83e531b87534ef17531cfec84f49c764e6410c8d5682fd80204a7", "625d9a10f136b103e85f0e7863df74db8049f77a75e52361748873fbdb2a3f73", "eb21a9d33e58daa0ead2dad3a71d4e5eaa7b0321c6cc2d4e86464c70cf366634", "6b9066c0d9049b0634edf92b34140d02a49e7a6d76483d14c32125f3ea41d8f4", "b68f5ebb20554bddbcbd92371c4e536210a0674e61577d552b6b405939acddfc", "2f8fc98373422a6dce98f183f25488520794b45b947c18ab0e1b924dee353b61", "64643340086927f78905c52784692557869bcf723b2ad19b69fd0349601aa7e5", "39c72e17874ba3a3850231ad77319c564e5fc1f23414c80d0531f8e618895ac6", "9e2afd30de5bfa30e237d9f2f773766a82e20d1a7efa10d34e37048b172d2e91", "c0888a46377fe1194a84313d3e9f64e90cb94648cbadc93ca1c077960b2946bf", "c7a54836aa914f27df8424e40d4c42183c7dce32798f7964fade258768beaa4d", "485865c169e3e60c2b0cd97fe7caf04bb5592a9a08c5abf53de92f5fa745845a", "77038185b0024d9e2e0881b8d57e4dea0b59fcbd2bc2a776c8d7b29b5356a240", "19be080d3f5d828b2826c221f35a07200540c47c5bd5c374175f8d1b55dcc8e9", "32d5a77433130085014cfa02eb0b0ff36be96763b8f100502ee09a93fa4a62bd", "9572c95caca053688f8cde1436a7d5652f1bb5bb4da92dd200df11d2a27da378", "b3db618f9e7680be0c485377b1f9e874798b5b9cb2800a098053b025c47e70f6", "67a77a0cdf101d5fca5d17bf2b49f3c00632bb4a53c4ef06617762f36c8c8e07", "1fff3805be7779014868c91462838db4e8f88e7759179f144008534a1724fcda", "efd453c249b898711874f643c4b66efd58e91ad5b3aee1aa6ad7a477b7248a94", "bf94e5f1c7b5c8483285a8dea4345e7519581d486fcb27a8da43a2b48be22346", "7ccb34279395a288bc3ce100245c6de77fd9fc35956f9ece35e6475bbd6f6ef8", "810ce536aa750b60cfc6acff3ff65b36515f60c1abe5816aa5e38549b0cf21ad", "be1c2775730ae524f44e05fc989ea33b24d262db5cb630cd13d56a2324f8fe37", "7b8bf85e45285fa4b800e544da002c0c43c2b87644dfb62c42090631c5abd1d5", "96e286ddeb65c5e54b4a8325cd695b53f4aff1fda635ce72c7b14ce1e926c7d4", "12e0310edca52b08cb8a18dd2e382da62908b476f14b1a8e0aa993a945e84399", "e8ceee44ab4241cb19d5da582abc8b9c7ec4d71bbfa456bbda2d3dfb120c1e82", "e3951d2637df7a24c3fb48360da87247d998c9f092d7ebe349bf5b493cf89034", "2657c928cb139ac30cb495a790e8a125d452a541267e71ca1635cb69d830c349", "4d0fab3685c9e14d8382253670d0453430010fdb95da9a0cf5427760ff8f4bf5", "85a65d69081dc88743067a1ae0f5abef0adf79ba23500954217f990bdd17246d", "b3d6e83386b11a0d736d43f1eb3235388abdfaf2c90e94ba02d4c50a3c830a66", "f1f207e702a02318635f35a70141ff96d50b1058f57c01f84fd5973112eec5bd", "10e412a4f7c37f47b63d39cbde4721f65670bc2085ec8db8a6ebd2db0f19531c", "a7679d3b0d86f7d19b865f9c25aa91c1bbcfcc89cac3415138393f68958699f2", "9be5b69545813b368cb6fd8e8e2f0843a3299c268f3c78691d62f14cc08e1fd5", "c7ef2594ead75dd56e8effb151e72c72efd2e3151c22f113a9952c2d2a094ef8", "43406fa30813bf114ad791f19f91783ee623dbf5882e9361dbb9dd42dcc124a9", "f45c2618d639e25d60a6ff4e3d3c54aca3afda8887feeda48b3931d5fb3a890d", "021d36f9b63ae9509a139f5919a2c7c6daaa8b775b67d175d9fdc2caf1545247", "221662e3384acfda6b419aca64194a7e2b515c470eb515641a43ad280f5d8c64", "93a2280c52123349f7143d8f90b8862985eab8856ce01c1e65847f74e82f3585", "97595d2f3e15492623c1180c3448d91e27e8caa91a2286ffdde6e0e01d73487c", "554e51f4e422d00765369712a73dbe5e18c4f59aa55546b9aff3f1b94c8f75ee", "373c9b4a6fa3fc747881123d342ad6fd4bfe280c1550517f329e7b5fd9c90824", "5466a29fb42efa17c090eedb46bb213988ef7656634eff61d399c4540bf185d4", "68882db32387229d3c096e4f075c9075d1128759c3fdf5e5d8bcdfe24072d559", "f703f98c5b75380e73f861b3ceb685094aee6341309d5161b761fcca78acda0e", "59f93b2d63f4643f566199a92d955bd78caaf7ec7e3078fd5264f5b478ac09b2", "639731cfd7ab582be092da8ec8da53718c206b8f0fa5c75953fcff3cb116a172", "2bfe2a097a074fdff140fef54c104953996a032dc162edf32dc357e09abb3fcc", "466dd64bfa5468a071705d8b3f86206a481673ced10e0a4f172d7486cd29e8ce", "a40e511b719b6275dedb1b46f2c5f8b0cd725312ab239132c5b9b29547f6f764", "6583f450fd9001e5355551acb58a3c95ac663f8f58a82cc3f9f31135fe492442", "2a818d069c34b05be52769437dba3051f931aae1b1453e950c591b3920c3b3ee", "0b26d32e1e31400f4c3a5e2750fee52239b2dc3728f927ec455ba49fcc16bbbd", "7d90705556fd11248be8e53c04bafeb395b123c3b42d3e0e07f02ae5bba74681", "79ad2329c40c96cd2e4d694d51d2610b8a28971d6b253f5a54c22301afdb293d", "147eed7b0ff213c3ba36f679ba864cb2b050de968fdedcdcb48e6916bc264574", "d027dfcaaf6e04f676c619244515b823e7adff3dd01da6730342421168a61c45", "e2199dbc29264ddf0edc446706d684cc19ab7c81fd19f2c25a6aedfaf38bff61", "74219656debd84f572508135fb03c4ddb80a992c629a1483a4b32535156ee1b7", "cc6b74e9616a1facb82a483e19039348ccbc6a387a3c6991f50133ca844bb499", "3084b541105fe892ddfad7efe4d428a8cfb5890c6970d4c4d05bc1b1e7ea38ef", "a0b5c69bf883147418969ffca6cd45e9f710223b8da9bd93d77ce8aec76d4bea", "e08c7e844d6fa6cdcabb04975fb6c66ceda4cadef3b1e4fad7367207d674e973", "6033e2342b470e18a442cc73eebfc5e77303cd4ecb3507930f777cd2fb740a15", "3c20d132ea8e829fd8fb7b18cf5f9a5a71dd88bf35bc81f7cf37b4ab4cc7b961", "0ee98db4b01bea147bbcb1bd492a66c85abe9e20985738bb5a035d587badff8d", "bd78400ee797aba19c82c3bf060a13d720be4cab6358a39075e1ad721cfd0b99", "91c0f7efc5e43eefa3e587d1e2685bbbf68a7b064c06da9b21f3e38be2f8915e", "f0c2ff1abe61e4c0c3092afba482e7eef6f0744c267b5334e060485d01974b18", "dd4d830bd248066832624a2a5ceca133b9f5b9fa66c1d3a41eb4cc29169f955d", "04175c02b43883fa4b3c4b990334e2c3e23e85ddc36edcf04bee9f86e8a116af", "2eafcbc1db5005dbf74c90a56554ba71201e21d21ef4a77094f4b1c6c6d10497", "f6c826a659eef7eca7685ce1e574066a007906163041aaba2ac90a12f0315660", "2dc4d5de794e832b499f493c99fa948e10079f74552f23fc5d3700722e8d0f8d", "c02e4905c3876a3fa382c1a7f90cf91496d66da1b2495cb3f5a345993360280a", "5a375be2718ac37a38ee1c84b84476695a384e2a2ff43068c8d7989b4fd3cea5", "b70b2e6d667be606bd1c511f7e2cf631f533948cbb5af26db8650d4101253f63", "35a49d20ab277ac8c092985c9faad58320d1af7427124c4828888f4bd7491b36", "2a67df5cdd3e8c2a1241dfd24554af46feee6b138b4809663f86e9012ec47b27", "b50c7e29386970d39258f395e05f3caeb8648d9a40a0c14a603ba1e729c1782e", "0db1d79fc1686e0388b8439fe7331862314b77ced506dfdaccc2a21faf74f44f", "6b3393eacda7dc18a2ce451f2541681f5dd4e9af21a2624956542b60268a9405", "8e17ed5e690277e1156294c6904f6899de1497d15d8862a98cfe349c5296ec13", "e44b9eb141e8ff07acd5bc5a2fdd6d334192e27b27b5f4c26a225ad28cd9ab9a", "02b6fe45acb7af83932640c81519a7cf4d33af40e8c66510855286f1b869df7f", "c8aff4d8670456d4e64051e65f018226f7abcb40dc77b7a36a934f4afeb42888", "aa4a4dabb9038bb1bc8dafa93397b77b81e263fcfff59eb86c07920e6c8c218f", "3b8203b9ed708044720313b67f9b98cf9e96544e95ada0200bc4ea0e54a3c633", "524aced0165da7aa4aed8d02720276c3895a37fcfd8db9cffbc9d353ccc960c4", "553fcf8e9e53d37da153a4f8bfd16a2c5379da0472076719b05a26d10100801b", "fbb7b3e31f1d0d1606dc34bf1c624db7c62133e173203dad5cf4c3792351fbbb", "e62eddd4a815b35bf6916c615a52f185395baceaa52cee8a836de3a4db0c5381", "9ea285ecbb3cc9189511d2148e3d732bd98582324d2a597ccb942e8b0158548c", "6c9ecf00a9f605bd50375d0793e8ebad382060daebbbad0ec1427d5501b95186", "00a5392f9bf5114694596652d3f47debb758a1ef4a408490688a8b3b6f4d076d", "c9d5bf16c017b12a95d62a92b270c9c100fee78fc85c91f830c56be00235ce7f", "68ea43f029fa915aafc14bfa5eb8ab1ab1e6e20c467c0985dfeeb72af1859659", "172c4fada590aedd1eb45a16ca2ac669cc0371f12aceecf1467e0dd6e2af387c", "0e8c60669d5b505ff9f6fb941f3247bee6458fa1d6f1829c1444135c55b5b58a", "83e174c96ba972dd05b14f9e7d8dc0923ad96cdf6b2926c81baece8c7c3ccbc0", "55699232a0c96bd45cf5bbb81ae2e033d22b534b2fcec3b70ab661d22bc25b0f", "9d4ba8d5cb7404ae253587e6a583c595214407007c049988a08b51e8c05a67ef", "1d63978b718b86d8d84bd1f6e7cd053fec76dbc922c597abeeee64066d02b57a", "6d03e10f0787dd16296266414cb6bacb961387fbec686348f586a4d053718f02", "e4ae9203d1b61a37a98b21769f110e46de7ab6772d15b4af93a9f39cb2d096a8", "a5de66a7fa9666e03e6dd9e114d3cbed11e14454758fb20f42586685509f315e", "f0accba58611444a9eb7c3d41218740ffed85556762d5245f4d1bbd6d958d488", "95de4a732eaee2996786c28c3ae80a7bbfd34ad276694cdd64194e7d45d6b1b8", "59b03bd978a4a5ed212fd094e90048aca406d16c196410eb8be8122f2856d1d0", "2b6c3018cfd7cc55746864434c9b2c610a4971e60d9128a338451d46c78bfc86", "2428da7b24364be8aa93c6a255543d7da27f4cbe57dde5f14a8512fa5ffb981d", "bce26d655a0efb6f287be49da07393f30feee6bb6c2306bbad88e04c8984e7d0", "0fe2ad6dbadcd9c423b5eebde12b78365ff1c4fbc85e933206523afc2a2f8a48", "67482decfd58bdc49de9ec5a8147945130a928b98202457647c66865ca336c71", "7d22130b398f4085766f4909a68b4f7fa2c4b26db1e107f3a2ef29417ee5cfae", "98778612b5124e3d7d455f725f4f2462ef780f0323e0c36cb9bc81811c00a045", "51e7511c0f2ef6bfc7e17c7906fd604e42e862f3f4475d50d86bfc1401099d0d", "f120fe5e0ef2b223977b4519069cac7e4e77c587c5b011663d06aa08f80fd477", "9d00ace943765ba7f2a3a414f534d8e751af83fed0f8e872c36b311a15ae21bf", "93cc266fd13aaa341f03d20115f066cb126497bc0d6d5de719c9f80604a2e57c", "ddddd5d3636ab27be531f09a9a93e5d8b39fb2c03a79d4b7908f2b40b52bd1f2", "626c9f4c4e3bad8d65523b0f4b820f4e59a720007fc35aa925bc99d9deae3e00", "af9d9060c20e16bb1f94b3da86b8f4c074c472f2d402ebcadb879d9d5853dc78", "309db5e72eed85d70fb56caffd8bfc1dffb79fb9b599916468a68982c975dca9", "0738d677af3228b95cf444baba3469dd67aaeba54a93c91ae62845d2ab12bb3b", "720666a5e21383c6546a87b8cc93be7044c87c015ee2995f87b55bb291e9924b", "21d91ecc9946962e60ae1119f45687a670eb725a392425e3dca05d108808a314", "253c1ba525d54f4075c8aa01ee5383d0ea6a41b62d243fb06d4f90987e557578", "73429a7a5981f25624a1ea521c95c1aa4e744bca69c6b63f495e3c72571d403f", "e92100e5825a11d06c55a544f83e71a1cb86516805549d0d16c085a690645682", "3969b8d71699943cd01e410fb2b072638ffdc59d10eb3316ee12a98783c09181", "3dd6b9d720af724e3bba14e7fc41213a0c6b7fd5c4a6d6081cdde8b05941023e", "a8c6b92481b9b52f50fc996f3fc023f720b832f79f306aebe9e1db5d5d680f33", "84bde27cda62db77fac212cc9a399467cf466e0d5af32984b04f389c28e6b0b6", "d416c534ceaa07ce856d3fe9fb6d8cae21f28aa45eadd4fee27b791e69c8f045", "0b370fe3369b09d22ddd43f870a428c4b65974430a18261c59781ae77d941480", "906ad75351144066d6d0d914c5145664825d2004d778aeb41aec56644f81ba25", "3c57221b786a6de68d8d8db9db8ed3928a20eff9e688ad1121d73085a0fe9d75", "e1c262992728e3ede684e77f4a06efde3e2eebf8f12a0406dcede1aafe299648", "c60819a050b2d4e6ac4d72ea6683fde04dbaf6b66bd74ff988fbc7d2b29b9bf2", "e8468896b3f9734cd0f7c721ee0896ad1548902340242b7fdd16e39b361c4ac5", "6a8f24b12c66adc9e771cc6b52392688bb8535c1ba026ca7f79d26ce2c7ed9a2", "f5d607b7d774d7c5d81d6c8d58b4a7ed576403a4dfce8f2e63e1b7ce9c7f8a02", "011d439d089fcb3c7d44c2d5a6420cf60cf1b8716db31286f7c9ce390a0f2fa6", "d6fe9c609aefadabb0efff44e5375ea4eacc5237c21b58a2e199cc2899dbfbb0", "3a0b54bd93d3305354b07b6bb7807bace50476c4e120a0b327de1cdb93617079", "41e55404a5998f71571a200c032127a6241b2e7b232e82147fb6769d8256bd29", "5756ac43c1df14927d3af8ef161c403ee1f92b1ed296d0adc72e2cb45d98d7de", "f82cf2b7895ba7802d0478d2b20b069d3c8500637fe98d4194da02c884cf9d17", "3a10b6cc7cc3bb244fbd0d49910e588abe7dbaf759d4cf44783a7139af064824", "5a9b9b31eaedbb651f42d207a14b502b4b73885330c37f8e615ad89e3e61213b", "e61688578b28b999d906798525736d64a5aac1b5544b7507badb20b34b556d8c", "45b27a6ef06340c3ed81433083ac81ce99abcc951f5e334919f3ff56cd1c75d6", "fceb7a9bd727f1e8438f617d02674039902f195dcbbfb01b43d5f72edea02831", "d19c5e3b8aeb8f8b4c08ee8b61f34277bfe579398a76e28e58b972cd69089b61", "a32c7ab77af334e2d5c4eb3caf95d3aaad689f28a2dc3a7557f2528be402407e", "b6c17c21cecca5ac92a1fdc1032369e4c6d9cf2fd4f1d5b4406e1d7e7606b2ac", "be1b81276adee2c0f4df4cdc6d1b82df87dceaf516b7e4d994e023a937479f9f", "439251ab04c231c48b891702a2061921fa88cfef44741ee173853b6bf8490430", "26b7068c7272d9feaab03fef3083e50d49885e375f77792d59ff0cd502c03df1", "85dce2eba1a9ae5a41d06854f4db88dd7fe022727be35ad6b18e6087c8b91f1b", "e4f7178d36429096577518bf47e2d296c021ae7349aca78e2c0a4c606acca5a8", "e8d88f547187b278275c799b25a94d814f3174bac46077df9820a338b4d9c267", "ac8f48385b06e1c43da7fb74e522d347603b7b973ac3c3d06412ad72f5762fd6", "22f39a936e8e401a404457cbbef921c3568ce016a5c75de9256011b988c252c6", "77fa7038e7ded01577a2ae592cdc9663311b5e1e42f5f87ad8a66ae0e9a54c28", "87f6e5ae2adc65a736c9b1746ec1f18340bbee45481d7c1f5509ad71d5f3c9c2", "180e9ee8a321a1e91c490cd90afd74d556ae2a9bae223ec6c094587f359870b0", "f6c87366cdd0be058ebf9295d8b6b42729be58a0f7f057fe3243f9b2949ada26", "d45c27211e8a4b77a9e76c12db25e6e9ba9d03647f3691d158edbd8b7c38ab69", "8ebac15b55c4a2c5d3f4866858fe3ab9324bd785036dc0ce8ababa396419eb35", "6a80d86e69694ebeec5f6f5a5d37d12c2f813147c1116d5d26538d25f8882729", "2cf7e4c33c2a63ef54c444020bac3648738bee48779db4a3a0f9e72ca5b4e380", "9d101afcd85b7331d4008230f29b761b9f798e8814d123140e8b648b230261f9", "c6ee0ade266785f9dadcf6892bf4b98d7bbc292aaf2bfe5b7dd484785760375b", "94d239b78781096e3e8e7e6a7d9ad70d0804adeb6a6675fc5da4f05d1152c19d", "55ca49e0e313f14ae0f214ac0a51843158ee07aa5f381cb9d596b8612dbd3f36", "e3e3672131fe9a71f54a41b0e8143c63bc0aeb823288527bda069a1616a41529", "ad1b386b668b79c7cada251a6c2bd19c53e51045e4a4562b4b9212852d334556", "bd08a3ba2d8603332b31b2394a556edf6ef949ec8d49e5d54a13318213a0da65", "b34731e855ce7fc834aa0846c72ce7f455f40564b11181b340ec07a003787e88", "ae292c8d03de63af642539e6559960770d80dc4e9590c46f54ab8a74b68f145c", "10a28c04e90016bc744986e50d2a240ff553cea32c8ccbfc218445d6f9e32271", "182df763c8b4dc2c1698567546dac90ed5de00c033322c9f731a64f08cf7ae61", "eaad2e6f6dbc000fe3b8f60fc7ce7011c22c4d062ae2c33a3621098190027381", "1e7d630f59f8c968c54a803f8c70e15d85a1214be4e0f8e82cab9b2056df4ef6", "af485e0990350c9814bf8a8b3db91f44d4d459f513f9e0635ff54a444a45055e", "c5339ed11420ef44af6d7eec085a7495ac1f59264119184d3183a937d7012295", "ee4c98e7b5e1b5fc19c8e5e75b9be39690ebf15bc9b1e5fbb3ecb75a2ec89d3a", "c88b24689438c8f097cec81f2178fd162d4c53ba51f1b835c9b7d1f33f3bfed4", "b3f12ee06f773536bc4882441d7b40153fd02ff4abd97a5686bc8ec294de5303", "74b69c91d7b24cbc734d5bbfccf3442b10aa94f835dd49e84aeb9fb93d48f984", "7249af9eedd2ff198a93c9fd96d3847d05fd24e4a2dee3213f8b0157028a7a1e", "4c663e23616d31135cf9b4c33a89556d9973b2df0fe8b5a851163ce3e770df33", "4afede394dff0a2b6f0b1b3dedf82614ca5133814c9466e7856a53cf33a83359", "b7f3d596f87080e6fe4b0c5e17364dc87ba269ca561689d20085c9890270145a", "a91c666326b9198e9954c4461da9e173c21042edbc8e63e6527f69aa06144ad5", "c11375b5ba44d9be64cf8ccc8eaba4689ce8d0a1d75f4b932d14b4e26b962ba8", "c737cddd051af963d4109063a7c98bfbbe500abdf2761545fb2e3f592f1c3183", "9b09f03742db7491a7a96f20d2735d669383b59570c919c5f8f4d804ccf552af", "112ba278ae78125b0ee2a9ae9d4c857d7b09d3636d8afd9e175a3557917409f2", "3ec2366bdb151bc04838ad4459790d217d7e70104dbb6a13de48c8e97873c874", "e592d021807bc768bc2eb1b6b7832d7326565c39b82658ce9c340ee50a443626", "446de54c9e312644e2fd20f49b8d9926edeb2c995e627414da25b664f14e4fb2", "c0e6c970fb25f5ec11f0c76316e7eff5bb180acd21bc777616ad3212edf5cb3c", "32c3a1e954262361dfea8dcd6d4e74c436d53e6518a2bfd080302187e454ef3d", "af6c5f72dbd65e75a91a40ba9c6abad575f12b7fd8b66c41d88948fa8e026f3d", "2f858194e1da082ac8ba94373768de9fa1842a1adba13b2bf6c67474d0a233c8", "74b19f6456e34582f963dba6d7faebb6289050227f55d5bead6aed9f6394eb41", "e249aa1cc573b722bfb4e6613dfc70e2a5d6cb7df94ba1002e7f549f57aedcef", "0ad80c6bbea362b8bdb966cbc50135bfa321bb8cbb0179f76f445dde3d156c8b", "898f699a5c52bdada6a62d24ac05ec8cb043f5679b554ae5a9b4d666a440fb76", "305cf536a22fcbdee3353cdf59ddbd42e24ea1a8b91967d5038ca3f9094868c5", "2847f3395f902b011e2eb0ce5e995cd97af861c925e04021a5bd893447025060", "91f09953dda135db571d5e159e07a495b0ca9d2eb6ba584b6bff019ae5693624", "648126d6266a94fd567040da2a9becb5e6be4055f9f4176d252ea8b29915b8a1", "46451db7b8576c094fa561a81e6d1300220b42b886e3e3b5faeb95c78090e6e0", "97817465e9219742eaf8121d0d053224793083991313a7b376093f5cdf7329b2", "4e5c52de7f2d110910f12126b36f9ee712f4a70ec48a86ef10b21767b876396f", "6510078a1522e2f137600f9183802c1581f882bd9fa0f8f1391484f84cf0fb43", "2b687ea5a740865b89abc5657546a55b7d5f7fe4e4796354b4b4266f0c0ec10c", "879d6960613b3138e2a92c821026f5858a99338db1f769923ccb7f32ec4afcd6", "6c37cd022e745b6666c0388b81296be90dce442972de52400fa3adb8e734d2ee", "e58f22310f59fdddb90479cc36c763c1fcf60d6e09501d51c495dcb95c033d05", "70ac02944106daddc97b53db0a0f9bdc1cdf7e789b698b4234a88d8acb945233", "e797d50c461ed06e255f8106694f1e3c3dff45ca342b631c9d93fd6868ee7862", "d645d1ce9d365a5ea79ccaa9b24ec597a029e07e667bdd5461a7cec83344f83a", "2fdc7e98eaa0910fd04914e2ac4c1216e2a4d37621e23c69daa7539b6d403ad6", "3ea00f497980193dac3261c3e12d7593b1668465227775c53b01e0029a3dbaee", "eff07e9c0aa7f889f74bd0daabfa20017aeac105fb09d11647059f37eb1027eb", "69d3cce33ba2f60e895201dd8d0a92db55e4db99b04de54976d3f11ca280dfe4", "64aef37268e77bcbbda83cb568ba365aa650c4363e22f08ebd9ea8dd4c5ec3ba", "837f82d3bed0341335bd5ab9d633bb5b1117a0b71664315643f710321451b08d", "52b1677f38980e1ba9eee33faf8a60f50d76a9020fc18aadad44ef12d102c630", "c5727a2a22170ed9a40b4e003e7039bb6f51ef719faa103159869f715cd79d64", "2bd8376008ef3339ad49383a12754f63710ab01657cf717aa945f8ebeb351d26", "617d5e3734a176c6aaa970e78f412532263398023f922604d69d73a34d7c9600", "b508b6f323862d1393522ce67c9f267f8f7a08c4f17ec2d7e9230df6a7dcc83d", "003b1c8857c2366b415d5b1eb23ab8c0705065bd87fe08e7c25114098bc2d020", "9c18e71750ab5a52520fa5c6f4b48047d34af42b9feedfcfa96a9b9cf6c2231d", "c3d69220994caf490d6d8f4c7f7689da6e533bdbf775309af7b13b25359c15db", "64945a074fe5d593413f740fbb0fb036efc1585073a5c769e6b7bba5083bff67", "da64240fb5aefe994b80dcbf86c6775e1d8b9827c90ea914dc89ed96994c1b06", "f3dcceebebff82171d500aa5bfa42d923af47fd9d935ff3b24e4246c2c240bb0", "5e9c33d78cdd3d5f71a74981aee540c199f9928c132f047ff975f9c4528929ed", "e83e08ca018747334d5bef54eff1527d03fc478a9a2ce3bc1d08eb74b1e05c5a", "2b4404ceb208a4cbcca4eca597cc25e50c156d1d4320b937795c201bf62e8e27", "6cf6e54742a3e3a2469296b51863123d6939a3e4f18973bed3350f361a0a7fa1", "173648ce3c3faebf66b1b400e2ba1d09a6f7a0e90c4f6eb259cf141cf2702868", "1602f84cd08034833d4d6b6f0a63017840b0517fcd716dc5bb82071f81cacf22", "5c9a5a89db7ce103784cd0a185ef589967930fa6e92aa90fb8c02031694a9404", "a99a83be39be7d0d247f3805d7c78f47bf16a3babf9d63cb68e28c0f630e15c2", "9a92a01899a649676ac792b2a2be8db3ab24f1f464a1af6b3c03b7f67e572510", "e0448af4bfdabe13a044362ab133a5560a77e8e6605df7d9b36f22a9ccdd806f", "8f675662f98a9961e9a67114a98f442359b8797f729c94c5a041ebdb937e0b57", "6dd8437315fb9be06fcbb22ebc82103648da5b142622857175dd75a0f78c7a8f", "6c4a96d440dbfc0f26f1bdf1e1c0ac273b573c36f14e55342fd98435e806b676", "700725449099dc98933ea1c8f1b9fdaf21ccb7f7439451cbdcf763e7b633e52d", "22c986a29a24c02703a8be6fc3a17f00975fe6f323366da8284a4c1070b18160", "037036f85de49e6136d1f54c2b1f754d61c262bb88c806b72a156e272d60c535", "8813017f3878a97b15c272982b95b3534a4475dbc3a6f40aaee3eb9dd593eb2a", "403a7a97d3c47c57e89982086de458cc1c62d01449945e9adeb160bdb487e7c8", "e1ae2a3ca0a102d9d7b80462c5c75ce1fd49a341a3ae60a497a98c9e84dc4d2c", "7d3cf5fdda0516c200a2a5d622c256d481f9764d6a72799995e01b31c97f4f26", "a080f0e1bf33dc8190c844c3b13c56c058ea08af44e1c7363d55e8fd8a7a3afc", "a611f43917fd4c23e5bb65ba8dcbde6db510142346cad2b9ab596fa75635d9e3", "ba068f56418356e2c0ee98119cc3030fa7a9b8c27d5530c93f134e899afedc02", "81a7d27fa4e8d911410a733248f102e5a9eff4d8f5617114e97c1267cbf3d348", "ea711ec0f66cec18c17b3bfa39967b00480a0df0575412c0e8a7aa8869ab93ac", "dc2efe412c0c7cf5d7e838641bdbe2d59877ca74357536da58aaa0fd1b711ac0", "93e321c3371d69fade1451f2f537579c54934aba5271a018540f70d4ac91a78e", "8f1368dfc99618f3e1b2302ebee88319371106bef78471b0eb876f2f06a3a818", "5fffc415587f815bf9645acdd481294fc4d83ac5b9a37275e8725921eaeed7f7", "3f29e067de0e036efd2684b9c54e0e6b2787fb9d83504c1201c4d0a017a0785f", "07f4a000178a78a4a8faa370d5aea0aa5628ff669522fbf6ee0d016ce016f8dc", "773ac8e936b1618243407a82d1ec9a6feaa5ebd9cbd82619d19b5bd7f0297536", "af56203cef3a9126c3442d964fe09bfeba50d9243fd9bb87ec38a961c59b5960", "fbbdfc94f38b514470de4290bba2ebdff7aac5523d97a0abbb20859ebc82065a", "471ab6bea6f7cae837a9fc601f70c7c8e53e84a544e43008d945875d61df04ad", "e20fa6fa46cd4d80d54d393c86e49b282ea1526c5f339e579bad5b39304498b8", "cac629d37126684710d0bb74fb52d529f2d16c73734f2005de6de9a504ad84ff", "a953032ffba659a809d5f733daa9db681082aa65dd08c0b05664dbefd87707ba", "5bab2244233e9f9f2d7191dfbe1ac968652ea1bc0fac48a5557b01c40d260f4a", "9d09dc8281294423fd516835ab30f15416cfd011e74dff4bf5e05f87416f0cf6", "893776d2cccda1f86b0e405d13a75a11a96528a45e0872e4ffc0b87513594100", "758a1e6461aeb3ffb55c231caacce8f663d83eef4d12f8cf94d69b09252b6e06", "0dee497dd3a7bbc26c1b2b2f807e55bc62765b3557cd50960e8b913a2e3acdba", "35a08cc32bdce97e91ba274bde6d6f19c74ae3fd3566cf1c40002a0775872505", "689104a13715e4e881a4640fd5e4bcd46687c67f53c91db4b8cae8d21cf90722", "e48d19e8a8a211358e7e7ffe964e981d3a1d11ae76a2b44a44faa856566abc5b", "28d7c2498774be7540d3b85cd67e873db198267ebd59cefb1164969d56544940", "8440cbb16acf418689ac4fe6d2b65ddd949e96458542539d30bfe2125e3a88ca", "6f837c7e4a9f4c4c1b17fb202a5bc7479add8cc0d26564766328f77455627961", "fb786f9dc125141f04857fd1393abe9172ad9c3aade782bd4d8dc23018c662bb", "be101e3278740014287a572b2b27fe3e20712bf589db356e800fad1e633d34b6", "02770ff50283c20a9a9de291de391fe7ebb4744da607a7780b10a20c49a753c2", "84801d626b5998746e0865aec4fcd1378bb376edcc763a80ee96373b01cbf72c", "1da1dd3aa77a4e2d8aa0857ccd857d4952e58ab49c26a1f0cb60275030f6607e", "04fefbda5ec9f182c2a22ad6bbbc42ffa322338e3562976b8d32b3406c2e38c9", "e8ccdcb248078a482359f4f7973d3b2069794b9777c4e2ac21558fbffee59c8c", "51507a05fbdfcc522a1f29099cc06458591bcd5809d2b210901e275dc1daed7d", "05e6b311d3a3241022b0152924627706edf857161004dc785983c5c8e4059b19", "986ccd7ef43c8085b738a0e2eb84b98aa920fd19f372c34c37569a5c7354d6df", "37c4370297131fcef6101bb43e37ada63ee4c63eadd53c683cdffda2c22b6a5f", "c8a736669a5a1c69c6088735306b2aa6da1fa685584446b27c53612344a28d39", "0c829d4a74a40e4338a406a268de64a9ac1b58ad2f0655cf1412cfe10a81f128", "ea8aeeeb0fcfa66319b5d1560c1c7e805cb445b678f60735a5450233a08f5146", "0c03e2902e4374dc2ae6e9d46b27028af86c461ec65b9708829f6e341c5dfa86", "427623b7f21f13216b47d64b3cce69d8695a12a8b76ceda909038e8ed1ad7ad6", "309bd0bf85e4b9bb130a17df032a6d057d2f4774abca3a8af6fdbf25de9182d9", "7f3da6402da41b66b0e5e957a40a787c53a3a31228f06d45f6ddfc275c06e815", "9453352b0b6541e28b5c36d1ef833b7f49dad472ac7bc01712f04a1d0bd8cb3d", "35b6a024cb364ee9e7ac55b3ee07e137b7dc7756c6e7131d02d603613f876578", "6ce8b20bf01933590374ff85f4a2fcab43cde2bbf9bf7b56c7e4c21acce02af1", "f02acb1e0f786b78b042e5d5e4d25fe711ecc05b2cbdc37077a4a1b66d925808", "b5697acfcc9d3d4b58bf01ee959bb519b165d6e2b3ff799dcd8581f2e4ecc4b4", "e5dcd86553008584de8d4e67edb1049198922900801bf51da55efcb7de45c37b", "e0c3e5997bd114db9c09728c21b8b35748eee68f8eb305b5cc099be3c265d327", "6c1e0ef8496d1c39fcde030239772ddf1182807dde25d54fea68085434a08b02", "4fbd6bcb31a607f792cca7f514d8259a05f684092be8ac91b242bc90169a7042", "9dbd18a509716c53037d8713d0353094d55b48253cb0d38cd7bc08959d7ff014", "a444e2b82333cbd5dfe250e393e245d5db8b78f91bbb6a572761a0a43ed56b38", "b163cba8c2d0441ac59033f7742733cb77812bd74de1147ae8173faae4f9269b", "0ac9c6fc35728d1317490b51b36277e825a49ba95be2a6783ef7af99e49228f7", "abe44cdbc6aea6876b8f009d6279479dca2c4f17c650c51bd7de410bbf23cd24", "4b9370d4ae2fe08db33f468ffceca5d9fe6b0273ef2887a4ea8522293870e0a1", "98b3b29996faf548b808efa1fd4ca779882bb75cc2ab3304f049b429a3638a97", "dfb57e8a34f4911773133529e0e222f6a5cf691b25a65c288f8d6baa68b5f406", "d1e35d54b3df21193102e9dcbb194a294323522ae35c68597b4b08f53cbf36ec", "53e8bb244f3c2c90fcc8ceb1662e03aab3e1a781fa1697f7383e0bdc59831195", "255874e4ced532485777b878f2d779c62853bd8d4d05ddadfa6163465703dc8c", "6b61c176da93e56226cb6fb7a4f8acf1df87d02be81f823dc851680ae64f80b6", "f035af0a109e467fd4ecd7c45bed043dd1ba0d02164c2b2aa0ab1989d8eaeff7", "81b239e1213841934e989034959c9ca0448ad64ac3ab919751c2289600a20723", "251b4f7823c8449e2e154cbab4aa72fb2cc55495da5fdc2d31075aa5647ba4cd", "0769a11a881bfd2f02a087803235d344ad2f005010e40ecd7af5db96245dd719", "f4963f675eefacf4cdd14ff7b759d5752aecee4cd704744e58b9bbbe078e0faa", "28916a97e55790f8e0a95c1203c1f8f1eac99b866aac5800445ef2d888b4be87", "575a46ecc4c7757656b9371e9b8dc058f99f9d9ad20a3e6de2d4e6cbc193711c", "935994c1df9323d2bdcbab8762904e48edf6298904f3ae7e234599366bfd86ef", "dec5bac62e0ef64db4936f818e325e12aed29ee0933277259185da1298dd0a28", "3ba063cbea967fc0b7bb9a25c5a12ee801eaa92f5570d1d1a977a229834fd0a0", "3327cc41ebebc9e82f06f836d5868f9c5023b05498bd73d836f04179d24fc7b9", "8d70f449bda2223d0d647d7543bc3a2c29fedffaef789dc5bd73d25a6f0afd38", "9902826a10b226265f357562bb20774358dbc636e790257a57af7f791b600acf", "c5821a347232865496580de7f3043822ca56eea4f8266c51e3be4a16016cdeed", "2817d6dee3e6706b92989f2dcef7cd0fef5d2263ed3d1c5dab8ba99550b1e5d5", "b918f2ce206701dfe60eee1d40fad119540e928b8da813fe29d77a2e26c2738b", "7f836479ecd2c4aec31c96935e2ce932135249c6077184b837f724fbdd425408", "1381c39fb5a68c134b948aacf72b5127a7b0d5a721ed2091da25a3856b9a9af8", "80e6ab5756de5eba8551f62d8943e5f650f4ae8864ea6bdffc3257ef1072679a", "ae7dd5fcf4688844f5ef72471cc0273e0e2f8f43ba4fc3dd41208f70b880e5d4", "e0f1d8c1a745ede1198fefbd0555bc118f7ccbd9ee783d8ed7a148f54fb1903f", "33c8a75fad49fd3b3bb1e031fb283858f79b05a8b461eb1f8f0e9d41c53474bc", "3864e97cd6f47c2eaf3fdcbb105e014accb4eb902be8a43dfca77dfe0d92761e", "e524e7c40053d3d1da35ac8a584ad7034cd30de0e9513bf7731f8e5f51f7178e", "12e121ad8a9be231659d08746b1a8b2b9247304dddc69cec074711970986cc6d", "149a0d197a6c2dba3044e43f5fac90f6a797e0d4c8d91e241725e963083bb472", "6a062ba02e79d2b2c001e1689daa1b3ade7c917ef26b30987798123818b202bd", "99e47c124d128f741f30e7c5bc7575f11a005befaa26ab60b560fe4a65717aa0", "147961e3d28573540582cb4a6e266f3a677d9e5b24da19c29fa611d3f8fba8a9", "59261c94c9000fe26b3b050c4cf7ab06343d4ffcbe3934da65f12d8a7b0c6862", "7428bc174ef7fd68911d46b35da30bbf8a292bb6b9ea99489b0c28bb55876e54", "6fbff71f7187e67e5cc11f85ecc7d063284c6829ffc2b647d9439cf6d80c71b3", "d49db17aa1e54596333d1962db0050b54a96abc6184f28b46778ac3eb9bc2290", "082436ca15376750587883056c2b5fceafd232f6fd91d839dcf7f138583565d0", "2d6c7614ddf121cedd9db989f73da61c3e5d5d7a876139d2d441d8dc28bef0ab", "10b5eb9db4b22b9047b2c9a2b40abefc9786d8f0b33514bcef81c462f241ca60" ], "key_material": { "scan_priv_key": "000000000000000000000000000000000000000000000000000000000000dead", "spend_priv_key": "000000000000000000000000000000000000000000000000000000000000beef" }, "labels": [ 0 ] }, "expected": { "addresses": [ "sp1qqtnvg7hxjck9ag24naytgd7pjwsmevwh95ydwht58w3uh7uw0ta7kq6xcdal4dazgg2txp472hdz4svms98328lqdflmpxppmc6ykamcrv9s7w9g", "sp1qqtnvg7hxjck9ag24naytgd7pjwsmevwh95ydwht58w3uh7uw0ta7kqmk4a3pm24z0yepw6aw27pku56md0hq5ace0l3p3jstkqaajwrsjqc5dde5" ], "n_outputs": 2323, "tweak": "022c333a8938ca0c7433c5e39d440b469f58374d0363b5bffc66aca1cc10d7b609", "shared_secret": "03abe0979dbbe4e1bb2cd2e06524a411c0b829c1d2282052da817b46f1d6e598e4", "input_pub_key_sum": "02bca87f72e604e8850064552bedf380ca4584227057efe12a6cc238470658aaa3" } } ] } ] ================================================ FILE: bip-0352.mediawiki ================================================
  BIP: 352
  Layer: Applications
  Title: Silent Payments
  Authors: josibake 
           Ruben Somsen 
           Sebastian Falbesoner 
  Status: Complete
  Type: Specification
  Assigned: 2023-03-09
  License: BSD-2-Clause
  Discussion: 2022-03-13: https://gist.github.com/RubenSomsen/c43b79517e7cb701ebf77eec6dbb46b8 [gist] Original proposal
              2022-03-28: https://gnusha.org/pi/bitcoindev/CAPv7TjbXm953U2h+-12MfJ24YqOM5Kcq77_xFTjVK+R2nf-nYg@mail.gmail.com/ [bitcoin-dev] Silent Payments – Non-interactive private payments with no on-chain overhead
              2022-10-11: https://gnusha.org/pi/bitcoindev/P_21MLHGJicZ-hkbC4DGu86c5BtNKiH8spY4TOw5FJsfimdi_6VyHzU_y-s1mZsOcC2FA3EW_6w6W5qfV9dRK_7AvTAxDlwVfU-yhWZPEuo=@protonmail.com/ [bitcoin-dev] Silent Payment v4 (coinjoin support added)
              2023-08-04: https://gnusha.org/pi/bitcoindev/ZM03twumu88V2NFH@petertodd.org/ [bitcoin-dev] BIP-352 Silent Payments addresses should have an expiration time
  Version: 1.0.2
== Introduction == === Abstract === This document specifies a protocol for static payment addresses in Bitcoin without on-chain linkability of payments or a need for on-chain notifications. === Copyright === This BIP is licensed under the BSD 2-clause license. === Motivation === Using a new address for each Bitcoin transaction is a crucial aspect of maintaining privacy. This often requires a secure interaction between sender and receiver, so that the receiver can hand out a fresh address, a batch of fresh addresses, or a method for the sender to generate addresses on-demand, such as an xpub. However, interaction is often infeasible and in many cases undesirable. To solve for this, various protocols have been proposed which use a static payment address and notifications sent via the blockchain'''Why not use out-of-band notifications''' Out-of-band notifications (e.g. using something other than the Bitcoin blockchain) have been proposed as a way of addressing the privacy and cost concerns of using the Bitcoin blockchain as a messaging layer. This, however, simply moves the privacy and cost concerns somewhere else and increases the risk of losing money due to a notification not being reliably delivered, or even censored, and makes this notification data critical for backup to recover funds.. These protocols eliminate the need for interaction, but at the expense of increased costs for one-time payments and a noticeable footprint in the blockchain, potentially revealing metadata about the sender and receiver. Notification schemes also allow the receiver to link all payments from the same sender, compromising sender privacy. This proposal aims to address the limitations of these current approaches by presenting a solution that eliminates the need for interaction, eliminates the need for notifications, and protects both sender and receiver privacy. These benefits come at the cost of requiring wallets to scan the blockchain in order to detect payments. This added requirement is generally feasible for full nodes but poses a challenge for light clients. While it is possible today to implement a privacy-preserving light client at the cost of increased bandwidth, light client support is considered an area of open research (see [[#appendix-a-light-client-support|Appendix A: Light Client Support]]). The design keeps collaborative transactions such as CoinJoins and inputs with MuSig and FROST keys in mind, but it is recommended that the keys of all inputs of a transaction belong to the same entity as there is no formal proof that the protocol is secure in a collaborative setting. == Goals == We aim to present a protocol which satisfies the following properties: * No increase in the size or cost of transactions * Resulting transactions blend in with other bitcoin transactions and can't be distinguished * Transactions can't be linked to a silent payment address by an outside observer * No sender-receiver interaction required * No linking of multiple payments to the same sender * Each silent payment goes to a unique address, avoiding accidental address reuse * Supports payment labeling * Uses existing seed phrase or descriptor methods for backup and recovery * Separates scanning and spending responsibilities * Compatible with other spending protocols, such as CoinJoin * Light client/SPV wallet support * Protocol is upgradeable == Overview == We first present an informal overview of the protocol. In what follows, uppercase letters represent public keys, lowercase letters represent private keys, ''||'' refers to byte concatenation, ''·'' refers to elliptic curve scalar multiplication, ''G'' represents the generator point for secp256k1, and ''n'' represents the curve order for secp256k1. Each section of the overview is incomplete on its own and is meant to build on the previous section in order to introduce and briefly explain each aspect of the protocol. For the full protocol specification, see [[#specification|Specification]]. ''' Simple case ''' Bob publishes a public key ''B'' as a silent payment address. Alice discovers Bob's silent payment address, selects a UTXO with private key ''a'', public key ''A'' and creates a destination output ''P'' for Bob in the following manner: * Let ''P = B + hash(a·B)·G'' * Encode ''P'' as a [https://github.com/bitcoin/bips/blob/master/bip-0341.mediawiki BIP341] taproot output Since ''a·B == b·A'' ([https://en.wikipedia.org/wiki/Elliptic-curve_Diffie%E2%80%93Hellman Elliptic-curve Diffie–Hellman]), Bob scans with his private key ''b'' by collecting the input public keys for each transaction with at least one unspent taproot output and performing the ECDH calculation until ''P'' is found (i.e. calculating ''P = B + hash(b·A)·G'' and seeing that ''P'' is present in the transaction outputs). ''' Creating more than one output ''' In order to allow Alice to create more than one output for Bob'''Why allow for more than one output?''' Allowing Alice to break her payment to Bob into multiple amounts opens up a number of privacy improving techniques for Alice, making the transaction look like a CoinJoin or better hiding the change amount by splitting both the payment and change outputs into multiple amounts. It also allows for Alice and Carol to both have their own unique output paying Bob in the event they are in a collaborative transaction and both paying Bob's silent payment address., we include an integer in the following manner: * Let ''k = 0'' * Let ''P0 = B + hash(a·B || k)·G'' * For additional outputs: ** Increment ''k'' by one (''k++'') ** Let ''Pi = B + hash(a·B || k)·G'' Bob detects this output the same as before by searching for ''P0 = B + hash(b·A || 0)·G''. Once he detects the first output, he must: * Check for ''P1 = B + hash(b·A || 1)·G'' * If ''P1'' is not found, stop * If ''P1'' is found, continue to check for ''P2'' and so on until an additional output is not found Since Bob will only perform these subsequent checks after a transaction with at least one output paying him is found, the increase to his overall scanning requirement is negligible. It should also be noted that the order in which these outputs appear in the transaction does not affect the outcome. ''' Preventing address reuse ''' If Alice were to use a different UTXO from the same public key ''A'' for a subsequent payment to Bob, she would end up deriving the same destinations ''Pi''. To prevent this, Alice should include an input hash in the following manner: * Let ''input_hash = hash(outpoint || A)'''''Why include A in the input hash calculation?''' By committing to A in input hash, this ensures that the sender cannot maliciously choose a private key ''a′'' in a subsequent transaction where ''a′ = input_hash·a / input_hash′'', which would force address reuse in the protocol. * Let ''P0 = B + hash(input_hash·a·B || 0)·G'' Bob must calculate the same ''input_hash'' when scanning. ''' Using all inputs ''' In our simplified example we have been referring to Alice's transactions as having only one input ''A'', but in reality a Bitcoin transaction can have many inputs. Instead of requiring Alice to pick a particular input and requiring Bob to check each input separately, we can instead require Alice to perform the tweak with the sum of the input public keys'''What about inputs without public keys?''' Inputs without public keys can still be spent in the transaction but are simply ignored in the silent payments protocol.. This significantly reduces Bob's scanning requirement, makes light client support more feasible'''How does using all inputs help light clients?''' If Alice uses a random input for the tweak, Bob necessarily has to have access to and check all transaction inputs, which requires performing an ECC multiplication per input. If instead Alice performs the tweak with the sum of the input public keys, Bob only needs the summed 33 byte public key per transaction and only does one ECC multiplication per transaction. Bob can then use BIP158 block filters to determine if any of the outputs exist in a block and thus avoids downloading transactions which don't belong to him. It is still an open question as to how Bob can source the 33 bytes per transaction in a trustless manner, see [[#appendix-a-light-client-support|Appendix A: Light Client Support]] for more details., and protects Alice's privacy in collaborative transaction protocols such as CoinJoin'''Why does using all inputs matter for CoinJoin?''' If Alice uses a random input to create the output for Bob, this necessarily reveals to Bob which input Alice has control of. If Alice is paying Bob as part of a CoinJoin, this would reveal which input belongs to her, degrading the anonymity set of the CoinJoin and giving Bob more information about Alice. If instead all inputs are used, Bob has no way of knowing which input(s) belong to Alice. This comes at the cost of increased complexity as the CoinJoin participants now need to coordinate to create the silent payment output and would need to use [https://gist.github.com/RubenSomsen/be7a4760dd4596d06963d67baf140406 Blind Diffie–Hellman] to prevent the other participants from learning who Alice is paying. Note it is currently not recommended to use this protocol for CoinJoins due to a lack of a formal security proof.. Alice performs the tweak with the sum of her input private keys in the following manner: * Let ''a = a1 + a2 + ... + an'' * Let ''input_hash = hash(outpointL || (a·G))'', where ''outpointL'' is the smallest outpoint lexicographically'''Why use the lexicographically smallest outpoint for the hash?''' Recall that the purpose of including the input hash is so that the sender and receiver can both come up with a deterministic nonce that ensures that a unique address is generated each time, even when reusing the same scriptPubKey as an input. Choosing the smallest outpoint lexicographically satisfies this requirement, while also ensuring that the generated output is not dependent on the final ordering of inputs in the transaction. Using a single outpoint also works well with memory constrained devices (such as hardware signing devices) as it does not require the device to have the entire transaction in memory in order to generate the silent payment output. * Let ''P0 = B + hash(input_hash·a·B || 0)·G'' ''' Spend and Scan Key ''' Since Bob needs his private key ''b'' to check for incoming payments, this requires ''b'' to be exposed to an online device. To minimize the risks involved, Bob can instead publish an address of the form ''(Bscan, Bspend)''. This allows Bob to keep ''bspend'' in offline cold storage and perform the scanning with the public key ''Bspend'' and private key ''bscan''. Alice performs the tweak using both of Bob's public keys in the following manner: * Let ''P0 = Bspend + hash(input_hash·a·Bscan || 0)·G'' Bob detects this payment by calculating ''P0 = Bspend + hash(input_hash·bscan·A || 0)·G'' with his online device and can spend from his cold storage signing device using ''(bspend + hash(input_hash·bscan·A || 0)) mod n'' as the private key. ''' Labels ''' For a single silent payment address of the form ''(Bscan, Bspend)'', Bob may wish to differentiate incoming payments. Naively, Bob could publish multiple silent payment addresses, but this would require him to scan for each one, which becomes prohibitively expensive. Instead, Bob can label his spend public key ''Bspend'' with an integer ''m'' in the following way: * Let ''Bm = Bspend + hash(bscan || m)·G'' where m is an incrementable integer starting from 1 * Publish ''(Bscan, B1)'', ''(Bscan, B2)'' etc. Alice performs the tweak as before using one of the published ''(Bscan, Bm)'' pairs. Bob detects the labeled payment in the following manner: * Let ''P0 = Bspend + hash(input_hash·bscan·A || 0)·G'' * Subtract ''P0'' from each of the transaction outputs and check if the remainder matches any of the labels (''hash(bscan || 1)·G'', ''hash(bscan || 2)·G'' etc.) that the wallet has previously used It is important to note that an outside observer can easily deduce that each published ''(Bscan, Bm)'' pair is owned by the same entity as each published address will have ''Bscan'' in common. As such, labels are not meant as a way for Bob to manage separate identities, but rather a way for Bob to determine the source of an incoming payment. ''' Labels for change ''' Bob can also use labels for managing his own change outputs. We reserve ''m = 0'' for this use case. This gives Bob an alternative to using BIP32 for managing change, while still allowing him to know which of his unspent outputs were change when recovering his wallet from the master key. It is important that the wallet never hands out the label with ''m = 0'' in order to ensure nobody else can create payments that are wrongly labeled as change. While the use of labels is optional, every receiving silent payments wallet should at least scan for the change label when recovering from backup in order to ensure maximum cross-compatibility. == Specification == We use the following functions and conventions: * ''outpoint'' (36 bytes): the COutPoint of an input (32-byte txid, least significant byte first || 4-byte vout, least significant byte first)'''Why are outpoints little-endian?''' Despite using big endian throughout the rest of the BIP, outpoints are sorted and hashed matching their transaction serialization, which is little-endian. This allows a wallet to parse a serialized transaction for use in silent payments without needing to re-order the bytes when computing the input hash. Note: despite outpoints being stored and serialized as little-endian, the transaction hash (txid) is always displayed as big-endian. * ser32(i): serializes a 32-bit unsigned integer ''i'' as a 4-byte sequence, most significant byte first. * ser256(p): serializes the integer p as a 32-byte sequence, most significant byte first. * serP(P): serializes the coordinate pair P = (x,y) as a byte sequence using SEC1's compressed form: (0x02 or 0x03) || ser256(x), where the header byte depends on the parity of the omitted Y coordinate. For everything not defined above, we use the notation from [https://github.com/bitcoin/bips/blob/master/bip-0340.mediawiki#specification BIP340]. This includes the ''hashtag(x)'' notation to refer to ''SHA256(SHA256(tag) || SHA256(tag) || x)''. === Versions === This document defines version 0 (''sp1q''). Version is communicated through the address in the same way as bech32 addresses (see [https://github.com/bitcoin/bips/blob/master/bip-0173.mediawiki#bech32 BIP173]. Future upgrades to silent payments will require a new version. As much as possible, future upgrades should support receiving from older wallets (e.g. a silent payments v0 wallet can send to both v0 and v1 addresses). Any changes that break compatibility with older silent payment versions should be a new BIP. Future silent payments versions will use the following scheme: {| class="wikitable" |- ! !0 !1 !2 !3 !4 !5 !6 !7 !Compatibility |- !+0 |q||p||z||r||y||9||x||8||rowspan="4" | backwards compatible |- !+8 |g||f||2||t||v||d||w||0 |- !+16 |s||3||j||n||5||4||k||h |- !+24 |c||e||6||m||u||a||7|| - |} ''v31'' (l) is reserved for a backwards incompatible change, if needed. For silent payments v0: * If the receiver's silent payment address version is: ** ''v0'': check that the data part is exactly 66-bytes. Otherwise, fail ** ''v1'' through ''v30'': read the first 66-bytes of the data part and discard the remaining bytes ** ''v31'': fail * Receiver addresses are always [https://github.com/bitcoin/bips/blob/master/bip-0341.mediawiki BIP341] taproot outputs'''Why only taproot outputs?''' Providing too much optionality for the protocol makes it difficult to implement and can be at odds with the goal of providing the best privacy. Limiting to taproot outputs helps simplify the implementation significantly while also putting users in the best eventual anonymity set. * The sender should sign with one of the sighash flags ''DEFAULT'', ''ALL'', ''SINGLE'', ''NONE'' (''ANYONECANPAY'' is unsafe). It is strongly recommended implementations use ''SIGHASH_ALL'' (''SIGHASH_DEFAULT'' for taproot inputs) when possible'''Why is it unsafe to use ''SIGHASH_ANYONECANPAY''?''' Since the output address for the receiver is derived from the sum of the [[#inputs-for-shared-secret-derivation|Inputs For Shared Secret Derivation]] public keys, the inputs must not change once the sender has signed the transaction. If the inputs are allowed to change after the fact, the receiver will not be able to calculate the shared secret needed to find and spend the output. It is currently an open question on how a future version of silent payments could be made to work with new sighash flags such as ''SIGHASH_GROUP'' and ''SIGHASH_ANYPREVOUT''. * Inputs used to derive the shared secret are from the ''[[#inputs-for-shared-secret-derivation|Inputs For Shared Secret Derivation]]'' list === Scanning silent payment eligible transactions === For silent payments v0 a transaction MUST be scanned if and only if all of the following are true: * The transaction contains at least one BIP341 taproot output (note: spent transactions optionally can be skipped by only considering transactions with at least one unspent taproot output) * The transaction has at least one input from the ''[[#inputs-for-shared-secret-derivation|Inputs For Shared Secret Derivation]]'' list * The transaction does not spend an output with SegWit version > 1'''Why skip transactions that spend SegWit version > 1?''' Skipping transactions that spend unknown output scripts allows us to have a clean upgrade path for silent payments by avoiding the need to scan the same transaction multiple times with different rule sets. If a new SegWit version is added in the future and silent payments v1 is released with support, we would want to avoid having to first scan the transaction with the silent payment v0 rules and then again with the silent payment v1 rules. Note: this restriction only applies to the inputs of a transaction. === Address encoding === A silent payment address is constructed in the following manner: * Let ''Bscan, bscan = Receiver's scan public key and corresponding private key'' * Let ''Bspend, bspend = Receiver's spend public key and corresponding private key'' * Let ''Bm = Bspend + hashBIP0352/Label(ser256(bscan) || ser32(m))·G'', where ''hashBIP0352/Label(ser256(bscan) || ser32(m))·G'' is an optional integer tweak for labeling ** If no label is applied then ''Bm = Bspend'' * The final address is a [https://github.com/bitcoin/bips/blob/master/bip-0350.mediawiki Bech32m] encoding of: ** The human-readable part "sp" for mainnet, "tsp" for testnets (e.g. signet, testnet) ** The data-part values: *** The character "q", to represent a silent payment address of version 0 *** The 66-byte concatenation of the receiver's public keys, ''serP(Bscan) || serP(Bm)'' Note: [https://github.com/bitcoin/bips/blob/master/bip-0173.mediawiki BIP173] imposes a 90 character limit for Bech32 segwit addresses and limits versions to 0 through 16, whereas a silent payment address requires ''at least'' 117 characters ''' Why do silent payment addresses need at least 117 characters?''' A silent payment address is a bech32m encoding comprised of the following parts: * HRP [2-3 characters] * separator [1 character] * version [1-2 characters] * payload, 66 bytes concatenated pubkeys [ceil(66*8/5) = 106 characters] * checksum [6 characters] For a silent payments v0 address, this results in a 117-character address when using a 3-character HRP. Future versions of silent payment addresses may add to the payload, which is why a 1023-character limit is suggested. and allows versions up to 31. Additionally, since higher versions may add to the data field, it is recommended implementations use a limit of 1023 characters (see [https://github.com/bitcoin/bips/blob/master/bip-0173.mediawiki#checksum-design BIP173: Checksum design] for more details). === Inputs For Shared Secret Derivation === While any UTXO with known output scripts can be used to fund the transaction, the sender and receiver MUST use inputs from the following list when deriving the shared secret: * ''P2TR'' * ''P2WPKH'' * ''P2SH-P2WPKH'' * ''P2PKH'' Inputs with conditional branches or multiple public keys (e.g. ''CHECKMULTISIG'') are excluded from shared secret derivation as this introduces malleability and would allow a sender to re-sign with a different set of public keys after the silent payment output has been derived. This is not a concern when the sender controls all of the inputs, but is an issue for CoinJoins and other collaborative protocols, where a malicious participant can participate in deriving the silent payment address with one set of keys and then re-broadcast the transaction with signatures for a different set of public keys. P2TR can have hidden conditional branches (script path), but we work around this by using only the output public key. For all of the output types listed, only X-only and compressed public keys are permitted''' Why only compressed public keys ''' Uncompressed and hybrid public keys are less common than compressed keys and generally considered to be a bad idea due to their blockspace inefficiency. Additionally, [https://github.com/bitcoin/bips/blob/master/bip-0143.mediawiki#restrictions-on-public-key-type BIP143] recommends restricting P2WPKH inputs to compressed keys as a default policy.. ''' P2TR ''' '' Keypath spend '' witness: scriptSig: (empty) scriptPubKey: 1 <32-byte-x-only-key> (0x5120{32-byte-x-only-key}) The sender uses the private key corresponding to the taproot output key (i.e. the tweaked private key). This can be a single private key or an aggregate key (e.g. taproot outputs using MuSig or FROST)'''Are key aggregation techniques like FROST and MuSig supported?''' While we do not recommend it due to lack of a security proof (except if all participants are trusted or are the same entity), any taproot output able to do a key path theoretically is supported. Any offline key aggregation technique can be used, such as FROST or MuSig. This would require participants to perform the ECDH step collaboratively e.g. ''ECDH = a1·Bscan + a2·Bscan + ... + at·Bscan'' and ''P = Bspend + hash(input_hash·ECDH || 0)·G''. Additionally, it may be necessary for the participants to provide a DLEQ proof to ensure they are not acting maliciously.. The receiver obtains the public key from the ''scriptPubKey'' (i.e. the taproot output key). '' Script path spend '' witness: scriptSig: (empty) scriptPubKey: 1 <32-byte-x-only-key> (0x5120{32-byte-x-only-key}) Same as a keypath spend, the sender MUST use the private key corresponding to the taproot output key. If this key is not available, the output cannot be included as an input to the transaction. Same as a keypath spend, the receiver obtains the public key from the ''scriptPubKey'' (i.e. the taproot output key)''' Why not skip all taproot script path spends? ''' This causes malleability issues for CoinJoins. If the silent payments protocol skipped taproot script path spends, this would allow an attacker to join a CoinJoin round, participate in deriving the silent payment address using the tweaked private key for a key path spend, and then broadcast their own version of the transaction using the script path spend. If the receiver were to only consider key path spends, they would skip the attacker's script path spend input when deriving the shared secret and not be able to find the funds. Additionally, there may be scenarios where the sender can perform ECDH with the key path private key but spends the output using the script path.. The one exception is script path spends that use NUMS point ''H'' as their internal key (where ''H'' is constructed by taking the hash of the standard uncompressed encoding of the secp256k1 base point ''G'' as X coordinate, see [https://github.com/bitcoin/bips/blob/master/bip-0341.mediawiki#constructing-and-spending-taproot-outputs BIP341: Constructing and spending Taproot outputs] for more details), in which case the input will be skipped for the purposes of shared secret derivation'''Why skip outputs with H as the internal taproot key?''' If use cases get popularized where the taproot key path cannot be used, these outputs can still be included without getting in the way of making a silent payment, provided they specifically use H as their internal taproot key.. The receiver determines whether or not to skip the input by checking in the control block if the taproot internal key is equal to ''H''. ''' P2WPKH ''' witness: <33-byte-compressed-key> scriptSig: (empty) scriptPubKey: 0 <20-byte-key-hash> (0x0014{20-byte-key-hash}) The sender performs the tweak using the private key for the output and the receiver obtains the public key as the last witness item. ''' P2SH-P2WPKH ''' witness: <33-byte-compressed-key> scriptSig: <0 <20-byte-key-hash>> (0x160014{20-byte-key-hash}) scriptPubKey: HASH160 <20-byte-script-hash> EQUAL (0xA914{20-byte-script-hash}87) The sender performs the tweak using the private key for the nested ''P2WPKH'' output and the receiver obtains the public key as the last witness item. ''' P2PKH ''' scriptSig: <33-byte-compressed-key> scriptPubKey: OP_DUP HASH160 <20-byte-key-hash> OP_EQUALVERIFY OP_CHECKSIG (0x76A914{20-byte-key-hash}88AC) The receiver obtains the public key from the ''scriptSig''. The receiver MUST parse the ''scriptSig'' for the public key, even if the ''scriptSig'' does not match the template specified (e.g. OP_DROP ). This is to address the [https://en.bitcoin.it/wiki/Transaction_malleability third-party malleability of ''P2PKH'' ''scriptSigs'']. === Sender === ==== Selecting inputs ==== The sending wallet performs coin selection as usual with the following restrictions: * At least one input MUST be from the ''[[#inputs-for-shared-secret-derivation|Inputs For Shared Secret Derivation]]'' list * Exclude inputs with SegWit version > 1 (see ''[[#scanning-silent-payment-eligible-transactions|Scanning silent payment eligible transactions]]'') * For each taproot output spent the sending wallet MUST have access to the private key corresponding to the taproot output key, unless ''H'' is used as the internal public key ==== Creating outputs ==== After the inputs have been selected, the sender can create one or more outputs for one or more silent payment addresses in the following manner: * Collect the private keys for each input from the ''[[#inputs-for-shared-secret-derivation|Inputs For Shared Secret Derivation]]'' list * For each private key ''ai'' corresponding to a [https://github.com/bitcoin/bips/blob/master/bip-0341.mediawiki BIP341] taproot output, check that the private key produces a point with an even Y coordinate and negate the private key if not'''Why do taproot private keys need to be checked?''' Recall from [https://github.com/bitcoin/bips/blob/master/bip-0340.mediawiki BIP340] that each X-only public key has two corresponding private keys, ''d'' and ''n - d''. To maintain parity between sender and receiver, it is necessary to use the private key corresponding to the even Y coordinate when performing the ECDH step since the receiver will assume the even Y coordinate when summing the taproot X-only public keys. * Let ''a = a1 + a2 + ... + an'', where each ''ai'' has been negated if necessary ** If ''a = 0'', fail * Let ''input_hash = hashBIP0352/Inputs(outpointL || A)'', where ''outpointL'' is the smallest ''outpoint'' lexicographically used in the transaction and ''A = a·G'' ** If ''input_hash'' is not a valid scalar, i.e., if ''input_hash = 0'' or ''input_hash'' is larger or equal to the secp256k1 group order, fail * Group receiver silent payment addresses by ''Bscan'' (e.g. each group consists of one ''Bscan'' and one or more ''Bm'') * If any of the groups exceed the limit of ''Kmax'' (=2323) silent payment addresses, fail.'''Why is the size of groups (i.e. silent payment addresses sharing the same scan public key) limited by ''Kmax''?''' An adversary could construct a block filled with a single transaction consisting of N=23255 outputs (that's the theoretical maximum under current consensus rules, w.r.t. the block weight limit) that all target the same entity, consisting of one large group. Without a limit on the group size, scanning such a block with the algorithm described in this document would have a complexity of ''O(N2)'' for that entity, taking several minutes on modern systems. By capping the group size at ''Kmax'', we reduce the inner loop iterations to ''Kmax'', thereby decreasing the worst-case block scanning complexity to ''O(N·Kmax)''. This cuts down the scanning cost to the order of tens of seconds. The chosen value of ''Kmax'' = 2323 represents the maximum number of P2TR outputs that can fit into a 100kvB transaction, meaning a transaction that adheres to the current standardness rules is guaranteed to be within the limit. This ensures flexibility and also mitigates potential fingerprinting issues. * For each group: ** Let ''ecdh_shared_secret = input_hash·a·Bscan'' ** Let ''k = 0'' ** For each ''Bm'' in the group: *** Let ''tk = hashBIP0352/SharedSecret(serP(ecdh_shared_secret) || ser32(k))'' **** If ''tk'' is not a valid scalar, i.e., if ''tk = 0'' or ''tk'' is larger or equal to the secp256k1 group order, fail *** Let ''Pmn = Bm + tk·G'' *** Encode ''Pmn'' as a [https://github.com/bitcoin/bips/blob/master/bip-0341.mediawiki BIP341] taproot output *** Optionally, repeat with k++ to create additional outputs for the current ''Bm'' *** If no additional outputs are required, continue to the next ''Bm'' with ''k++''''' Why not re-use ''tk'' when paying different labels to the same receiver?''' If paying the same entity but to two separate labeled addresses in the same transaction without incrementing ''k'', an outside observer could subtract the two output values and observe that this value is the same as the difference between two published silent payment addresses and learn who the recipient is. ** Optionally, if the sending wallet implements receiving silent payments, it can create change outputs by sending to its own silent payment address using label ''m = 0'', following the steps above All generated outputs MUST be present in the final transaction. If an output ''Pi'' with ''i < k'' is omitted, the receiver will not be able to find outputs ''Pj'' where ''i < j <= k''. === Receiver === ==== Key Derivation ==== Two keys are needed to create a silent payments address: the spend key and the scan key. To ensure compatibility, wallets MAY use BIP32 derivation with the following derivation paths for the spend and scan key. When using BIP32 derivation, wallet software MUST use hardened derivation'''Why use BIP32 hardened derivation?''' Using BIP32 derivation allows users to add silent payments to an existing master seed. It also ensures that a user's silent payment funds are recoverable in any BIP32/BIP43 compatible wallet. Using hardened derivation ensures that it is safe to export the scan private key without exposing the master key or spend private key. for both the spend and scan key. A scan and spend key pair using BIP32 derivation are defined (taking inspiration from [https://github.com/bitcoin/bips/blob/master/bip-0044.mediawiki BIP44]) in the following manner: scan_private_key: m / purpose' / coin_type' / account' / 1' / 0 spend_private_key: m / purpose' / coin_type' / account' / 0' / 0 purpose is a constant set to ''352'' following the BIP43 recommendation. Refer to [https://github.com/bitcoin/bips/blob/master/bip-0043.mediawiki BIP43] and [https://github.com/bitcoin/bips/blob/master/bip-0044.mediawiki BIP44] for more details. ==== Scanning ==== If each of the checks in ''[[#scanning-silent-payment-eligible-transactions|Scanning silent payment eligible transactions]]'' passes, the receiving wallet must: * Let ''A = A1 + A2 + ... + An'', where each ''Ai'' is the public key of an input from the ''[[#inputs-for-shared-secret-derivation|Inputs For Shared Secret Derivation]]'' list ** If ''A'' is the point at infinity, skip the transaction * Let ''input_hash = hashBIP0352/Inputs(outpointL || A)'', where ''outpointL'' is the smallest ''outpoint'' lexicographically used in the transaction ** If ''input_hash'' is not a valid scalar, i.e., if ''input_hash = 0'' or ''input_hash'' is larger or equal to the secp256k1 group order, fail * Let ''ecdh_shared_secret = input_hash·bscan·A'' * Check for outputs: ** Let ''outputs_to_check'' be the taproot output keys from all taproot outputs in the transaction (spent and unspent). ** Starting with ''k = 0'': *** If ''k == Kmax'' (=2323), stop scanning. *** Let ''tk = hashBIP0352/SharedSecret(serP(ecdh_shared_secret) || ser32(k))'' **** If ''tk'' is not a valid scalar, i.e., if ''tk = 0'' or ''tk'' is larger or equal to the secp256k1 group order, fail *** Compute ''Pk = Bspend + tk·G'' *** For each ''output'' in ''outputs_to_check'': **** If ''Pk'' equals ''output'': ***** Add ''Pk'' to the wallet ***** Remove ''output'' from ''outputs_to_check'' and rescan ''outputs_to_check'' with ''k++'' **** Else, check for labels (always check for the change label, i.e. ''hashBIP0352/Label(ser256(bscan) || ser32(m))'' where ''m = 0'')''' Why precompute labels?''' Precomputing the labels is not strictly necessary: a wallet could track the max number of labels it has used (call it ''M'') and scan for labels by adding ''hash(bscan || m)·G'' to ''P0'' for each label ''m'' up to ''M'' and comparing to the transaction outputs. This is more performant than precomputing the labels and checking via subtraction in cases where the number of eligible outputs exceeds the number of labels in use. In practice this will mainly apply to users that choose never to use labels, or users that use a single label for generating silent payment change outputs. If using a large number of labels, the wallet would need to add all possible labels to each output. This ends up being ''n·M'' additions, where ''n'' is the number of outputs in the transaction and ''M'' is the number of labels in the wallet. By precomputing the labels, the wallet only needs to compute ''hash(bscan || m)·G'' once when creating the labeled address and can determine if a label was used via a lookup, rather than adding each label to each output.: ***** Compute ''label = output - Pk'' ***** Check if ''label'' exists in the list of labels used by the wallet ***** If a match is found: ****** Add ''Pk + label'' to the wallet ****** Remove ''output'' from ''outputs_to_check'' and rescan ''outputs_to_check'' with ''k++'' ***** If a label is not found, negate ''output'' and check a second time''' Why negate the output?''' Unfortunately taproot outputs are X-only, meaning we don't know what the correct Y coordinate is. This causes this specific calculation to fail 50% of the time, so we need to repeat it with the other Y coordinate by negating the output. *** If no matches are found, stop ==== Spending ==== Recall that a silent payment output is of the form ''Bspend + tk·G + hashBIP0352/Label(ser256(bscan) || ser32(m))·G'', where ''hashBIP0352/Label(ser256(bscan) || ser32(m))·G'' is an optional label. To spend a silent payment output: * Let ''d = (bspend + tk + hashBIP0352/Label(ser256(bscan) || ser32(m))) mod n'', where ''hashBIP0352/Label(ser256(bscan) || ser32(m))'' is the optional label * Spend the [https://github.com/bitcoin/bips/blob/master/bip-0341.mediawiki BIP341] output with the private key ''d'' ==== Backup and Recovery ==== Since each silent payment output address is derived independently, regular backups are recommended. When recovering from a backup, the wallet will need to scan since the last backup to detect new payments. If using a seed/seed phrase only style backup, the user can recover the wallet's unspent outputs from the UTXO set (i.e. only scanning transactions with at least one unspent taproot output) and can recover the full wallet history by scanning the blockchain starting from the wallet birthday. If a wallet uses labels, this information SHOULD be included in the backup. If the user does not know whether labels were used, it is strongly recommended they always precompute and check a large number of labels (e.g. 100k labels) to use when re-scanning. This ensures that the wallet can recover all funds from only a seed/seed phrase backup. The change label should simply always be scanned for, even when no other labels were used. This ensures the use of a change label is not critical for backups and maximizes cross-compatibility. == Backward Compatibility == Silent payments introduces a new address format and protocol for sending and as such is not compatible with older wallet software or wallets which have not implemented the silent payments protocol. == Test Vectors == A [[bip-0352/send_and_receive_test_vectors.json|collection of test vectors in JSON format]] is provided, along with a [[bip-0352/reference.py|python reference implementation]]. It uses a vendored copy of the [https://github.com/secp256k1lab/secp256k1lab/ secp256k1lab] library at version 1.0.0 (commit [https://github.com/secp256k1lab/secp256k1lab/commit/44dc4bd893b8f03e621585e3bf255253e0e0fbfb 44dc4bd893b8f03e621585e3bf255253e0e0fbfb]). Each test vector consists of a sending test case and corresponding receiving test case. This is to allow sending and receiving to be implemented separately. To ensure determinism while testing, sort the array of ''Bm'' by amount (see the [[bip-0352/reference.py|reference implementation]]). Test cases use the following schema: ''' test_case ''' { "comment": "Comment describing the behavior being tested", "sending": [], "receiving": [], } ''' sender ''' { "given": { "vin": [], "recipients": [ { "address": , "scan_pub_key": , "spend_pub_key": , "count": }, ... ] }, "expected": { "outputs": [], "n_outputs": , }, } ''' recipient ''' { "given": { "vin": [], "key_material": { "scan_priv_key": , "spend_priv_key": , } "labels": [], }, "expected": { "addresses": [], "outputs": [ { "priv_key_tweak": , "pub_key": , "signature": }, ... ], "n_outputs": } } Wallets should include inputs not in the ''[[#inputs-for-shared-secret-derivation|Inputs For Shared Secret Derivation]]'' list when testing to ensure that only inputs from the list are being used for shared secret derivation. Additionally, receiving wallets should include non-silent payment outputs for themselves in testing to ensure silent payments scanning does not interfere with regular outputs detection. === Functional tests === Below is a list of functional tests which should be included in sending and receiving implementations. ==== Sending ==== * Ensure taproot outputs are excluded during coin selection if the sender does not have access to the key path private key (unless using ''H'' as the taproot internal key) * Ensure the silent payment address is re-derived if inputs are added or removed during RBF ==== Receiving ==== * Ensure the public key can be extracted from non-standard ''P2PKH'' scriptSigs * Ensure taproot script path spends are included, using the taproot output key (unless ''H'' is used as the taproot internal key) * Ensure the scanner can extract the public key from each of the input types supported (e.g. ''P2WPKH'', ''P2SH-P2WPKH'', etc.) == Appendix A: Light Client Support == This section proposes a few ideas for how light clients could support scanning for incoming silent payments (sending is fairly straightforward) in ways that preserve bandwidth and privacy. While this is out of scope for the current BIP, it is included to motivate further research into this topic. In this context, a light client refers to any bitcoin wallet client which does not process blocks and does not have a direct connection to a node which does process blocks (e.g. a full node). Based on this definition, clients that directly connect to a personal electrum server or a bitcoin node are not light clients. This distinction makes the problem for light clients more clear: light clients need a way to source the necessary data for performing the tweaks and a way of determining if any of the generated outputs exist in a block. === Tweak Data === Recall that a silent payment eligible transaction follows [[#scanning-silent-payment-eligible-transactions|certain conditions]] and should have at least one unspent taproot output. Full nodes (or any index server backed by a full node, such as electrum server) can build an index which collects all of the eligible public keys for a silent payments eligible transaction, sums them up, multiplies the sum by the ''input_hash'', and serves them to clients. This would be 33 bytes per silent payment eligible transaction. For a typical bitcoin block of ~3500 txs, lets assume every transaction is a silent payments eligible transaction. This means a client would need to request ''33 bytes * 3500'' of data per block (roughly 100 kB per block). If a client were to request data for every block, this would amount to ~450 MB per month, assuming 100% taproot usage and all non-dust outputs remain unspent for > 1 month. As of today, these numbers are closer to 7–12 kB per block (30–50 MB per month)''' Data for Appendix A ''' These numbers are based on data from January 2023 until July 2024. See [https://github.com/josibake/bitcoin-data-analysis/blob/main/notebooks/silent-payments-light-client-data.ipynb Silent payments light client data] for the full analysis.. === Transaction cut-through === It is unlikely a light client would need to scan every block and as such can take advantage of transaction cut-through, depending on how often they choose to scan for new blocks. Empirically, ~75% of transactions with at least one non-dust unspent taproot output will have spent all non-dust taproot UTXOs in 150 blocks or less. This means a client that only scans once per day could ''significantly'' cut down on the number of blocks and the number of transactions per block that they need to request by only asking for data on transactions that were created since their last scan and that still have at least one non-dust unspent taproot output as of the current block height. Based on taproot adoption as of July 2024, a light client scanning once every 3 days would use roughly 30 MB per month. [[File:bip-0352/scan_data_downloader_per_month.png]] === BIP158 === Once a light client has the tweak data for a block, they can determine whether or not an output to them exists in the block using BIP158 block filters. Per BIP158, they would then request the entire block and add the transaction to their wallet, though it maybe be possible to only request the prevout txids and vouts for all transactions with at least one taproot output, along with the scriptPubKeys and amounts. This would allow the client to download the necessary data for constructing a spending transaction, without downloading the entire block. How this affects the security assumptions of BIP158 is an open question. === Out-of-band notifications === Assuming a secure messaging protocol exists, the sender can send an encrypted (using the scan public key of the silent payment address) notification to the receiver with the following information: * The spend public key (communicates the label) * The shared secret portion of the private key (i.e ''hash(ecdh_shared_secret || k)'') * The outpoint and amount (so it's immediately spendable) It is important to note that these notifications are not required. At any point, the receiver can fall back to scanning for silent payment transactions if they don't trust the notifications they are receiving, are being spammed with fake notifications, or if they are concerned that they are not receiving notifications. A malicious notification could potentially cause the following issues: * You did not actually receive money to the stated key ** This can be probabilistically resolved by matching the key against the BIP158 block filters and assuming it's not a false positive, or fully resolved by downloading the block * You received money but the outpoint or amount is incorrect, so attempts to spend it will fail or cause you to overpay fees ** There doesn't seem to be much motivation for malicious senders to ever do this, but light clients need to take into account that this can occur and should ideally check for it by downloading the block * The private key is correct but it wasn't actually derived using the silent payment protocol, causing recovery from back-up to fail (unsafe - no implementation should ever allow this) ** This can be detected by downloading the tweak data of the corresponding block and should be resolved by immediately spending the output Wallet designers can choose which tradeoffs they find appropriate. For example, a wallet could check the block filter to at least probabilistically confirm the likely existence of the UTXO, thus efficiently cutting down on spam. The payment could then be marked as unconfirmed until a scan is performed and the existence of the UTXO in accordance to the silent payment specification is verified. == Changelog == To help implementers understand updates to this document, we attach a version number that resembles ''semantic versioning'' (MAJOR.MINOR.PATCH). The MAJOR version is incremented if changes to the BIP are introduced that are incompatible with prior versions. The MINOR version is incremented whenever the inputs or the output of an algorithm changes in a backward-compatible way or new backward-compatible functionality is added. The PATCH version is incremented for other changes that are noteworthy (bug fixes, test vectors, important clarifications, etc.). * '''1.1.0''' (2026-03-02): ** Introduce per-group recipient limit ''Kmax'' to mitigate quadratic scanning behavior for adversarial transactions. * '''1.0.2''' (2025-07-25): ** Clarify how to handle the improbable corner case where the output of SHA256 is equal to 0 or greater than or equal to the secp256k1 curve order. * '''1.0.1''' (2024-06-22): ** Add steps to fail if private key sum is zero (for sender) or public key sum is point at infinity (for receiver), add corresponding test vectors. * '''1.0.0''' (2024-05-08): ** Initial version, merged as BIP-352. == Acknowledgements == This document is the result of many discussions and contains contributions by a number of people. The authors wish to thank all those who provided valuable feedback and reviews, including the participants of the [https://gist.github.com/RubenSomsen/21c477c90c942acf45f8e8f5c1ad4fae BIP47 Prague discussion], the [https://github.com/josibake/silent-payments-workshop Advancing Bitcoin silent payments Workshop], and [https://btctranscripts.com/bitcoin-core-dev-tech/2023-04/2023-04-26-silent-payments/ coredev]. The authors would like to also thank [https://github.com/w0xlt w0xlt] for writing the initial implementation of silent payments. == Rationale and References == ================================================ FILE: bip-0353.mediawiki ================================================
  BIP: 353
  Layer: Applications
  Title: DNS Payment Instructions
  Authors: Matt Corallo 
           Bastien Teinturier 
  Status: Complete
  Type: Specification
  Assigned: 2024-02-10
  License: CC0-1.0
  Discussion: 2024-02-13: https://groups.google.com/g/bitcoindev/c/uATaflkYglQ [bitcoin-dev] Mapping Human-Readable Names to Payment Instructions
==Copyright== This BIP is licensed under the CC0-1.0 license. ==Abstract== This BIP proposes a standard format for encoding [[bip-0021.mediawiki|BIP 21]] URI schemes in DNS TXT records. ==Motivation== Various Bitcoin and other cryptocurrency applications have developed human-readable names for payment instructions over time, with marketplace adoption signaling strong demand for it from users. The DNS provides a standard, global, hierarchical namespace mapping human-readable labels to records of various forms. Using DNSSEC, the DNS provides cryptographic guarantees using a straightforward PKI which follows the hierarchical nature of the DNS, allowing for stateless and even offline validation of DNS records from a single trusted root. Further, because DNS queries are generally proxied through ISP-provided or other resolvers, DNS queries usually do not directly expose the queryer's IP address. Further, because of the prevalence of open resolvers, the simplicity of the protocol, and broad availability of DNS recursive resolver implementations, finding a proxy for DNS records is trivial. Thus, using TXT records to store Bitcoin payment instructions allows for human-readable Bitcoin payment destinations which can be trivially verified on hardware wallets and which can be resolved relatively privately. ==Specification== === General rules for handling === Bitcoin wallets MUST NOT prefer to use DNS-based resolving when methods with explicit public keys or addresses are available. In other words, if a standard Bitcoin address or direct BIP 21 URI is available or would suffice, Bitcoin wallets MUST prefer to use that instead. === Records === Payment instructions are indexed by both a user and a domain. Instructions for a given user and domain are stored at user.user._bitcoin-payment.domain in a single TXT RR. The TXT RR’s RDATA MUST consist of one or more DNS s (see [[https://www.rfc-editor.org/rfc/rfc1035#section-3.3.14|RFC 1035 §3.3.14]]), each ≤255 bytes. All payment instructions MUST be DNSSEC-signed. Payment instructions MAY resolve through CNAME or DNAME records as long as all such records and the ultimate records pointed to by them are DNSSEC signed. User and domain names which are not expressible using standard printable ASCII MUST be encoded using the punycode IDN encoding defined in [[https://datatracker.ietf.org/doc/html/rfc3492|RFC 3492]] and [[https://datatracker.ietf.org/doc/html/rfc5891|RFC 5891]]. Note that because resolvers are not required to support resolving non-ASCII identifiers, wallets SHOULD avoid using non-ASCII identifiers. For payment instructions that have a built-in expiry time (e.g. Lightning BOLT 12 offers), care must be taken to ensure that the DNS records expire prior to the expiry of the payment instructions. Otherwise, senders may have payment instructions cached locally which have expired, preventing payment. === Resolution === Clients resolving Bitcoin payment instructions MUST ignore any TXT records at the same label which do not begin with (ignoring case) "bitcoin:". Resolvers encountering multiple "bitcoin:"-matching TXT records at the same label MUST treat the records as invalid and refuse to use any payment instructions therein. Clients resolving Bitcoin payment instructions MUST reconstruct the bitcoin: URI by concatenating the TXT RR’s fields in RDATA order, without inserting separators, before parsing.DNS TXT RDATA consists of one or more length-prefixed strings with a maximum of 255 bytes of content; see RFC 1035 §3.3.14. Clients MUST NOT concatenate across multiple TXT RRs at the same owner name. Clients resolving Bitcoin payment instructions MUST fully validate DNSSEC signatures leading to the DNS root (including any relevant CNAME or DNAME records) and MUST NOT accept DNSSEC signatures which use SHA-1 or RSA with keys shorter than 1024 bits. Resolvers MAY accept SHA-1 DS records. Clients resolving Bitcoin payment instructions MUST NOT trust a remote resolver to validate DNSSEC records on their behalf. Clients resolving Bitcoin payment instructions MUST support resolving through CNAME or DNAME records. Resolvers MAY support resolving non-ASCII user and domain identifiers. Resolvers which do support non-ASCII user and domain identifiers MUST take precautions to prevent homograph attacks and SHOULD consider denying paste functionality when entering non-ASCII identifiers. Wallets which do not take any such precautions MUST instead display non-ASCII user and domain identifiers using their raw punycode. As such, wallets SHOULD NOT create identifiers which are not entirely printable ASCII. While clients MAY cache the payment instructions they receive from the DNS, clients MUST NOT cache the payment instructions received from the DNS for longer than the TTL provided by their DNS resolver, and further MUST NOT cache the payment instructions for longer than the lowest initial TTL (which is signed as a part of DNSSEC signatures) received in the full DNSSEC chain leading from the DNS root to the resolved TXT record. === Address Reuse === Payment instructions with on-chain addresses which will be re-used SHOULD be rotated as regularly as possible to reduce address reuse. Such payment instructions SHOULD also use a relatively short DNS TTL to ensure regular rotation takes effect quickly. In cases where this is not practical, payment instructions SHOULD NOT contain on-chain addresses (i.e. the URI path SHOULD be empty). Payment instructions which do contain on-chain addresses which will be re-used SHOULD be rotated after any transaction to such an address is confirmed on-chain. === Display === When displaying a verified human-readable name, wallets SHOULD prefix it with ₿, i.e. ₿user@domain. They SHOULD parse recipient information in both user@domain and ₿user@domain forms and resolve such an entry into recipient information using the above record. For the avoidance of doubt, the ₿ is *not* included in the DNS label which is resolved. Wallets providing the ability for users to "copy" their address information SHOULD copy the underlying URI directly, rather than the human-readable name. This avoids an additional DNS lookup by the application in which it is pasted. Wallets that nevertheless provide users the ability to copy their human-readable name, MUST include the ₿ prefix (i.e. copy it in the form ₿user@domain). Wallets accepting payment information from external devices (e.g. hardware wallets) SHOULD accept RFC 9102-formatted proofs (as a series of unsorted AuthenticationChain records) and, if verification succeeds, SHOULD display the recipient in the form ₿user@domain. === PSBT types === Wallets accepting payment information from external devices (e.g. hardware wallets) MAY examine the following per-output PSBT fields to fetch RFC 9102-formatted proofs. Wallets creating PSBTs with recipient information derived from human-readable names SHOULD include the following fields. When validating the contained proof, clients MUST enforce the inception on all contained RRSigs is no later than the current time and that the expiry of all RRSigs is no earlier than an hour in the past. Clients MAY allow for an expiry up to an hour in the past to allow for delays between PSBT construction and signing only if such a delay is likely to occur in their intended usecase. {| ! Name ! ! ! ! Description ! Versions Requiring Inclusion ! Versions Requiring Exclusion ! Versions Allowing Inclusion |- | BIP 353 DNSSEC proof | PSBT_OUT_DNSSEC_PROOF = 0x35 | None | <1-byte-length-prefixed BIP 353 human-readable name without the ₿ prefix> | A BIP 353 human-readable name (without the ₿ prefix), prefixed by a 1-byte length. Followed by an [[https://www.rfc-editor.org/rfc/rfc9102.html#name-dnssec-authentication-chain|RFC 9102 DNSSEC AuthenticationChain]] (i.e. a series of DNS Resource Records in no particular order) providing a DNSSEC proof to a BIP 353 DNS TXT record. | | | 0, 2 |} == Rationale == === Display === There are several ways in which human-readable payment instructions could be displayed in wallets. In order to ensure compatibility with existing human-readable names schemes, @ is used as the separator between the user and domain parts. However, simply using the @ separator can lead to confusion between email addresses on a given domain and payment instructions on a domain. In order to somewhat reduce the incidence of such confusion, a ₿ prefix is used. === Rotation === On-chain addresses which are re-used (i.e. not including schemes like [[bip-0352.mediawiki|Silent Payments]]) need to be rotated to avoid contributing substantially to address reuse. However, rotating them on a timer or any time a transaction enters the mempool could lead to substantial overhead from excess address generation. Instead, rotating addresses any time a transaction is confirmed on-chain ensures address rotation happens often while bounding the maximum number of addresses needed to one per block, which grows very slowly and will not generate an address set too large to handle while scanning the chain going forward. === Alternatives === There are many existing schemes to resolve human-readable names to cryptocurrency payment instructions. Sadly, these current schemes suffer from a myriad of drawbacks, including (a) lacking succinct proofs of namespace to public key mappings, (b) revealing sender IP addresses to recipients or other intermediaries as a side-effect of payment, (c) relying on the bloated TLS Certificate Authority infrastructure, or (d) lacking open access, not allowing anyone to create a namespace mapping. ==== DNS Rather than blockchain-based solutions ==== There are many blockchain-based alternatives to the DNS which feature better censorship-resistance and, in many cases, security. However, here we chose to use the standard ICANN-managed DNS namespace as many blockchain-based schemes suffer from (a), above (though in some cases this could be addressed with cryptographic SNARK schemes). Further, because they do not have simple client-side querying ability, many of these schemes use trusted intermediaries which resolve names on behalf of clients. This reintroduces drawbacks (b) and often (c) as well. Finally, it is worth noting that none of the blockchain-based alternatives to the DNS have had material adoption outside of their specific silos, and committing Bitcoin wallets to rely on a separate system which doesn't see broad adoption may not be sustainable. ==== DNS Rather than HTTP-based solutions ==== HTTP(s)-based payment instruction resolution protocols suffer from drawbacks (a), (b), and (c), above, and generally shouldn't be considered a serious alternative for payment instruction resolution. ==== Private DNS Querying ==== While public recursive DNS resolvers are very common (e.g. 1.1.1.1, 8.8.8.8, and 9.9.9.9), using such resolvers directly (even after validating DNSSEC signatures) introduces drawback (b), at least in regard to a centralized intermediary. Resolving payment instructions recursively locally using a resolver on the same local network or in the paying application would instead introduce drawback (b) directly to the recipient, which may well be worse. For payers not using VPN or other proxying technologies, they generally trust their ISP to not snoop on their DNS requests anyway, so using ISP-provided recursive DNS resolvers is likely the best option. However, for the best privacy, payers are encouraged to perform DNS resolution over Tor or another VPN technology. Lightning payers should consider utilizing DNS resolution over native onion messages, using the protocol described in [[https://github.com/lightning/blips/blob/master/blip-0032.md|BLIP 32]] === DNS Enumeration === In most cases where payments are accepted from any third-party, user enumeration is practical by simply attempting to send small value payments to a list of possible user names. However, storing all valid users in the DNS directly may make such enumeration marginally more practical. Thus, those wishing to avoid such enumeration should carefully ensure all DNS names return valid payment instructions. Note when doing so that wildcard records are identified as such by the DNSSEC RRSIG labels counter and are differentiable from non-wildcard records. == Backwards Compatibility == This work is intended to extend and subsume the existing "Lightning Address" scheme, which maps similar names (without the ₿ prefix) using HTTPS servers to Lightning BOLT 11 payment instructions. Wallets implementing this scheme MAY fall back to existing "Lightning Address" logic if DNS resolution fails but SHOULD NOT do so after this scheme is sufficiently broadly deployed to avoid leaking sender IP address information. == Examples == matt@mattcorallo.com resolves to
matt.user._bitcoin-payment.mattcorallo.com. 1800 IN TXT  "bitcoin:?lno=lno1qsgr30k45jhvkfqxjqheaetac
u4guyxvqttftvqu0f5sneckep3lkwdut7mmhhpcyjmlmnjn4hze8ed7pq88xqkxt2dcw5mlxhz644fms82f7k4ymfxs2ehhpjtxw
xly0w5k8xdtlvpqyd8xzdq4tq8lgupnueshgydr330lc3j5kdcqh54gt7jdg9n68j4eqqeu7ts8uh0qxamee6ndj37tc6mzgejth
vvjqj96p8dz2h" "rsh5z5n27qfk6svjz5pmkh0smq26k0j2j4q36xgq3r5qzet9kuhq4lydpen5mskxgjdvs5faqgv8pmj7cfd7
ny84djksqpqk9ky6juc7fpezecxvg7sjx05dckyypnv9tmvfp6tkpehmtaqmvuupetxuzqf4t0azddjdcpasgw6hxuz9g"
* Note that lno indicates a value containing a lightning BOLT12 offer. * Note that the complete URI is broken into two strings with maximum 255 characters each === Example proofs === The following are valid DNSSEC proofs to be included in the PSBT_OUT_DNSSEC_PROOF record in a PSBT. This encodes address bc1qztwy6xen3zdtt7z0vrgapmjtfz8acjkfp5fp7l to simple@dnssec_proof_tests.bitcoin.ninja valid on August 7, 2025. Note that the second TXT record (which does not start with, case insensitively, "bitcoin:") is ignored. 2773696d706c6540646e737365635f70726f6f665f74657374732e626974636f696e2e6e696e6a610673696d706c650475736572105f626974636f696e2d7061796d656e7412646e737365635f70726f6f665f746573747307626974636f696e056e696e6a6100001000010000001e001110626974636f696e20697320636f6f6c210673696d706c650475736572105f626974636f696e2d7061796d656e7412646e737365635f70726f6f665f746573747307626974636f696e056e696e6a6100001000010000001e003736626974636f696e3a3f62633d626331717a7477793678656e337a647474377a3076726761706d6a74667a3861636a6b6670356670376c0673696d706c650475736572105f626974636f696e2d7061796d656e7412646e737365635f70726f6f665f746573747307626974636f696e056e696e6a6100002e00010000001e006100100d060000001e68a70b7e68948166d0e207626974636f696e056e696e6a61007e51ba5c43c4d18dc62a54d4647d1fcf2cfa594cd6bfddfe834c7b9bc6f1849490972441ea34283c6c7dbab3ed783deabebb3f1081ade02e57795a85220051bc07626974636f696e056e696e6a6100003000010001614500440100030dff753a27b08c3e48a642b210d6fcc444ff9ed4faf9c1241103db4ed3c19a95c3afbb52c0c02eb392ee048cc9e28ac2d272b1053bdc052bc18d5de05d7710196c07626974636f696e056e696e6a6100003000010001614500440101030df65551925ce6321888e685981823d617fbc10f329bffe4081bf18c2372632a5548010bf62e6556a92722629275e0bd001e3d7837d325a353f6a851c5b965259607626974636f696e056e696e6a6100002e000100016145006100300d0200093a806898c73468863d1c716c07626974636f696e056e696e6a610002fd1bf18c2ebb5ece5e28ca76bf30650695636c55633bccae8179c2d1ee7b97e78d188e08ffc869a8f67847bf557516ac12465ebea1acc281d6d636fdab612007626974636f696e056e696e6a6100002b000100000cfc0024716c0d023f7ad5a303e9c1cd1474b8df2ae56f3f82da8637ca55db4d9a2bb85960ca698e07626974636f696e056e696e6a6100002b000100000cfc0024768a0d02ce46a9aff9a06e789c1bdfe250b0ef6ba8d39a53b2a3427c551f5ad375e059b607626974636f696e056e696e6a6100002e000100000cfc0099002b080200000e1068a89268688cd4d892dc056e696e6a61004d88897d7d5f5d920ca436e81ee67b1bb22f1a96309693454ab9d0b06434794162cc42846a4b51a40475a5b44e940c04dd1ac2c902a190ca2251ae89184520b0f3f22c12c51403d0a6e1cd95792e8f6f5036cd2d50dbdfa5eba3b2ee70ff78d40dc2eba2cc899af26954a55e5b5d344d478cabd9423418495caee45c550b1144056e696e6a61000030000100000cfc0088010003080301000197edb59d4f181e2761dd8d0465854339afc71fd89e47155981ddd175cdce79477552aeaf7b5a08fc4ac6025555f60582f2060e630edfb35b9c7cc30990fb9c3dc9f2fd036c962f67b94c9670d4ceaacd77973bca82ab7c9615f7e4320dda5b6d74dec673017c6fa448b5542a804e08ac873c509c1945ff734c320491e4b18e6d056e696e6a61000030000100000cfc01080101030803010001c71e4c9dc49249a27b3ef42fcb8d56b4c3ac76715c7ad01c41d0d432590d15c3c62cee4b2d29ac35f2d72c9b32a70a0243cbd08aeebc9f6f1e0e63d9e1cdfe133c455a82435c0780b750012c942f7ed5b662eec8d9ae885a58993fa78d7561fedcd11d9e1c171acb02d0025837ba61a3c0a6756427414470c9ca0906b298168b5f4d9640e62e1b75dd06be664104ed32cfe447fa21f37401712c720a0dca4bb1bc20f3fa3103cad336bde20b16f73948e6b80dda0a528db536a958868c3870ecddcfb02dfb3cb4d22e2ad49a4b9f78c90ff6c7e10e301b3fb36fe859a94c30084660665741c14ff60d0535013fcf439840ecad82fc9278e4ace68ba95e708249056e696e6a61000030000100000cfc00880100030803010001d28cb7e2bb163d5815838bedeca1006dde8551b379cb963c8a2cb42bc360127e3a5cf88ffc851a67414815b875f65d78c39b58d2fb29a1d4e76d50cb6b4a58a11fe2fb7c1b6db7bf7d72f5a1401e381c57fcc76f599cc73f05095d2bd14d9895e4fa1cff21bd760598a734b640102d11bc159c6b2ae73dbfd2741518142584d1056e696e6a6100002e000100000cfc01190030080100000e1068a89268688cd4d8b402056e696e6a6100646e04cf5f76daa775ff98905ded3d2caad68d3198fc161340d558262c7ba7da28e7538a7f32d5a6485e4448037e8edf55759b7059fdc084f1017f790aa7c0d8f0e4af6c9af04e4afd16ce6052c30da59314c9c98075fd32bb77a81f34bea6190631b9d0a4351a764c14152ea217e6271647bf95b0df4c3d7cc00937bec01b65ad1b5209c976a4843e399f173f196a012c0876bc9afa3457d940d6ad7b9d50b3d496836d7342cf3aec75ac4785563e20574ddd2dab1cfb6b5da32508edf7186aa516b0451b221251652ee44353710cbe35928b79fff4293c5e8eff7ab371ce43595e2300305bda0108b911c3ef7d4d15c70d68686fddf28422d5fcbcdb967e84056e696e6a6100002b0001000151800024b4020802c8f816a7a575bdb2f997f682aab2653ba2cb5eddb69b036a30742a33befaf141056e696e6a6100002e0001000151800113002b08010001518068a55650689424c0b569007f4d7bbce2d77380e115f8469a3c6d1d4bd9be1145eeee843332f1d54da134a25f7d259ccfa36a2e833106139ba37bc28651b7717dabfc8c450e889c5d5d6d39d12f1004252fa08692794af4a7f29a94f6611f9b000ba899d90d6a32e91c54e63720811546b251fb265b7f62615391ab330f83a96841f0367347e67522112f63f3efda891ae0f7265ed5b89673f184027cdb9b5e94b16a9b1f99877cc8e078abf246cad1f76a48a34474977dbd89dd3b41f381df89a82e2939aeb06830f656253e4e347cd04ee6dba0c8377e818f919f80a7e6aefa0f8196d04845bc26b498b0115022ff75e363711e55337de505e50df69b840699160467516d15e8235aa4cf00003000010002a30001080100030803010001b11b182a464c3adc6535aa59613bda7a61cac86945c20b773095941194f4b9f516e8bd924b1e50e3fe83918b51e54529d4e5a1e45303df8462241d5e05979979ae5bf9c6c598c08a496e17f3bd3732d5aebe62667b61db1bbe178f27ac99408165a230d6aee78348e6c67789541f845b2ada96667f8dd16ae44f9e260c4a138b3bb1015965ebe609434a06464bd7d29bac47c3017e83c0f89bca1a9e3bdd0813715f3484292df589bc632e27d37efc02837cb85d770d5bd53a36edc99a8294771aa93cf22406f5506c8cf850ed85c1a475dee5c2d3700b3f5631d903524b849995c20cb407ed411f70b428ae3d642716fe239335aa961a752e67fb6dca0bf72900003000010002a30001080101030803010001af7a8deba49d995a792aefc80263e991efdbc86138a931deb2c65d5682eab5d3b03738e3dfdc89d96da64c86c0224d9ce02514d285da3068b19054e5e787b2969058e98e12566c8c808c40c0b769e1db1a24a1bd9b31e303184a31fc7bb56b85bbba8abc02cd5040a444a36d47695969849e16ad856bb58e8fac8855224400319bdab224d83fc0e66aab32ff74bfeaf0f91c454e6850a1295207bbd4cdde8f6ffb08faa9755c2e3284efa01f99393e18786cb132f1e66ebc6517318e1ce8a3b7337ebb54d035ab57d9706ecd9350d4afacd825e43c8668eece89819caf6817af62dc4fbd82f0e33f6647b2b6bda175f14607f59f4635451e6b27df282ef73d8700003000010002a30001080101030803010001acffb409bcc939f831f7a1e5ec88f7a59255ec53040be432027390a4ce896d6f9086f3c5e177fbfe118163aaec7af1462c47945944c4e2c026be5e98bbcded25978272e1e3e079c5094d573f0e83c92f02b32d3513b1550b826929c80dd0f92cac966d17769fd5867b647c3f38029abdc48152eb8f207159ecc5d232c7c1537c79f4b7ac28ff11682f21681bf6d6aba555032bf6f9f036beb2aaa5b3778d6eebfba6bf9ea191be4ab0caea759e2f773a1f9029c73ecb8d5735b9321db085f1b8e2d8038fe2941992548cee0d67dd4547e11dd63af9c9fc1c5466fb684cf009d7197c2cf79e792ab501e6a8a1ca519af2cb9b5f6367e94c0d47502451357be1b500003000010002a30001080100030803010001b6aec4b48567e2925a2d9c4fa4c96e6dddf86215a9bd8dd579c38ccb1199ed1be89946a7f72fc2633909a2792d0eed1b5afb2ee4c78d865a76d6cd9369d999c96af6be0a2274b8f2e9e0a0065bd20257570f08bc14c16f5616426881a83dbce6926e391c138a2ec317efa7349264de2e791c9b7d4a6048ee6eedf27bf1ece398ff0d229f18377cb1f6b98d1228ef217b8146c0c73851b89a6fc37c621ca187e16428a743ffea0072e185ef93e39525cee3ad01e0c94d2e511c8c313322c29ab91631e1856049a36898684c3056e5997473816fb547acb0be6e660bdfa89a5cb28b3669d8625f3f018c7b3b8a4860e774ee8261811ce7f96c461bc162c1a374f300002e00010002a3000113003008000002a30068a66180688ab2004f66007d114bf33e6d20e7588fdfde9a9e2a8ebd5593ce8bc06419e1d1a4afa8766abc1626504ea6243ca5fc9bce55a3f03c0e7eb488409690d84c3beb30f299da007ab69299d0e203c5b44b94328248768089a9b68982650e9ca2d37526307cbd9f06690e58c3c4a1703b1d1193ea0501417944b937b593294e339571eec42a3c700ce075d9c446e5d32bf979396c1c7935f69bd7df2826567fe582a3615d6095368be991b1e5dc39c0af3b0c39e0e353bbcb928e52e886193ac88da0cd8665ea992b642975aa5486f2e6514d0b5086c66ddd58fe8f7a27ecb128211e3ca1bdc4cad91f3cc9b63c526ebaea86075318e33bfc5a53c919e6f01262b24d178eb2cd04b1 This encodes address BC1QYYQ734DCNHHCWYW8YJXSWXG4P7K9NXU0QT84QZ to override.x_domain_cname_wild@dnssec_proof_tests.bitcoin.ninja valid on August 6, 2025. 3d6f766572726964652e785f646f6d61696e5f636e616d655f77696c6440646e737365635f70726f6f665f74657374732e626974636f696e2e6e696e6a61086f7665727269646513785f646f6d61696e5f636e616d655f77696c640475736572105f626974636f696e2d7061796d656e7412646e737365635f70726f6f665f746573747307626974636f696e056e696e6a6100001000010000001e003736424954434f494e3a3f42433d4243315159595137333444434e48484357595738594a58535758473450374b394e58553051543834515a086f7665727269646513785f646f6d61696e5f636e616d655f77696c640475736572105f626974636f696e2d7061796d656e7412646e737365635f70726f6f665f746573747307626974636f696e056e696e6a6100002e00010000001e006100100d070000001e68a5c51b68933b03d0e207626974636f696e056e696e6a61002076be9a243f968dad8a1fff2bce554e231998ca4e943a525a4ceb1d9cda053f7e95c4ca9e3fd5e9bd3af44b2d049c42a4f2f8fd273c9fb068267d6b9d69a2dc07626974636f696e056e696e6a6100003000010002a62900440100030dff753a27b08c3e48a642b210d6fcc444ff9ed4faf9c1241103db4ed3c19a95c3afbb52c0c02eb392ee048cc9e28ac2d272b1053bdc052bc18d5de05d7710196c07626974636f696e056e696e6a6100003000010002a62900440101030df65551925ce6321888e685981823d617fbc10f329bffe4081bf18c2372632a5548010bf62e6556a92722629275e0bd001e3d7837d325a353f6a851c5b965259607626974636f696e056e696e6a6100002e00010002a629006100300d0200093a806898c73468863d1c716c07626974636f696e056e696e6a610002fd1bf18c2ebb5ece5e28ca76bf30650695636c55633bccae8179c2d1ee7b97e78d188e08ffc869a8f67847bf557516ac12465ebea1acc281d6d636fdab612007626974636f696e056e696e6a6100002b000100000cda0024716c0d023f7ad5a303e9c1cd1474b8df2ae56f3f82da8637ca55db4d9a2bb85960ca698e07626974636f696e056e696e6a6100002b000100000cda0024768a0d02ce46a9aff9a06e789c1bdfe250b0ef6ba8d39a53b2a3427c551f5ad375e059b607626974636f696e056e696e6a6100002e000100000cda0099002b080200000e1068a89268688cd4d892dc056e696e6a61004d88897d7d5f5d920ca436e81ee67b1bb22f1a96309693454ab9d0b06434794162cc42846a4b51a40475a5b44e940c04dd1ac2c902a190ca2251ae89184520b0f3f22c12c51403d0a6e1cd95792e8f6f5036cd2d50dbdfa5eba3b2ee70ff78d40dc2eba2cc899af26954a55e5b5d344d478cabd9423418495caee45c550b1144056e696e6a61000030000100000e1000880100030803010001d28cb7e2bb163d5815838bedeca1006dde8551b379cb963c8a2cb42bc360127e3a5cf88ffc851a67414815b875f65d78c39b58d2fb29a1d4e76d50cb6b4a58a11fe2fb7c1b6db7bf7d72f5a1401e381c57fcc76f599cc73f05095d2bd14d9895e4fa1cff21bd760598a734b640102d11bc159c6b2ae73dbfd2741518142584d1056e696e6a61000030000100000e100088010003080301000197edb59d4f181e2761dd8d0465854339afc71fd89e47155981ddd175cdce79477552aeaf7b5a08fc4ac6025555f60582f2060e630edfb35b9c7cc30990fb9c3dc9f2fd036c962f67b94c9670d4ceaacd77973bca82ab7c9615f7e4320dda5b6d74dec673017c6fa448b5542a804e08ac873c509c1945ff734c320491e4b18e6d056e696e6a61000030000100000e1001080101030803010001c71e4c9dc49249a27b3ef42fcb8d56b4c3ac76715c7ad01c41d0d432590d15c3c62cee4b2d29ac35f2d72c9b32a70a0243cbd08aeebc9f6f1e0e63d9e1cdfe133c455a82435c0780b750012c942f7ed5b662eec8d9ae885a58993fa78d7561fedcd11d9e1c171acb02d0025837ba61a3c0a6756427414470c9ca0906b298168b5f4d9640e62e1b75dd06be664104ed32cfe447fa21f37401712c720a0dca4bb1bc20f3fa3103cad336bde20b16f73948e6b80dda0a528db536a958868c3870ecddcfb02dfb3cb4d22e2ad49a4b9f78c90ff6c7e10e301b3fb36fe859a94c30084660665741c14ff60d0535013fcf439840ecad82fc9278e4ace68ba95e708249056e696e6a6100002e000100000e1001190030080100000e1068a89268688cd4d8b402056e696e6a6100646e04cf5f76daa775ff98905ded3d2caad68d3198fc161340d558262c7ba7da28e7538a7f32d5a6485e4448037e8edf55759b7059fdc084f1017f790aa7c0d8f0e4af6c9af04e4afd16ce6052c30da59314c9c98075fd32bb77a81f34bea6190631b9d0a4351a764c14152ea217e6271647bf95b0df4c3d7cc00937bec01b65ad1b5209c976a4843e399f173f196a012c0876bc9afa3457d940d6ad7b9d50b3d496836d7342cf3aec75ac4785563e20574ddd2dab1cfb6b5da32508edf7186aa516b0451b221251652ee44353710cbe35928b79fff4293c5e8eff7ab371ce43595e2300305bda0108b911c3ef7d4d15c70d68686fddf28422d5fcbcdb967e84056e696e6a6100002b0001000151800024b4020802c8f816a7a575bdb2f997f682aab2653ba2cb5eddb69b036a30742a33befaf141056e696e6a6100002e0001000151800113002b08010001518068a404d06892d340b5690081d888ee9bd744185f24bfbaaae70172bb03b6c0a899dcd6801c44b2e3e6acd5fe2192f4f06e5690ace176cb08557f2d5ceef5e9d9eb72f4f639dcf34650eebdef5cb91cd546fbdbd8a529d7ef9bb2168160ae800790d7a7266b531174d8d9be06cad2f1d0f062d9431f7de4beceb02f30ddc97bba44535a703e2d3cc01d2341bb48eb7b25d938f0ed2a7d4c53818e7cb883dc14ffce5899504265869fd3133953c96f48b99ff2055acd53b9f69d2eb8a911bb1f05e2fb8d1d0cc391e1b9ae19fc32b00727a9d8551e1a09319ba94da44cc317bb66e8f372385560cdf8455f858d4afd602307d982d996f729a16c263efa9b8cebe7862b7f9a88ac9fbaf445a600003000010002a30001080100030803010001b6aec4b48567e2925a2d9c4fa4c96e6dddf86215a9bd8dd579c38ccb1199ed1be89946a7f72fc2633909a2792d0eed1b5afb2ee4c78d865a76d6cd9369d999c96af6be0a2274b8f2e9e0a0065bd20257570f08bc14c16f5616426881a83dbce6926e391c138a2ec317efa7349264de2e791c9b7d4a6048ee6eedf27bf1ece398ff0d229f18377cb1f6b98d1228ef217b8146c0c73851b89a6fc37c621ca187e16428a743ffea0072e185ef93e39525cee3ad01e0c94d2e511c8c313322c29ab91631e1856049a36898684c3056e5997473816fb547acb0be6e660bdfa89a5cb28b3669d8625f3f018c7b3b8a4860e774ee8261811ce7f96c461bc162c1a374f300003000010002a30001080101030803010001af7a8deba49d995a792aefc80263e991efdbc86138a931deb2c65d5682eab5d3b03738e3dfdc89d96da64c86c0224d9ce02514d285da3068b19054e5e787b2969058e98e12566c8c808c40c0b769e1db1a24a1bd9b31e303184a31fc7bb56b85bbba8abc02cd5040a444a36d47695969849e16ad856bb58e8fac8855224400319bdab224d83fc0e66aab32ff74bfeaf0f91c454e6850a1295207bbd4cdde8f6ffb08faa9755c2e3284efa01f99393e18786cb132f1e66ebc6517318e1ce8a3b7337ebb54d035ab57d9706ecd9350d4afacd825e43c8668eece89819caf6817af62dc4fbd82f0e33f6647b2b6bda175f14607f59f4635451e6b27df282ef73d8700003000010002a30001080100030803010001b11b182a464c3adc6535aa59613bda7a61cac86945c20b773095941194f4b9f516e8bd924b1e50e3fe83918b51e54529d4e5a1e45303df8462241d5e05979979ae5bf9c6c598c08a496e17f3bd3732d5aebe62667b61db1bbe178f27ac99408165a230d6aee78348e6c67789541f845b2ada96667f8dd16ae44f9e260c4a138b3bb1015965ebe609434a06464bd7d29bac47c3017e83c0f89bca1a9e3bdd0813715f3484292df589bc632e27d37efc02837cb85d770d5bd53a36edc99a8294771aa93cf22406f5506c8cf850ed85c1a475dee5c2d3700b3f5631d903524b849995c20cb407ed411f70b428ae3d642716fe239335aa961a752e67fb6dca0bf72900003000010002a30001080101030803010001acffb409bcc939f831f7a1e5ec88f7a59255ec53040be432027390a4ce896d6f9086f3c5e177fbfe118163aaec7af1462c47945944c4e2c026be5e98bbcded25978272e1e3e079c5094d573f0e83c92f02b32d3513b1550b826929c80dd0f92cac966d17769fd5867b647c3f38029abdc48152eb8f207159ecc5d232c7c1537c79f4b7ac28ff11682f21681bf6d6aba555032bf6f9f036beb2aaa5b3778d6eebfba6bf9ea191be4ab0caea759e2f773a1f9029c73ecb8d5735b9321db085f1b8e2d8038fe2941992548cee0d67dd4547e11dd63af9c9fc1c5466fb684cf009d7197c2cf79e792ab501e6a8a1ca519af2cb9b5f6367e94c0d47502451357be1b500002e00010002a3000113003008000002a30068a66180688ab2004f66007d114bf33e6d20e7588fdfde9a9e2a8ebd5593ce8bc06419e1d1a4afa8766abc1626504ea6243ca5fc9bce55a3f03c0e7eb488409690d84c3beb30f299da007ab69299d0e203c5b44b94328248768089a9b68982650e9ca2d37526307cbd9f06690e58c3c4a1703b1d1193ea0501417944b937b593294e339571eec42a3c700ce075d9c446e5d32bf979396c1c7935f69bd7df2826567fe582a3615d6095368be991b1e5dc39c0af3b0c39e0e353bbcb928e52e886193ac88da0cd8665ea992b642975aa5486f2e6514d0b5086c66ddd58fe8f7a27ecb128211e3ca1bdc4cad91f3cc9b63c526ebaea86075318e33bfc5a53c919e6f01262b24d178eb2cd04b1 The following encodes both the on-chain address bc1qztwy6xen3zdtt7z0vrgapmjtfz8acjkfp5fp7l and the BOLT 12 offer lno1zr5qyugqgskrk70kqmuq7v3dnr2fnmhukps9n8hut48vkqpqnskt2svsqwjakp7k6pyhtkuxw7y2kqmsxlwruhzqv0zsnhh9q3t9xhx39suc6qsr07ekm5esdyum0w66mnx8vdquwvp7dp5jp7j3v5cp6aj0w329fnkqqv60q96sz5nkrc5r95qffx002q53tqdk8x9m2tmt85jtpmcycvfnrpx3lr45h2g7na3sec7xguctfzzcm8jjqtj5ya27te60j03vpt0vq9tm2n9yxl2hngfnmygesa25s4u4zlxewqpvp94xt7rur4rhxunwkthk9vly3lm5hh0pqv4aymcqejlgssnlpzwlggykkajp7yjs5jvr2agkyypcdlj280cy46jpynsezrcj2kwa2lyr8xvd6lfkph4xrxtk2xc3lpq to a.x_domain_cname_wild@dnssec_proof_tests.bitcoin.ninja valid on August 6, 2025. Note that it requires following a CNAME to a different domain. 36612e785f646f6d61696e5f636e616d655f77696c6440646e737365635f70726f6f665f74657374732e626974636f696e2e6e696e6a61056e696e6a6100002b0001000151800024b4020802c8f816a7a575bdb2f997f682aab2653ba2cb5eddb69b036a30742a33befaf14107626974636f696e056e696e6a6100003000010002a54400440100030dff753a27b08c3e48a642b210d6fcc444ff9ed4faf9c1241103db4ed3c19a95c3afbb52c0c02eb392ee048cc9e28ac2d272b1053bdc052bc18d5de05d7710196c056e696e6a6100002e000100000d2b01190030080100000e1068a89268688cd4d8b402056e696e6a6100646e04cf5f76daa775ff98905ded3d2caad68d3198fc161340d558262c7ba7da28e7538a7f32d5a6485e4448037e8edf55759b7059fdc084f1017f790aa7c0d8f0e4af6c9af04e4afd16ce6052c30da59314c9c98075fd32bb77a81f34bea6190631b9d0a4351a764c14152ea217e6271647bf95b0df4c3d7cc00937bec01b65ad1b5209c976a4843e399f173f196a012c0876bc9afa3457d940d6ad7b9d50b3d496836d7342cf3aec75ac4785563e20574ddd2dab1cfb6b5da32508edf7186aa516b0451b221251652ee44353710cbe35928b79fff4293c5e8eff7ab371ce43595e2300305bda0108b911c3ef7d4d15c70d68686fddf28422d5fcbcdb967e84056e696e6a6100002e0001000151800113002b08010001518068a404d06892d340b5690081d888ee9bd744185f24bfbaaae70172bb03b6c0a899dcd6801c44b2e3e6acd5fe2192f4f06e5690ace176cb08557f2d5ceef5e9d9eb72f4f639dcf34650eebdef5cb91cd546fbdbd8a529d7ef9bb2168160ae800790d7a7266b531174d8d9be06cad2f1d0f062d9431f7de4beceb02f30ddc97bba44535a703e2d3cc01d2341bb48eb7b25d938f0ed2a7d4c53818e7cb883dc14ffce5899504265869fd3133953c96f48b99ff2055acd53b9f69d2eb8a911bb1f05e2fb8d1d0cc391e1b9ae19fc32b00727a9d8551e1a09319ba94da44cc317bb66e8f372385560cdf8455f858d4afd602307d982d996f729a16c263efa9b8cebe7862b7f9a88ac9fbaf445a6056e696e6a61000030000100000d2b00880100030803010001d28cb7e2bb163d5815838bedeca1006dde8551b379cb963c8a2cb42bc360127e3a5cf88ffc851a67414815b875f65d78c39b58d2fb29a1d4e76d50cb6b4a58a11fe2fb7c1b6db7bf7d72f5a1401e381c57fcc76f599cc73f05095d2bd14d9895e4fa1cff21bd760598a734b640102d11bc159c6b2ae73dbfd2741518142584d107626974636f696e056e696e6a6100002b000100000bf50024716c0d023f7ad5a303e9c1cd1474b8df2ae56f3f82da8637ca55db4d9a2bb85960ca698e00003000010002a30001080100030803010001b11b182a464c3adc6535aa59613bda7a61cac86945c20b773095941194f4b9f516e8bd924b1e50e3fe83918b51e54529d4e5a1e45303df8462241d5e05979979ae5bf9c6c598c08a496e17f3bd3732d5aebe62667b61db1bbe178f27ac99408165a230d6aee78348e6c67789541f845b2ada96667f8dd16ae44f9e260c4a138b3bb1015965ebe609434a06464bd7d29bac47c3017e83c0f89bca1a9e3bdd0813715f3484292df589bc632e27d37efc02837cb85d770d5bd53a36edc99a8294771aa93cf22406f5506c8cf850ed85c1a475dee5c2d3700b3f5631d903524b849995c20cb407ed411f70b428ae3d642716fe239335aa961a752e67fb6dca0bf7290b6d617474636f72616c6c6f03636f6d00003000010003d52200440101030dec7c1fa1752495c42d2224eace96ed74144e9cb811608dd91594974bdc723fdc5b38a37c3340f1deca68a7ec82248822954b2994de5ac99ff6e9db95fd42c94b00003000010002a30001080101030803010001acffb409bcc939f831f7a1e5ec88f7a59255ec53040be432027390a4ce896d6f9086f3c5e177fbfe118163aaec7af1462c47945944c4e2c026be5e98bbcded25978272e1e3e079c5094d573f0e83c92f02b32d3513b1550b826929c80dd0f92cac966d17769fd5867b647c3f38029abdc48152eb8f207159ecc5d232c7c1537c79f4b7ac28ff11682f21681bf6d6aba555032bf6f9f036beb2aaa5b3778d6eebfba6bf9ea191be4ab0caea759e2f773a1f9029c73ecb8d5735b9321db085f1b8e2d8038fe2941992548cee0d67dd4547e11dd63af9c9fc1c5466fb684cf009d7197c2cf79e792ab501e6a8a1ca519af2cb9b5f6367e94c0d47502451357be1b507626974636f696e056e696e6a6100002e000100000bf50099002b080200000e1068a89268688cd4d892dc056e696e6a61004d88897d7d5f5d920ca436e81ee67b1bb22f1a96309693454ab9d0b06434794162cc42846a4b51a40475a5b44e940c04dd1ac2c902a190ca2251ae89184520b0f3f22c12c51403d0a6e1cd95792e8f6f5036cd2d50dbdfa5eba3b2ee70ff78d40dc2eba2cc899af26954a55e5b5d344d478cabd9423418495caee45c550b114403636f6d00002e000100000266005700300d0100015180689f3dfb688b764f4d0603636f6d00d87373f3d5d404f7cdc3aace633c96357bc606ced620792597e1308b1d6c5902668c4d3c1a37bab8486ba24485d57a9d98157fe706424b2043bfb40306d01484046d6174740475736572105f626974636f696e2d7061796d656e740b6d617474636f72616c6c6f03636f6d00002e000100000e10006300100d0500000e1068a57e5a6892f44226480b6d617474636f72616c6c6f03636f6d004515e7d3cdf4137c316d4d36972fab9273df457789a9fabb16c4689e1644ae9080c7505e06daebc136d3c43054d0c69d185ac5616afca8998edf828e63a68286206f3266653035326d646a61336638746c3563353667706668646661696661687007626974636f696e056e696e6a6100003200010000001e002201000000083c92990db9cddbc614c8e4a40e1317cc888750fad000dab671a24e1a3a056e696e6a61000030000100000d2b01080101030803010001c71e4c9dc49249a27b3ef42fcb8d56b4c3ac76715c7ad01c41d0d432590d15c3c62cee4b2d29ac35f2d72c9b32a70a0243cbd08aeebc9f6f1e0e63d9e1cdfe133c455a82435c0780b750012c942f7ed5b662eec8d9ae885a58993fa78d7561fedcd11d9e1c171acb02d0025837ba61a3c0a6756427414470c9ca0906b298168b5f4d9640e62e1b75dd06be664104ed32cfe447fa21f37401712c720a0dca4bb1bc20f3fa3103cad336bde20b16f73948e6b80dda0a528db536a958868c3870ecddcfb02dfb3cb4d22e2ad49a4b9f78c90ff6c7e10e301b3fb36fe859a94c30084660665741c14ff60d0535013fcf439840ecad82fc9278e4ace68ba95e7082490b6d617474636f72616c6c6f03636f6d00002b0001000151800024e2f50d02f0e161567d468087ff27b051abc94476178a7cb635da1aa705e05c77ca81de520b6d617474636f72616c6c6f03636f6d00002e0001000151800057002b0d0200015180689a991368914e2b504103636f6d0070ac13ac37043e66f191553c554ee9307a91a4cf27bd724949e52032a2b464cadb776cd362918159344d9685b84650436449914f25fc62cc6dd6b761f565828303636f6d00002b00010001518000244d060d028acbb0cd28f41250a80a491389424d341522d946b0da0c0291f2d3d771d7805a0b6d617474636f72616c6c6f03636f6d00002e00010003d522006300300d0200093a80689c35ca6889abb2e2f50b6d617474636f72616c6c6f03636f6d0016857529219dd561091a51c72a27e25d963094f8dcd93b11f0917d45466251acb1402bb6fa4529bd20b7db697df429c4ba830685fc290ee5a8a937c2d34530c007626974636f696e056e696e6a6100003000010002a54400440101030df65551925ce6321888e685981823d617fbc10f329bffe4081bf18c2372632a5548010bf62e6556a92722629275e0bd001e3d7837d325a353f6a851c5b9652596016113785f646f6d61696e5f636e616d655f77696c640475736572105f626974636f696e2d7061796d656e7412646e737365635f70726f6f665f746573747307626974636f696e056e696e6a6100002e00010000001e006100050d060000001e68a4c58868923b70d0e207626974636f696e056e696e6a6100849202c2306be651b9a5901331d9bf363e74ba758c16e993c4f93fe4c1a08e7bc46baa64b22e9540435b4b6b83fc4800c58d27bd9b2fe82d02ed6d6f9059cfa50b6d617474636f72616c6c6f03636f6d00003000010003d52200440100030dfd9dbc34cb5053a2c4a6b3d0dc60fc65d8a992dc1e080f6deeddba7fe6b25217730de64c9a1ce986b3f81f556881fe0e7b5b20c8ae381c4fefdbc311aa7d22ee206f3266653035326d646a61336638746c3563353667706668646661696661687007626974636f696e056e696e6a6100002e00010000001e006100320d030000003c68a5076a68927d52d0e207626974636f696e056e696e6a6100620532890060f3f82a90a05ab32afe628ef58a58fbed98df2fbb1d3d00064b05111503f67cbd0f485f6196f007ddb3e6ec087e31f94221bf2b388179d31373b203636f6d00003000010000026600440101030db71f0465101ddbe2bf0c9455d12fa16c1cda44f4bf1ba2553418ad1f3aa9b06973f21b84eb532cf4035ee8d4832ca26d89306a7d32560c0cb0129d450ac10835016113785f646f6d61696e5f636e616d655f77696c640475736572105f626974636f696e2d7061796d656e7412646e737365635f70726f6f665f746573747307626974636f696e056e696e6a6100000500010000001e002c046d6174740475736572105f626974636f696e2d7061796d656e740b6d617474636f72616c6c6f03636f6d0007626974636f696e056e696e6a6100002b000100000bf50024768a0d02ce46a9aff9a06e789c1bdfe250b0ef6ba8d39a53b2a3427c551f5ad375e059b60b6d617474636f72616c6c6f03636f6d00003000010003d52200440100030d8b1cf07c86f18c19c8c3146db093893648dcc1ab5fb79e99ccbab4aa06f98d52ac27b92e215d9da98d7535f3c2ce038fbb9d41b9c63d3845d444feffc1f71ed703636f6d00002e0001000151800113002b08010001518068a404d06892d340b5690024fbea2f86eb0e472114b9da41f1da69e4ef2d02ffcd6bdd987239f288795603d5f54308b238ef19f2747d6a1bc0e775782025561b0f14d1dd19be6bf36b495a3e2d538d5532c5c6e1056c06aa4e81de07f637313955a7761d313db0c6cd0b5c17b4ee22d530d6cdc0c4e195df85b354bbe32027537f1ca21f2815b2d0dbd154582124b3c4c27f1c3aea16f6bfe7e6f5c80aaccd61601bdd8f947ef5c30f004482617cf97629b8b89d8e7320719c979c6a9defdf79b743ecef08bdf2f90796da018fdc6be1e0629fe706044e0f8ad1b25927eca09074a502eb9136eefe5903ad3f97866ab014f1ec96e1f38e3aba66520a25ace386f4897e1ecfd774ce0a0f8a03636f6d00003000010000026600440100030df17b60fb56d522f8634153e785c0a978532ea76de39d34bb356d3d042e07f29f7b992176cc83acef7b78ea750425203b18f2b8228b3cdd2bc7eb13c3e3035a7e0b6d617474636f72616c6c6f03636f6d00002b00010001518000249f000d02594d2813e04a1d2660ff3c0afc5579b9ec0fe72cc206dc6f248bbe6dd652e19500002e00010002a3000113003008000002a30068a66180688ab2004f66007d114bf33e6d20e7588fdfde9a9e2a8ebd5593ce8bc06419e1d1a4afa8766abc1626504ea6243ca5fc9bce55a3f03c0e7eb488409690d84c3beb30f299da007ab69299d0e203c5b44b94328248768089a9b68982650e9ca2d37526307cbd9f06690e58c3c4a1703b1d1193ea0501417944b937b593294e339571eec42a3c700ce075d9c446e5d32bf979396c1c7935f69bd7df2826567fe582a3615d6095368be991b1e5dc39c0af3b0c39e0e353bbcb928e52e886193ac88da0cd8665ea992b642975aa5486f2e6514d0b5086c66ddd58fe8f7a27ecb128211e3ca1bdc4cad91f3cc9b63c526ebaea86075318e33bfc5a53c919e6f01262b24d178eb2cd04b100003000010002a30001080100030803010001b6aec4b48567e2925a2d9c4fa4c96e6dddf86215a9bd8dd579c38ccb1199ed1be89946a7f72fc2633909a2792d0eed1b5afb2ee4c78d865a76d6cd9369d999c96af6be0a2274b8f2e9e0a0065bd20257570f08bc14c16f5616426881a83dbce6926e391c138a2ec317efa7349264de2e791c9b7d4a6048ee6eedf27bf1ece398ff0d229f18377cb1f6b98d1228ef217b8146c0c73851b89a6fc37c621ca187e16428a743ffea0072e185ef93e39525cee3ad01e0c94d2e511c8c313322c29ab91631e1856049a36898684c3056e5997473816fb547acb0be6e660bdfa89a5cb28b3669d8625f3f018c7b3b8a4860e774ee8261811ce7f96c461bc162c1a374f3046d6174740475736572105f626974636f696e2d7061796d656e740b6d617474636f72616c6c6f03636f6d000010000100000e1001ecff626974636f696e3a626331717a7477793678656e337a647474377a3076726761706d6a74667a3861636a6b6670356670376c3f6c6e6f3d6c6e6f317a7235717975677167736b726b37306b716d7571377633646e7232666e6d68756b7073396e386875743438766b7170716e736b743273767371776a616b70376b36707968746b7578773779326b716d73786c777275687a7176307a736e686839713374397868783339737563367173723037656b6d3565736479756d307736366d6e783876647175777670376470356a70376a337635637036616a3077333239666e6b7171763630713936737a356e6b726335723935716666783030327135337471646beb3878396d32746d7438356a74706d63796376666e727078336c723435683267376e6133736563377867756374667a7a636d386a6a71746a3579613237746536306a303376707430767139746d326e3979786c32686e67666e6d79676573613235733475347a6c78657771707670393478743772757234726878756e776b74686b39766c79336c6d356868307071763461796d6371656a6c6773736e6c707a776c6767796b6b616a7037796a73356a76723261676b79797063646c6a323830637934366a70796e73657a72636a326b7761326c797238787664366c666b706834787278746b327863336c707100003000010002a30001080101030803010001af7a8deba49d995a792aefc80263e991efdbc86138a931deb2c65d5682eab5d3b03738e3dfdc89d96da64c86c0224d9ce02514d285da3068b19054e5e787b2969058e98e12566c8c808c40c0b769e1db1a24a1bd9b31e303184a31fc7bb56b85bbba8abc02cd5040a444a36d47695969849e16ad856bb58e8fac8855224400319bdab224d83fc0e66aab32ff74bfeaf0f91c454e6850a1295207bbd4cdde8f6ffb08faa9755c2e3284efa01f99393e18786cb132f1e66ebc6517318e1ce8a3b7337ebb54d035ab57d9706ecd9350d4afacd825e43c8668eece89819caf6817af62dc4fbd82f0e33f6647b2b6bda175f14607f59f4635451e6b27df282ef73d8707626974636f696e056e696e6a6100002e00010002a544006100300d0200093a806898c73468863d1c716c07626974636f696e056e696e6a610002fd1bf18c2ebb5ece5e28ca76bf30650695636c55633bccae8179c2d1ee7b97e78d188e08ffc869a8f67847bf557516ac12465ebea1acc281d6d636fdab6120056e696e6a61000030000100000d2b0088010003080301000197edb59d4f181e2761dd8d0465854339afc71fd89e47155981ddd175cdce79477552aeaf7b5a08fc4ac6025555f60582f2060e630edfb35b9c7cc30990fb9c3dc9f2fd036c962f67b94c9670d4ceaacd77973bca82ab7c9615f7e4320dda5b6d74dec673017c6fa448b5542a804e08ac873c509c1945ff734c320491e4b18e6d The following is an *invalid* DNSSEC proof when included in the PSBT_OUT_DNSSEC_PROOF record of a PSBT. The following encodes the on-chain address bc1qztwy6xen3zdtt7z0vrgapmjtfz8acjkfp5fp7l to invalid@dnssec_proof_tests.bitcoin.ninja but is '''invalid'''. This proof contains two TXT records which start with, case insensitively, "bitcoin:". It is a valid DNSSEC proof but should fail BIP 353-specific validation. 28696e76616c696440646e737365635f70726f6f665f74657374732e626974636f696e2e6e696e6a6107696e76616c69640475736572105f626974636f696e2d7061796d656e7412646e737365635f70726f6f665f746573747307626974636f696e056e696e6a6100001000010000001e003736426954634f694e3a3f42433d626331717a7477793678656e337a647474377a3076726761706d6a74667a3861636a6b6670356670376c07696e76616c69640475736572105f626974636f696e2d7061796d656e7412646e737365635f70726f6f665f746573747307626974636f696e056e696e6a6100001000010000001e003736626974636f696e3a3f62633d626331717a7477793678656e337a647474377a3076726761706d6a74667a3861636a6b6670356670376c07696e76616c69640475736572105f626974636f696e2d7061796d656e7412646e737365635f70726f6f665f746573747307626974636f696e056e696e6a6100002e00010000001e006100100d060000001e68a70b256894810dd0e207626974636f696e056e696e6a6100a7ed29b28f64a885e6496f080befc724da98afe8879a985c1f82b15dc6f97cf595b8a3b62edc58870291448a7f4017fba8c3e8380ab32a0883439fba965773ac07626974636f696e056e696e6a610000300001000161f300440100030dff753a27b08c3e48a642b210d6fcc444ff9ed4faf9c1241103db4ed3c19a95c3afbb52c0c02eb392ee048cc9e28ac2d272b1053bdc052bc18d5de05d7710196c07626974636f696e056e696e6a610000300001000161f300440101030df65551925ce6321888e685981823d617fbc10f329bffe4081bf18c2372632a5548010bf62e6556a92722629275e0bd001e3d7837d325a353f6a851c5b965259607626974636f696e056e696e6a6100002e0001000161f3006100300d0200093a806898c73468863d1c716c07626974636f696e056e696e6a610002fd1bf18c2ebb5ece5e28ca76bf30650695636c55633bccae8179c2d1ee7b97e78d188e08ffc869a8f67847bf557516ac12465ebea1acc281d6d636fdab612007626974636f696e056e696e6a6100002b000100000daa0024716c0d023f7ad5a303e9c1cd1474b8df2ae56f3f82da8637ca55db4d9a2bb85960ca698e07626974636f696e056e696e6a6100002b000100000daa0024768a0d02ce46a9aff9a06e789c1bdfe250b0ef6ba8d39a53b2a3427c551f5ad375e059b607626974636f696e056e696e6a6100002e000100000daa0099002b080200000e1068a89268688cd4d892dc056e696e6a61004d88897d7d5f5d920ca436e81ee67b1bb22f1a96309693454ab9d0b06434794162cc42846a4b51a40475a5b44e940c04dd1ac2c902a190ca2251ae89184520b0f3f22c12c51403d0a6e1cd95792e8f6f5036cd2d50dbdfa5eba3b2ee70ff78d40dc2eba2cc899af26954a55e5b5d344d478cabd9423418495caee45c550b1144056e696e6a61000030000100000daa01080101030803010001c71e4c9dc49249a27b3ef42fcb8d56b4c3ac76715c7ad01c41d0d432590d15c3c62cee4b2d29ac35f2d72c9b32a70a0243cbd08aeebc9f6f1e0e63d9e1cdfe133c455a82435c0780b750012c942f7ed5b662eec8d9ae885a58993fa78d7561fedcd11d9e1c171acb02d0025837ba61a3c0a6756427414470c9ca0906b298168b5f4d9640e62e1b75dd06be664104ed32cfe447fa21f37401712c720a0dca4bb1bc20f3fa3103cad336bde20b16f73948e6b80dda0a528db536a958868c3870ecddcfb02dfb3cb4d22e2ad49a4b9f78c90ff6c7e10e301b3fb36fe859a94c30084660665741c14ff60d0535013fcf439840ecad82fc9278e4ace68ba95e708249056e696e6a61000030000100000daa0088010003080301000197edb59d4f181e2761dd8d0465854339afc71fd89e47155981ddd175cdce79477552aeaf7b5a08fc4ac6025555f60582f2060e630edfb35b9c7cc30990fb9c3dc9f2fd036c962f67b94c9670d4ceaacd77973bca82ab7c9615f7e4320dda5b6d74dec673017c6fa448b5542a804e08ac873c509c1945ff734c320491e4b18e6d056e696e6a61000030000100000daa00880100030803010001d28cb7e2bb163d5815838bedeca1006dde8551b379cb963c8a2cb42bc360127e3a5cf88ffc851a67414815b875f65d78c39b58d2fb29a1d4e76d50cb6b4a58a11fe2fb7c1b6db7bf7d72f5a1401e381c57fcc76f599cc73f05095d2bd14d9895e4fa1cff21bd760598a734b640102d11bc159c6b2ae73dbfd2741518142584d1056e696e6a6100002e000100000daa01190030080100000e1068a89268688cd4d8b402056e696e6a6100646e04cf5f76daa775ff98905ded3d2caad68d3198fc161340d558262c7ba7da28e7538a7f32d5a6485e4448037e8edf55759b7059fdc084f1017f790aa7c0d8f0e4af6c9af04e4afd16ce6052c30da59314c9c98075fd32bb77a81f34bea6190631b9d0a4351a764c14152ea217e6271647bf95b0df4c3d7cc00937bec01b65ad1b5209c976a4843e399f173f196a012c0876bc9afa3457d940d6ad7b9d50b3d496836d7342cf3aec75ac4785563e20574ddd2dab1cfb6b5da32508edf7186aa516b0451b221251652ee44353710cbe35928b79fff4293c5e8eff7ab371ce43595e2300305bda0108b911c3ef7d4d15c70d68686fddf28422d5fcbcdb967e84056e696e6a6100002b0001000151800024b4020802c8f816a7a575bdb2f997f682aab2653ba2cb5eddb69b036a30742a33befaf141056e696e6a6100002e0001000151800113002b08010001518068a55650689424c0b569007f4d7bbce2d77380e115f8469a3c6d1d4bd9be1145eeee843332f1d54da134a25f7d259ccfa36a2e833106139ba37bc28651b7717dabfc8c450e889c5d5d6d39d12f1004252fa08692794af4a7f29a94f6611f9b000ba899d90d6a32e91c54e63720811546b251fb265b7f62615391ab330f83a96841f0367347e67522112f63f3efda891ae0f7265ed5b89673f184027cdb9b5e94b16a9b1f99877cc8e078abf246cad1f76a48a34474977dbd89dd3b41f381df89a82e2939aeb06830f656253e4e347cd04ee6dba0c8377e818f919f80a7e6aefa0f8196d04845bc26b498b0115022ff75e363711e55337de505e50df69b840699160467516d15e8235aa4cf00003000010002a30001080101030803010001acffb409bcc939f831f7a1e5ec88f7a59255ec53040be432027390a4ce896d6f9086f3c5e177fbfe118163aaec7af1462c47945944c4e2c026be5e98bbcded25978272e1e3e079c5094d573f0e83c92f02b32d3513b1550b826929c80dd0f92cac966d17769fd5867b647c3f38029abdc48152eb8f207159ecc5d232c7c1537c79f4b7ac28ff11682f21681bf6d6aba555032bf6f9f036beb2aaa5b3778d6eebfba6bf9ea191be4ab0caea759e2f773a1f9029c73ecb8d5735b9321db085f1b8e2d8038fe2941992548cee0d67dd4547e11dd63af9c9fc1c5466fb684cf009d7197c2cf79e792ab501e6a8a1ca519af2cb9b5f6367e94c0d47502451357be1b500003000010002a30001080100030803010001b6aec4b48567e2925a2d9c4fa4c96e6dddf86215a9bd8dd579c38ccb1199ed1be89946a7f72fc2633909a2792d0eed1b5afb2ee4c78d865a76d6cd9369d999c96af6be0a2274b8f2e9e0a0065bd20257570f08bc14c16f5616426881a83dbce6926e391c138a2ec317efa7349264de2e791c9b7d4a6048ee6eedf27bf1ece398ff0d229f18377cb1f6b98d1228ef217b8146c0c73851b89a6fc37c621ca187e16428a743ffea0072e185ef93e39525cee3ad01e0c94d2e511c8c313322c29ab91631e1856049a36898684c3056e5997473816fb547acb0be6e660bdfa89a5cb28b3669d8625f3f018c7b3b8a4860e774ee8261811ce7f96c461bc162c1a374f300003000010002a30001080100030803010001b11b182a464c3adc6535aa59613bda7a61cac86945c20b773095941194f4b9f516e8bd924b1e50e3fe83918b51e54529d4e5a1e45303df8462241d5e05979979ae5bf9c6c598c08a496e17f3bd3732d5aebe62667b61db1bbe178f27ac99408165a230d6aee78348e6c67789541f845b2ada96667f8dd16ae44f9e260c4a138b3bb1015965ebe609434a06464bd7d29bac47c3017e83c0f89bca1a9e3bdd0813715f3484292df589bc632e27d37efc02837cb85d770d5bd53a36edc99a8294771aa93cf22406f5506c8cf850ed85c1a475dee5c2d3700b3f5631d903524b849995c20cb407ed411f70b428ae3d642716fe239335aa961a752e67fb6dca0bf72900003000010002a30001080101030803010001af7a8deba49d995a792aefc80263e991efdbc86138a931deb2c65d5682eab5d3b03738e3dfdc89d96da64c86c0224d9ce02514d285da3068b19054e5e787b2969058e98e12566c8c808c40c0b769e1db1a24a1bd9b31e303184a31fc7bb56b85bbba8abc02cd5040a444a36d47695969849e16ad856bb58e8fac8855224400319bdab224d83fc0e66aab32ff74bfeaf0f91c454e6850a1295207bbd4cdde8f6ffb08faa9755c2e3284efa01f99393e18786cb132f1e66ebc6517318e1ce8a3b7337ebb54d035ab57d9706ecd9350d4afacd825e43c8668eece89819caf6817af62dc4fbd82f0e33f6647b2b6bda175f14607f59f4635451e6b27df282ef73d8700002e00010002a3000113003008000002a30068a66180688ab2004f66007d114bf33e6d20e7588fdfde9a9e2a8ebd5593ce8bc06419e1d1a4afa8766abc1626504ea6243ca5fc9bce55a3f03c0e7eb488409690d84c3beb30f299da007ab69299d0e203c5b44b94328248768089a9b68982650e9ca2d37526307cbd9f06690e58c3c4a1703b1d1193ea0501417944b937b593294e339571eec42a3c700ce075d9c446e5d32bf979396c1c7935f69bd7df2826567fe582a3615d6095368be991b1e5dc39c0af3b0c39e0e353bbcb928e52e886193ac88da0cd8665ea992b642975aa5486f2e6514d0b5086c66ddd58fe8f7a27ecb128211e3ca1bdc4cad91f3cc9b63c526ebaea86075318e33bfc5a53c919e6f01262b24d178eb2cd04b1 The following encodes both the on-chain address bc1qztwy6xen3zdtt7z0vrgapmjtfz8acjkfp5fp7l and the BOLT 12 offer lno1zr5qyugqgskrk70kqmuq7v3dnr2fnmhukps9n8hut48vkqpqnskt2svsqwjakp7k6pyhtkuxw7y2kqmsxlwruhzqv0zsnhh9q3t9xhx39suc6qsr07ekm5esdyum0w66mnx8vdquwvp7dp5jp7j3v5cp6aj0w329fnkqqv60q96sz5nkrc5r95qffx002q53tqdk8x9m2tmt85jtpmcycvfnrpx3lr45h2g7na3sec7xguctfzzcm8jjqtj5ya27te60j03vpt0vq9tm2n9yxl2hngfnmygesa25s4u4zlxewqpvp94xt7rur4rhxunwkthk9vly3lm5hh0pqv4aymcqejlgssnlpzwlggykkajp7yjs5jvr2agkyypcdlj280cy46jpynsezrcj2kwa2lyr8xvd6lfkph4xrxtk2xc3lpq to a.x_domain_cname_wild@dnssec_proof_tests.bitcoin.ninja but is '''invalid'''. This proof is missing the required NSEC3 record to prove the lack of an override to the wildcard CNAME entry. 36612e785f646f6d61696e5f636e616d655f77696c6440646e737365635f70726f6f665f74657374732e626974636f696e2e6e696e6a61016113785f646f6d61696e5f636e616d655f77696c640475736572105f626974636f696e2d7061796d656e7412646e737365635f70726f6f665f746573747307626974636f696e056e696e6a6100000500010000001e002c046d6174740475736572105f626974636f696e2d7061796d656e740b6d617474636f72616c6c6f03636f6d00016113785f646f6d61696e5f636e616d655f77696c640475736572105f626974636f696e2d7061796d656e7412646e737365635f70726f6f665f746573747307626974636f696e056e696e6a6100002e00010000001e006100050d060000001e68a4c58868923b70d0e207626974636f696e056e696e6a6100849202c2306be651b9a5901331d9bf363e74ba758c16e993c4f93fe4c1a08e7bc46baa64b22e9540435b4b6b83fc4800c58d27bd9b2fe82d02ed6d6f9059cfa5046d6174740475736572105f626974636f696e2d7061796d656e740b6d617474636f72616c6c6f03636f6d000010000100000e1001ecff626974636f696e3a626331717a7477793678656e337a647474377a3076726761706d6a74667a3861636a6b6670356670376c3f6c6e6f3d6c6e6f317a7235717975677167736b726b37306b716d7571377633646e7232666e6d68756b7073396e386875743438766b7170716e736b743273767371776a616b70376b36707968746b7578773779326b716d73786c777275687a7176307a736e686839713374397868783339737563367173723037656b6d3565736479756d307736366d6e783876647175777670376470356a70376a337635637036616a3077333239666e6b7171763630713936737a356e6b726335723935716666783030327135337471646beb3878396d32746d7438356a74706d63796376666e727078336c723435683267376e6133736563377867756374667a7a636d386a6a71746a3579613237746536306a303376707430767139746d326e3979786c32686e67666e6d79676573613235733475347a6c78657771707670393478743772757234726878756e776b74686b39766c79336c6d356868307071763461796d6371656a6c6773736e6c707a776c6767796b6b616a7037796a73356a76723261676b79797063646c6a323830637934366a70796e73657a72636a326b7761326c797238787664366c666b706834787278746b327863336c7071046d6174740475736572105f626974636f696e2d7061796d656e740b6d617474636f72616c6c6f03636f6d00002e000100000e10006300100d0500000e1068a57e5a6892f44226480b6d617474636f72616c6c6f03636f6d004515e7d3cdf4137c316d4d36972fab9273df457789a9fabb16c4689e1644ae9080c7505e06daebc136d3c43054d0c69d185ac5616afca8998edf828e63a68286206f3266653035326d646a61336638746c3563353667706668646661696661687007626974636f696e056e696e6a6100002e00010000001e006100320d030000003c68a5076a68927d52d0e207626974636f696e056e696e6a6100620532890060f3f82a90a05ab32afe628ef58a58fbed98df2fbb1d3d00064b05111503f67cbd0f485f6196f007ddb3e6ec087e31f94221bf2b388179d31373b207626974636f696e056e696e6a6100003000010002a54400440100030dff753a27b08c3e48a642b210d6fcc444ff9ed4faf9c1241103db4ed3c19a95c3afbb52c0c02eb392ee048cc9e28ac2d272b1053bdc052bc18d5de05d7710196c07626974636f696e056e696e6a6100003000010002a54400440101030df65551925ce6321888e685981823d617fbc10f329bffe4081bf18c2372632a5548010bf62e6556a92722629275e0bd001e3d7837d325a353f6a851c5b965259607626974636f696e056e696e6a6100002e00010002a544006100300d0200093a806898c73468863d1c716c07626974636f696e056e696e6a610002fd1bf18c2ebb5ece5e28ca76bf30650695636c55633bccae8179c2d1ee7b97e78d188e08ffc869a8f67847bf557516ac12465ebea1acc281d6d636fdab612007626974636f696e056e696e6a6100002b000100000bf50024768a0d02ce46a9aff9a06e789c1bdfe250b0ef6ba8d39a53b2a3427c551f5ad375e059b607626974636f696e056e696e6a6100002b000100000bf50024716c0d023f7ad5a303e9c1cd1474b8df2ae56f3f82da8637ca55db4d9a2bb85960ca698e07626974636f696e056e696e6a6100002e000100000bf50099002b080200000e1068a89268688cd4d892dc056e696e6a61004d88897d7d5f5d920ca436e81ee67b1bb22f1a96309693454ab9d0b06434794162cc42846a4b51a40475a5b44e940c04dd1ac2c902a190ca2251ae89184520b0f3f22c12c51403d0a6e1cd95792e8f6f5036cd2d50dbdfa5eba3b2ee70ff78d40dc2eba2cc899af26954a55e5b5d344d478cabd9423418495caee45c550b11440b6d617474636f72616c6c6f03636f6d00003000010003d52200440100030d8b1cf07c86f18c19c8c3146db093893648dcc1ab5fb79e99ccbab4aa06f98d52ac27b92e215d9da98d7535f3c2ce038fbb9d41b9c63d3845d444feffc1f71ed70b6d617474636f72616c6c6f03636f6d00003000010003d52200440101030dec7c1fa1752495c42d2224eace96ed74144e9cb811608dd91594974bdc723fdc5b38a37c3340f1deca68a7ec82248822954b2994de5ac99ff6e9db95fd42c94b0b6d617474636f72616c6c6f03636f6d00003000010003d52200440100030dfd9dbc34cb5053a2c4a6b3d0dc60fc65d8a992dc1e080f6deeddba7fe6b25217730de64c9a1ce986b3f81f556881fe0e7b5b20c8ae381c4fefdbc311aa7d22ee0b6d617474636f72616c6c6f03636f6d00002e00010003d522006300300d0200093a80689c35ca6889abb2e2f50b6d617474636f72616c6c6f03636f6d0016857529219dd561091a51c72a27e25d963094f8dcd93b11f0917d45466251acb1402bb6fa4529bd20b7db697df429c4ba830685fc290ee5a8a937c2d34530c00b6d617474636f72616c6c6f03636f6d00002b00010001518000249f000d02594d2813e04a1d2660ff3c0afc5579b9ec0fe72cc206dc6f248bbe6dd652e1950b6d617474636f72616c6c6f03636f6d00002b0001000151800024e2f50d02f0e161567d468087ff27b051abc94476178a7cb635da1aa705e05c77ca81de520b6d617474636f72616c6c6f03636f6d00002e0001000151800057002b0d0200015180689a991368914e2b504103636f6d0070ac13ac37043e66f191553c554ee9307a91a4cf27bd724949e52032a2b464cadb776cd362918159344d9685b84650436449914f25fc62cc6dd6b761f5658283056e696e6a61000030000100000d2b00880100030803010001d28cb7e2bb163d5815838bedeca1006dde8551b379cb963c8a2cb42bc360127e3a5cf88ffc851a67414815b875f65d78c39b58d2fb29a1d4e76d50cb6b4a58a11fe2fb7c1b6db7bf7d72f5a1401e381c57fcc76f599cc73f05095d2bd14d9895e4fa1cff21bd760598a734b640102d11bc159c6b2ae73dbfd2741518142584d1056e696e6a61000030000100000d2b01080101030803010001c71e4c9dc49249a27b3ef42fcb8d56b4c3ac76715c7ad01c41d0d432590d15c3c62cee4b2d29ac35f2d72c9b32a70a0243cbd08aeebc9f6f1e0e63d9e1cdfe133c455a82435c0780b750012c942f7ed5b662eec8d9ae885a58993fa78d7561fedcd11d9e1c171acb02d0025837ba61a3c0a6756427414470c9ca0906b298168b5f4d9640e62e1b75dd06be664104ed32cfe447fa21f37401712c720a0dca4bb1bc20f3fa3103cad336bde20b16f73948e6b80dda0a528db536a958868c3870ecddcfb02dfb3cb4d22e2ad49a4b9f78c90ff6c7e10e301b3fb36fe859a94c30084660665741c14ff60d0535013fcf439840ecad82fc9278e4ace68ba95e708249056e696e6a61000030000100000d2b0088010003080301000197edb59d4f181e2761dd8d0465854339afc71fd89e47155981ddd175cdce79477552aeaf7b5a08fc4ac6025555f60582f2060e630edfb35b9c7cc30990fb9c3dc9f2fd036c962f67b94c9670d4ceaacd77973bca82ab7c9615f7e4320dda5b6d74dec673017c6fa448b5542a804e08ac873c509c1945ff734c320491e4b18e6d056e696e6a6100002e000100000d2b01190030080100000e1068a89268688cd4d8b402056e696e6a6100646e04cf5f76daa775ff98905ded3d2caad68d3198fc161340d558262c7ba7da28e7538a7f32d5a6485e4448037e8edf55759b7059fdc084f1017f790aa7c0d8f0e4af6c9af04e4afd16ce6052c30da59314c9c98075fd32bb77a81f34bea6190631b9d0a4351a764c14152ea217e6271647bf95b0df4c3d7cc00937bec01b65ad1b5209c976a4843e399f173f196a012c0876bc9afa3457d940d6ad7b9d50b3d496836d7342cf3aec75ac4785563e20574ddd2dab1cfb6b5da32508edf7186aa516b0451b221251652ee44353710cbe35928b79fff4293c5e8eff7ab371ce43595e2300305bda0108b911c3ef7d4d15c70d68686fddf28422d5fcbcdb967e84056e696e6a6100002b0001000151800024b4020802c8f816a7a575bdb2f997f682aab2653ba2cb5eddb69b036a30742a33befaf141056e696e6a6100002e0001000151800113002b08010001518068a404d06892d340b5690081d888ee9bd744185f24bfbaaae70172bb03b6c0a899dcd6801c44b2e3e6acd5fe2192f4f06e5690ace176cb08557f2d5ceef5e9d9eb72f4f639dcf34650eebdef5cb91cd546fbdbd8a529d7ef9bb2168160ae800790d7a7266b531174d8d9be06cad2f1d0f062d9431f7de4beceb02f30ddc97bba44535a703e2d3cc01d2341bb48eb7b25d938f0ed2a7d4c53818e7cb883dc14ffce5899504265869fd3133953c96f48b99ff2055acd53b9f69d2eb8a911bb1f05e2fb8d1d0cc391e1b9ae19fc32b00727a9d8551e1a09319ba94da44cc317bb66e8f372385560cdf8455f858d4afd602307d982d996f729a16c263efa9b8cebe7862b7f9a88ac9fbaf445a603636f6d00003000010000026600440100030df17b60fb56d522f8634153e785c0a978532ea76de39d34bb356d3d042e07f29f7b992176cc83acef7b78ea750425203b18f2b8228b3cdd2bc7eb13c3e3035a7e03636f6d00003000010000026600440101030db71f0465101ddbe2bf0c9455d12fa16c1cda44f4bf1ba2553418ad1f3aa9b06973f21b84eb532cf4035ee8d4832ca26d89306a7d32560c0cb0129d450ac1083503636f6d00002e000100000266005700300d0100015180689f3dfb688b764f4d0603636f6d00d87373f3d5d404f7cdc3aace633c96357bc606ced620792597e1308b1d6c5902668c4d3c1a37bab8486ba24485d57a9d98157fe706424b2043bfb40306d0148403636f6d00002b00010001518000244d060d028acbb0cd28f41250a80a491389424d341522d946b0da0c0291f2d3d771d7805a03636f6d00002e0001000151800113002b08010001518068a404d06892d340b5690024fbea2f86eb0e472114b9da41f1da69e4ef2d02ffcd6bdd987239f288795603d5f54308b238ef19f2747d6a1bc0e775782025561b0f14d1dd19be6bf36b495a3e2d538d5532c5c6e1056c06aa4e81de07f637313955a7761d313db0c6cd0b5c17b4ee22d530d6cdc0c4e195df85b354bbe32027537f1ca21f2815b2d0dbd154582124b3c4c27f1c3aea16f6bfe7e6f5c80aaccd61601bdd8f947ef5c30f004482617cf97629b8b89d8e7320719c979c6a9defdf79b743ecef08bdf2f90796da018fdc6be1e0629fe706044e0f8ad1b25927eca09074a502eb9136eefe5903ad3f97866ab014f1ec96e1f38e3aba66520a25ace386f4897e1ecfd774ce0a0f8a00003000010002a30001080101030803010001acffb409bcc939f831f7a1e5ec88f7a59255ec53040be432027390a4ce896d6f9086f3c5e177fbfe118163aaec7af1462c47945944c4e2c026be5e98bbcded25978272e1e3e079c5094d573f0e83c92f02b32d3513b1550b826929c80dd0f92cac966d17769fd5867b647c3f38029abdc48152eb8f207159ecc5d232c7c1537c79f4b7ac28ff11682f21681bf6d6aba555032bf6f9f036beb2aaa5b3778d6eebfba6bf9ea191be4ab0caea759e2f773a1f9029c73ecb8d5735b9321db085f1b8e2d8038fe2941992548cee0d67dd4547e11dd63af9c9fc1c5466fb684cf009d7197c2cf79e792ab501e6a8a1ca519af2cb9b5f6367e94c0d47502451357be1b500003000010002a30001080101030803010001af7a8deba49d995a792aefc80263e991efdbc86138a931deb2c65d5682eab5d3b03738e3dfdc89d96da64c86c0224d9ce02514d285da3068b19054e5e787b2969058e98e12566c8c808c40c0b769e1db1a24a1bd9b31e303184a31fc7bb56b85bbba8abc02cd5040a444a36d47695969849e16ad856bb58e8fac8855224400319bdab224d83fc0e66aab32ff74bfeaf0f91c454e6850a1295207bbd4cdde8f6ffb08faa9755c2e3284efa01f99393e18786cb132f1e66ebc6517318e1ce8a3b7337ebb54d035ab57d9706ecd9350d4afacd825e43c8668eece89819caf6817af62dc4fbd82f0e33f6647b2b6bda175f14607f59f4635451e6b27df282ef73d8700003000010002a30001080100030803010001b11b182a464c3adc6535aa59613bda7a61cac86945c20b773095941194f4b9f516e8bd924b1e50e3fe83918b51e54529d4e5a1e45303df8462241d5e05979979ae5bf9c6c598c08a496e17f3bd3732d5aebe62667b61db1bbe178f27ac99408165a230d6aee78348e6c67789541f845b2ada96667f8dd16ae44f9e260c4a138b3bb1015965ebe609434a06464bd7d29bac47c3017e83c0f89bca1a9e3bdd0813715f3484292df589bc632e27d37efc02837cb85d770d5bd53a36edc99a8294771aa93cf22406f5506c8cf850ed85c1a475dee5c2d3700b3f5631d903524b849995c20cb407ed411f70b428ae3d642716fe239335aa961a752e67fb6dca0bf72900003000010002a30001080100030803010001b6aec4b48567e2925a2d9c4fa4c96e6dddf86215a9bd8dd579c38ccb1199ed1be89946a7f72fc2633909a2792d0eed1b5afb2ee4c78d865a76d6cd9369d999c96af6be0a2274b8f2e9e0a0065bd20257570f08bc14c16f5616426881a83dbce6926e391c138a2ec317efa7349264de2e791c9b7d4a6048ee6eedf27bf1ece398ff0d229f18377cb1f6b98d1228ef217b8146c0c73851b89a6fc37c621ca187e16428a743ffea0072e185ef93e39525cee3ad01e0c94d2e511c8c313322c29ab91631e1856049a36898684c3056e5997473816fb547acb0be6e660bdfa89a5cb28b3669d8625f3f018c7b3b8a4860e774ee8261811ce7f96c461bc162c1a374f300002e00010002a3000113003008000002a30068a66180688ab2004f66007d114bf33e6d20e7588fdfde9a9e2a8ebd5593ce8bc06419e1d1a4afa8766abc1626504ea6243ca5fc9bce55a3f03c0e7eb488409690d84c3beb30f299da007ab69299d0e203c5b44b94328248768089a9b68982650e9ca2d37526307cbd9f06690e58c3c4a1703b1d1193ea0501417944b937b593294e339571eec42a3c700ce075d9c446e5d32bf979396c1c7935f69bd7df2826567fe582a3615d6095368be991b1e5dc39c0af3b0c39e0e353bbcb928e52e886193ac88da0cd8665ea992b642975aa5486f2e6514d0b5086c66ddd58fe8f7a27ecb128211e3ca1bdc4cad91f3cc9b63c526ebaea86075318e33bfc5a53c919e6f01262b24d178eb2cd04b1 Further valid test cases can be generated by using https://satsto.me and selecting the "Look up using satsto.me's native proof server" option. This will cause lookups to be a single request to a server that returns a full DNSSEC proof (without the HRN prefix), which can be exracted using your browser's console. Generated proofs can be tested against the below dnssec-prover implementation at https://satsto.me/prooftest.html == Reference Implementations == * A DNSSEC proof generation and validation implementation can be found at https://git.bitcoin.ninja/index.cgi?p=dnssec-prover;a=summary * A lightning-specific name to payment instruction resolver can be found at https://git.bitcoin.ninja/index.cgi?p=lightning-resolver;a=summary * Reference implementations for parsing the URI contents can be found in [[bip-0321.mediawiki|BIP 321]]. == Footnotes == == Acknowledgements == Thanks to Rusty Russell for the concrete address rotation suggestion. Thanks to the Bitcoin Design Community, and especially Christoph Ono for lots of discussion, analysis, and UX mockups in how human-readable payment instructions should be displayed. Thanks to Andrew Kaizer for the suggestion to explicitly restrict cache lifetime to the relevant DNS TTLs. ================================================ FILE: bip-0360/ref-impl/.gitignore ================================================ rust-bitcoin rust-miniscript libbitcoinpqc target .btcdeb_history *.swp ================================================ FILE: bip-0360/ref-impl/common/tests/data/p2mr_construction.json ================================================ { "version": 1, "test_vectors": [ { "id": "p2tr_using_v2_witness_version_error", "objective": "Tests that a P2TR v2 scriptPubKey fails with use of witness version 2", "given": { "internalPubkey": "d6889cb081036e0faefa3a35157ad71086b123b2b144b649798b494c300a961d", "scriptTree": null }, "intermediary": { "merkleRoot": null, "tweak": "b86e7be8f39bab32a6f2c0443abbc210f0edac0e2c53d501b36b64437d9c6c70", "tweakedPubkey": "53a1f6e454df1aa2776a2814a721372d6258050de330b3c6d10ee8f4e0dda343" }, "expected": { "scriptPubKey": "522053a1f6e454df1aa2776a2814a721372d6258050de330b3c6d10ee8f4e0dda343", "error": "P2TR requires witness version of 1" } }, { "id": "p2mr_missing_leaf_script_tree_error", "objective": "Tests P2MR with missing leaf script tree", "given": { "script_tree": "" }, "intermediary": { }, "expected": { "error": "P2MR requires a script tree with at least one leaf" } }, { "id": "p2mr_single_leaf_script_tree", "objective": "Tests P2MR with single leaf script tree", "given": { "scriptTree": { "id": 0, "script": "20b617298552a72ade070667e86ca63b8f5789a9fe8731ef91202a91c9f3459007ac", "asm": "b617298552a72ade070667e86ca63b8f5789a9fe8731ef91202a91c9f3459007 OP_CHECKSIG", "leafVersion": 192 } }, "intermediary": { "leafHashes": [ "c525714a7f49c28aedbbba78c005931a81c234b2f6c99a73e4d06082adc8bf2b" ], "merkleRoot": "c525714a7f49c28aedbbba78c005931a81c234b2f6c99a73e4d06082adc8bf2b" }, "expected": { "scriptPubKey": "5220c525714a7f49c28aedbbba78c005931a81c234b2f6c99a73e4d06082adc8bf2b", "bip350Address": "bc1zc5jhzjnlf8pg4mdmhfuvqpvnr2quyd9j7mye5uly6psg9twghu4ssr0v9k", "scriptPathControlBlocks": [ "c1" ] } }, { "id": "p2mr_different_version_leaves", "objective": "Tests P2MR with two script leaves of different versions. TO-DO: currently ignores given leaf version and over-rides. Probably better to throw error", "given": { "scriptTree": [ { "id": 0, "script": "20387671353e273264c495656e27e39ba899ea8fee3bb69fb2a680e22093447d48ac", "asm": "387671353e273264c495656e27e39ba899ea8fee3bb69fb2a680e22093447d48 OP_CHECKSIG", "leafVersion": 192 }, { "id": 1, "script": "06424950333431", "asm": "424950333431", "description": "just pushes the string 'BIP341' onto the stack", "leafVersion": 250 } ] }, "intermediary": { "leafHashes": [ "8ad69ec7cf41c2a4001fd1f738bf1e505ce2277acdcaa63fe4765192497f47a7", "f224a923cd0021ab202ab139cc56802ddb92dcfc172b9212261a539df79a112a" ], "merkleRoot": "6c2dc106ab816b73f9d07e3cd1ef2c8c1256f519748e0813e4edd2405d277bef" }, "expected": { "scriptPubKey": "52206c2dc106ab816b73f9d07e3cd1ef2c8c1256f519748e0813e4edd2405d277bef", "bip350Address": "bc1zdskuzp4ts94h87ws0c7drmev3sf9dagewj8qsylyahfyqhf800hsam4d6e", "scriptPathControlBlocks": [ "c1f224a923cd0021ab202ab139cc56802ddb92dcfc172b9212261a539df79a112a", "c18ad69ec7cf41c2a4001fd1f738bf1e505ce2277acdcaa63fe4765192497f47a7" ] } }, { "id": "p2mr_simple_lightning_contract", "objective": "Tests P2MR with two script leaves that simulate a simple lightning network contract. Reference: https://github.com/bitcoin-core/btcdeb/blob/master/doc/tapscript-example-with-tap.md", "given": { "scriptTree": [ { "id": 0, "script": "029000b275209997a497d964fc1a62885b05a51166a65a90df00492c8d7cf61d6accf54803beac", "asm": "144 OP_CHECKSEQUENCEVERIFY OP_DROP 9997a497d964fc1a62885b05a51166a65a90df00492c8d7cf61d6accf54803be OP_CHECKSIG", "description": "Alice takes the money after waiting 1 day", "leafVersion": 192 }, { "id": 1, "script": "a8206c60f404f8167a38fc70eaf8aa17ac351023bef86bcb9d1086a19afe95bd533388204edfcf9dfe6c0b5c83d1ab3f78d1b39a46ebac6798e08e19761f5ed89ec83c10ac", "asm": "OP_SHA256 6c60f404f8167a38fc70eaf8aa17ac351023bef86bcb9d1086a19afe95bd5333 OP_EQUALVERIFY 4edfcf9dfe6c0b5c83d1ab3f78d1b39a46ebac6798e08e19761f5ed89ec83c10 OP_CHECKSIG", "description": "Bob takes the money whenever he wishes to by revealing the preimage_hash", "leafVersion": 192 } ] }, "intermediary": { "leafHashes": [ "c81451874bd9ebd4b6fd4bba1f84cdfb533c532365d22a0a702205ff658b17c9", "632c8632b4f29c6291416e23135cf78ecb82e525788ea5ed6483e3c6ce943b42" ], "merkleRoot": "41646f8c1fe2a96ddad7f5471bc4fee7da98794ef8c45a4f4fc6a559d60c9f6b" }, "expected": { "scriptPubKey": "522041646f8c1fe2a96ddad7f5471bc4fee7da98794ef8c45a4f4fc6a559d60c9f6b", "bip350Address": "bc1zg9jxlrqlu25kmkkh74r3h387uldfs72wlrz95n60c6j4n4svna4s4lhfhe", "scriptPathControlBlocks": [ "c1c81451874bd9ebd4b6fd4bba1f84cdfb533c532365d22a0a702205ff658b17c9", "c1632c8632b4f29c6291416e23135cf78ecb82e525788ea5ed6483e3c6ce943b42" ] } }, { "id": "p2mr_two_leaf_same_version", "objective": "Tests P2MR with two script leaves of same version", "given": { "scriptTree": [ { "id": 0, "script": "2044b178d64c32c4a05cc4f4d1407268f764c940d20ce97abfd44db5c3592b72fdac", "asm": "44b178d64c32c4a05cc4f4d1407268f764c940d20ce97abfd44db5c3592b72fd OP_CHECKSIG", "leafVersion": 192 }, { "id": 1, "script": "07546170726f6f74", "asm": "546170726f6f74", "description": "pushes the string 'Taproot' onto the stack", "leafVersion": 192 } ] }, "intermediary": { "leafHashes": [ "64512fecdb5afa04f98839b50e6f0cb7b1e539bf6f205f67934083cdcc3c8d89", "2cb2b90daa543b544161530c925f285b06196940d6085ca9474d41dc3822c5cb" ], "merkleRoot": "ab179431c28d3b68fb798957faf5497d69c883c6fb1e1cd9f81483d87bac90cc" }, "expected": { "scriptPubKey": "5220ab179431c28d3b68fb798957faf5497d69c883c6fb1e1cd9f81483d87bac90cc", "bip350Address": "bc1z4vtegvwz35ak37me39tl4a2f045u3q7xlv0pek0czjpas7avjrxqz20g2y", "scriptPathControlBlocks": [ "c12cb2b90daa543b544161530c925f285b06196940d6085ca9474d41dc3822c5cb", "c164512fecdb5afa04f98839b50e6f0cb7b1e539bf6f205f67934083cdcc3c8d89" ] } }, { "id": "p2mr_three_leaf_complex", "objective": "Tests P2MR with a complex three-leaf script tree structure, demonstrating nested script paths and multiple verification options", "given": { "internalPubkey": "e0dfe2300b0dd746a3f8674dfd4525623639042569d829c7f0eed9602d263e6f", "scriptTree": [ { "id": 0, "script": "2072ea6adcf1d371dea8fba1035a09f3d24ed5a059799bae114084130ee5898e69ac", "asm": "72ea6adcf1d371dea8fba1035a09f3d24ed5a059799bae114084130ee5898e69 OP_CHECKSIG", "leafVersion": 192 }, [ { "id": 1, "script": "202352d137f2f3ab38d1eaa976758873377fa5ebb817372c71e2c542313d4abda8ac", "asm": "2352d137f2f3ab38d1eaa976758873377fa5ebb817372c71e2c542313d4abda8 OP_CHECKSIG", "leafVersion": 192 }, { "id": 2, "script": "207337c0dd4253cb86f2c43a2351aadd82cccb12a172cd120452b9bb8324f2186aac", "asm": "7337c0dd4253cb86f2c43a2351aadd82cccb12a172cd120452b9bb8324f2186a OP_CHECKSIG", "leafVersion": 192 } ] ] }, "intermediary": { "leafHashes": [ "2645a02e0aac1fe69d69755733a9b7621b694bb5b5cde2bbfc94066ed62b9817", "ba982a91d4fc552163cb1c0da03676102d5b7a014304c01f0c77b2b8e888de1c", "9e31407bffa15fefbf5090b149d53959ecdf3f62b1246780238c24501d5ceaf6" ], "merkleRoot": "ccbd66c6f7e8fdab47b3a486f59d28262be857f30d4773f2d5ea47f7761ce0e2" }, "expected": { "scriptPubKey": "5220ccbd66c6f7e8fdab47b3a486f59d28262be857f30d4773f2d5ea47f7761ce0e2", "bip350Address": "bc1zej7kd3hhar76k3an5jr0t8fgyc47s4lnp4rh8uk4afrlwasuur3qzgewqq", "scriptPathControlBlocks": [ "c1ffe578e9ea769027e4f5a3de40732f75a88a6353a09d767ddeb66accef85e553", "c1ba982a91d4fc552163cb1c0da03676102d5b7a014304c01f0c77b2b8e888de1c2645a02e0aac1fe69d69755733a9b7621b694bb5b5cde2bbfc94066ed62b9817", "c19e31407bffa15fefbf5090b149d53959ecdf3f62b1246780238c24501d5ceaf62645a02e0aac1fe69d69755733a9b7621b694bb5b5cde2bbfc94066ed62b9817" ] } }, { "id": "p2mr_three_leaf_alternative", "objective": "Tests another variant of P2MR with three leaves arranged in a different tree structure, showing alternative script path spending options", "given": { "internalPubkey": "55adf4e8967fbd2e29f20ac896e60c3b0f1d5b0efa9d34941b5958c7b0a0312d", "scriptTree": [ { "id": 0, "script": "2071981521ad9fc9036687364118fb6ccd2035b96a423c59c5430e98310a11abe2ac", "asm": "71981521ad9fc9036687364118fb6ccd2035b96a423c59c5430e98310a11abe2 OP_CHECKSIG", "leafVersion": 192 }, [ { "id": 1, "script": "20d5094d2dbe9b76e2c245a2b89b6006888952e2faa6a149ae318d69e520617748ac", "asm": "d5094d2dbe9b76e2c245a2b89b6006888952e2faa6a149ae318d69e520617748 OP_CHECKSIG", "leafVersion": 192 }, { "id": 2, "script": "20c440b462ad48c7a77f94cd4532d8f2119dcebbd7c9764557e62726419b08ad4cac", "asm": "c440b462ad48c7a77f94cd4532d8f2119dcebbd7c9764557e62726419b08ad4c OP_CHECKSIG", "leafVersion": 192 } ] ] }, "intermediary": { "leafHashes": [ "f154e8e8e17c31d3462d7132589ed29353c6fafdb884c5a6e04ea938834f0d9d", "737ed1fe30bc42b8022d717b44f0d93516617af64a64753b7a06bf16b26cd711", "d7485025fceb78b9ed667db36ed8b8dc7b1f0b307ac167fa516fe4352b9f4ef7" ], "merkleRoot": "2f6b2c5397b6d68ca18e09a3f05161668ffe93a988582d55c6f07bd5b3329def" }, "expected": { "scriptPubKey": "52202f6b2c5397b6d68ca18e09a3f05161668ffe93a988582d55c6f07bd5b3329def", "bip350Address": "bc1z9a4jc5uhkmtgegvwpx3lq5tpv68layaf3pvz64wx7paatvejnhhsv52lcv", "scriptPathControlBlocks": [ "c13cd369a528b326bc9d2133cbd2ac21451acb31681a410434672c8e34fe757e91", "c1737ed1fe30bc42b8022d717b44f0d93516617af64a64753b7a06bf16b26cd711f154e8e8e17c31d3462d7132589ed29353c6fafdb884c5a6e04ea938834f0d9d", "c1d7485025fceb78b9ed667db36ed8b8dc7b1f0b307ac167fa516fe4352b9f4ef7f154e8e8e17c31d3462d7132589ed29353c6fafdb884c5a6e04ea938834f0d9d" ] } } ] } ================================================ FILE: bip-0360/ref-impl/common/tests/data/p2mr_pqc_construction.json ================================================ { "version": 1, "test_vectors": [ { "id": "p2mr_missing_leaf_script_tree_error", "objective": "Tests P2MR with missing leaf script tree", "given": { "script_tree": "" }, "intermediary": { }, "expected": { "error": "P2MR requires a script tree with at least one leaf" } }, { "id": "p2mr_single_leaf_script_tree", "objective": "Tests P2MR with single leaf script tree", "given": { "scriptTree": { "id": 0, "script": "201f4b1febdc7dfa77c1efacc875b43317b46155e5a564decf475fc369124c5f247f", "asm": "1f4b1febdc7dfa77c1efacc875b43317b46155e5a564decf475fc369124c5f24 OP_SUBSTR", "priv_key": "3f0213a51771f25c906cd82c656175e4b2a10e85958039d6e358352a2eb62b791f4b1febdc7dfa77c1efacc875b43317b46155e5a564decf475fc369124c5f24", "leafVersion": 192 } }, "intermediary": { "leafHashes": [ "3bb0db8c6adcd87330a4a8c91be0fe1b23da3c151b6f2fb4f269429c43b8d8bc" ], "merkleRoot": "3bb0db8c6adcd87330a4a8c91be0fe1b23da3c151b6f2fb4f269429c43b8d8bc" }, "expected": { "scriptPubKey": "52203bb0db8c6adcd87330a4a8c91be0fe1b23da3c151b6f2fb4f269429c43b8d8bc", "bip350Address": "bc1z8wcdhrr2mnv8xv9y4ry3hc87rv3a50q4rdhjld8jd9pfcsacmz7qg5szm8", "scriptPathControlBlocks": [ "c1" ] } }, { "id": "p2mr_different_version_leaves", "objective": "Tests P2MR with two script leaves of different versions. TO-DO: currently ignores given leaf version and over-rides. Probably better to throw error", "given": { "scriptTree": [ { "id": 0, "script": "201f4b1febdc7dfa77c1efacc875b43317b46155e5a564decf475fc369124c5f247f", "asm": "1f4b1febdc7dfa77c1efacc875b43317b46155e5a564decf475fc369124c5f24 OP_SUBSTR", "priv_key": "3f0213a51771f25c906cd82c656175e4b2a10e85958039d6e358352a2eb62b791f4b1febdc7dfa77c1efacc875b43317b46155e5a564decf475fc369124c5f24", "leafVersion": 192 }, { "id": 1, "script": "06424950333431", "asm": "424950333431", "description": "just pushes the string 'BIP341' onto the stack", "leafVersion": 250 } ] }, "intermediary": { "leafHashes": [ "3bb0db8c6adcd87330a4a8c91be0fe1b23da3c151b6f2fb4f269429c43b8d8bc", "f224a923cd0021ab202ab139cc56802ddb92dcfc172b9212261a539df79a112a" ], "merkleRoot": "1619ce6d22a46dea045c4adf7f5f33d6810d00d0e9c8a4c7ba35db37b915c604" }, "expected": { "scriptPubKey": "52201619ce6d22a46dea045c4adf7f5f33d6810d00d0e9c8a4c7ba35db37b915c604", "bip350Address": "bc1zzcvuumfz53k75pzuft0h7hen66qs6qxsa8y2f3a6xhdn0wg4cczq0h84sj", "scriptPathControlBlocks": [ "c13bb0db8c6adcd87330a4a8c91be0fe1b23da3c151b6f2fb4f269429c43b8d8bc", "c1f224a923cd0021ab202ab139cc56802ddb92dcfc172b9212261a539df79a112a" ] } }, { "id": "p2mr_simple_lightning_contract", "objective": "Tests P2MR with two script leaves that simulate a simple lightning network contract. Reference: https://github.com/bitcoin-core/btcdeb/blob/master/doc/tapscript-example-with-tap.md", "given": { "scriptTree": [ { "id": 0, "script": "029000b275201f4b1febdc7dfa77c1efacc875b43317b46155e5a564decf475fc369124c5f247f", "asm": "144 OP_CHECKSEQUENCEVERIFY OP_DROP 1f4b1febdc7dfa77c1efacc875b43317b46155e5a564decf475fc369124c5f24 OP_SUBSTR", "priv_key": "3f0213a51771f25c906cd82c656175e4b2a10e85958039d6e358352a2eb62b791f4b1febdc7dfa77c1efacc875b43317b46155e5a564decf475fc369124c5f24", "description": "Alice takes the money after waiting 1 day", "leafVersion": 192 }, { "id": 1, "script": "a8206c60f404f8167a38fc70eaf8aa17ac351023bef86bcb9d1086a19afe95bd533388204c7f98ab73cc36abeb76d6eace6a9d8b0ff69dfe0f4a17e4f94f0898ec52fadd", "asm": "OP_SHA256 6c60f404f8167a38fc70eaf8aa17ac351023bef86bcb9d1086a19afe95bd5333 OP_EQUALVERIFY 4c7f98ab73cc36abeb76d6eace6a9d8b0ff69dfe0f4a17e4f94f0898ec52fadd OP_SUBSTR", "priv_key": "49a4214f386240d97ea68efb4268043fd5a55208dcdac18ce5bd3332b8e488944c7f98ab73cc36abeb76d6eace6a9d8b0ff69dfe0f4a17e4f94f0898ec52fadd", "description": "Bob takes the money whenever he wishes to by revealing the preimage_hash", "leafVersion": 192 } ] }, "intermediary": { "leafHashes": [ "cfd5fc07ac39947cba799e14f933f20e7c233dea72dc2792f5547c58cdce743e", "a9745ac96d4f3702b78751f1e08f3040fbe6347e7b4f520d22d3f907730cbb7e" ], "merkleRoot": "2794771cd51f215ba3a19fbcdf08c771edb7de782a0c34457e0e9be5d0e4008f" }, "expected": { "scriptPubKey": "52202794771cd51f215ba3a19fbcdf08c771edb7de782a0c34457e0e9be5d0e4008f", "bip350Address": "bc1zy728w8x4rus4hgapn77d7zx8w8km0hnc9gxrg3t7p6d7t58yqz8sg0nccq", "scriptPathControlBlocks": [ "c1cfd5fc07ac39947cba799e14f933f20e7c233dea72dc2792f5547c58cdce743e", "c1a9745ac96d4f3702b78751f1e08f3040fbe6347e7b4f520d22d3f907730cbb7e" ] } }, { "id": "p2mr_two_leaf_same_version", "objective": "Tests P2MR with two script leaves of same version", "given": { "scriptTree": [ { "id": 0, "script": "20e6b3dad32fc04095a021f5356163cfc14e15f703831e332c56f6b499801f53447f", "asm": "e6b3dad32fc04095a021f5356163cfc14e15f703831e332c56f6b499801f5344 OP_SUBSTR", "priv_key": "a695d8a1351774d59ed1b980462c2ab8d58b3b7a48f55b114c6a39980dc1c13ee6b3dad32fc04095a021f5356163cfc14e15f703831e332c56f6b499801f5344", "leafVersion": 192 }, { "id": 1, "script": "07546170726f6f74", "asm": "546170726f6f74", "description": "pushes the string 'Taproot' onto the stack", "leafVersion": 192 } ] }, "intermediary": { "leafHashes": [ "9de7eeded7832c28c6f80de76904dd79f98fd302747823b5bc5be440186b0c6d", "2cb2b90daa543b544161530c925f285b06196940d6085ca9474d41dc3822c5cb" ], "merkleRoot": "5112b3edfd2c0b717491e9d4888ed2d5dfeaa25115143540e0a08516b68c008c" }, "expected": { "scriptPubKey": "52205112b3edfd2c0b717491e9d4888ed2d5dfeaa25115143540e0a08516b68c008c", "bip350Address": "bc1z2yft8m0a9s9hzay3a82g3rkj6h074gj3z52r2s8q5zz3dd5vqzxqngpk2w", "scriptPathControlBlocks": [ "c19de7eeded7832c28c6f80de76904dd79f98fd302747823b5bc5be440186b0c6d", "c12cb2b90daa543b544161530c925f285b06196940d6085ca9474d41dc3822c5cb" ] } }, { "id": "p2mr_three_leaf_complex", "objective": "Tests P2MR with a complex three-leaf script tree structure, demonstrating nested script paths and multiple verification options", "given": { "scriptTree": [ { "id": 0, "script": "201d58016252d5a941f84574c4821b5f87e56778b2bbc3b610dfd801fc0250f6cc7f", "asm": "1d58016252d5a941f84574c4821b5f87e56778b2bbc3b610dfd801fc0250f6cc OP_SUBSTR", "priv_key": "2b339b5055fad695f0595d5581fa087455854f64c5443c03d5b4ca53549f12a41d58016252d5a941f84574c4821b5f87e56778b2bbc3b610dfd801fc0250f6cc", "leafVersion": 192 }, [ { "id": 1, "script": "20a3b0dcac08f86306ba04f5fe2a3243ef3a0347c0e2a4529720a18d3cfdce90ad7f", "asm": "a3b0dcac08f86306ba04f5fe2a3243ef3a0347c0e2a4529720a18d3cfdce90ad OP_SUBSTR", "priv_key": "ec29d60c1be9263602906499b5e3c1de9e36cc88cec31154210191a578b92e9da3b0dcac08f86306ba04f5fe2a3243ef3a0347c0e2a4529720a18d3cfdce90ad", "leafVersion": 192 }, { "id": 2, "script": "20e6ccf03593dbd07eba10403e33586c130889de6e8219da0a9ccbdd46a56a5f367f", "asm": "e6ccf03593dbd07eba10403e33586c130889de6e8219da0a9ccbdd46a56a5f36 OP_SUBSTR", "priv_key": "da04d13f706a6e0d22ac0db7c361f1aaa706a27043efca4edfecfed3125238e1e6ccf03593dbd07eba10403e33586c130889de6e8219da0a9ccbdd46a56a5f36", "leafVersion": 192 } ] ] }, "intermediary": { "leafHashes": [ "0840c39e59eda6c9deee687a480cb169130c2f053ed2eb3134511ec1cfd8a2c7", "837ef6677aeb0df2b0de47f45024684cc6ca03bda10fa30bb5bc05a94beb8dd1", "b2a5304f678cc5a2ed51feb377dd0a609bd22ec979cc608bfcf884d0f8e6f93a" ], "merkleRoot": "eaf8f557fdb9673de7bb9bad7e7452da9f44a3e65133fdadf2849c55cfb3cf5b" }, "expected": { "scriptPubKey": "5220eaf8f557fdb9673de7bb9bad7e7452da9f44a3e65133fdadf2849c55cfb3cf5b", "bip350Address": "bc1zatu024lah9nnmeamnwkhuazjm205fglx2yelmt0jsjw9tnaneadszq7wg7", "scriptPathControlBlocks": [ "c1837ef6677aeb0df2b0de47f45024684cc6ca03bda10fa30bb5bc05a94beb8dd1b2a5304f678cc5a2ed51feb377dd0a609bd22ec979cc608bfcf884d0f8e6f93a", "c10840c39e59eda6c9deee687a480cb169130c2f053ed2eb3134511ec1cfd8a2c7b2a5304f678cc5a2ed51feb377dd0a609bd22ec979cc608bfcf884d0f8e6f93a", "c118781f42f664d67acaf0ce7c6826437e5440eb1789f232af05e9a09fdf547903" ] } }, { "id": "p2mr_three_leaf_alternative", "objective": "Tests another variant of P2MR with three leaves arranged in a different tree structure, showing alternative script path spending options", "given": { "scriptTree": [ { "id": 0, "script": "20409f78ce0978519ff5d960c4ab595174c7efca11b1f89410a4e98b70cd423e1c7f", "asm": "409f78ce0978519ff5d960c4ab595174c7efca11b1f89410a4e98b70cd423e1c OP_SUBSTR", "priv_key": "c6ec3801b04afa40be6f77f3f7a7b3b7cb8cfe233b0263fb70e2f087b21397c1409f78ce0978519ff5d960c4ab595174c7efca11b1f89410a4e98b70cd423e1c", "leafVersion": 192 }, [ { "id": 1, "script": "209f0955dc884a5c88d1732e017d30e27e8a445889bce5aa42611b7635c5c1073a7f", "asm": "9f0955dc884a5c88d1732e017d30e27e8a445889bce5aa42611b7635c5c1073a OP_SUBSTR", "priv_key": "7524bca170d54231f1246f30fb00f9da2208b1363ba5a7bbaf11fc3b0309e9519f0955dc884a5c88d1732e017d30e27e8a445889bce5aa42611b7635c5c1073a", "leafVersion": 192 }, { "id": 2, "script": "20c60b10d57c0cdf27e5c751e131ea4301b37abe7384948059256c7f5f1f285a7f7f", "asm": "c60b10d57c0cdf27e5c751e131ea4301b37abe7384948059256c7f5f1f285a7f OP_SUBSTR", "priv_key": "d9d0f17d630b6a538e6a8a036373e7b9e5023a4c08f72dd8c3ef59288b98c079c60b10d57c0cdf27e5c751e131ea4301b37abe7384948059256c7f5f1f285a7f", "leafVersion": 192 } ] ] }, "intermediary": { "leafHashes": [ "52e9326c2bf04d926b7e9f6c7645dd853f3f007b870201de9b814952750c9310", "dcef3ce86cc8cea78c9e00f3d9ef58360cb6ed3cb90ec62efe00b9703854ba5c", "ddb521a44e33ff4974e618d8b8b7794275b7dc754d847c537404f84330454361" ], "merkleRoot": "51e3c1151ba73d9efce801837773331bf9030977242f62dfeb6756795f482409" }, "expected": { "scriptPubKey": "522051e3c1151ba73d9efce801837773331bf9030977242f62dfeb6756795f482409", "bip350Address": "bc1z283uz9gm5u7eal8gqxphwuenr0usxzthyshk9hltvat8jh6gysys28twnc", "scriptPathControlBlocks": [ "c1dcef3ce86cc8cea78c9e00f3d9ef58360cb6ed3cb90ec62efe00b9703854ba5cddb521a44e33ff4974e618d8b8b7794275b7dc754d847c537404f84330454361", "c152e9326c2bf04d926b7e9f6c7645dd853f3f007b870201de9b814952750c9310ddb521a44e33ff4974e618d8b8b7794275b7dc754d847c537404f84330454361", "c1b45680a7821e4b9450096ab38adbc3c99225af8f6c7ec121a0a5f1ae02893ba3" ] } } ] } ================================================ FILE: bip-0360/ref-impl/common/utils/signet_miner_loop.sh ================================================ #!/bin/bash # Invokes mining simulator a configurable number of times if [ -z "${P2MR_ADDR}" ]; then echo "Error: Environment variable P2MR_ADDR needs to be set" exit 1 fi BITCOIN_SOURCE_DIR=${BITCOIN_SOURCE_DIR:-$HOME/bitcoin} # path to bitcoin.conf for signet BITCOIN_CONF_FILE_PATH=${BITCOIN_CONF_FILE_PATH:-$HOME/anduro-360/configs/bitcoin.conf.signet} # Set default LOOP_COUNT to 110 if not set LOOP_COUNT=${LOOP_COUNT:-110} # Validate LOOP_COUNT is a positive integer if ! [[ "$LOOP_COUNT" =~ ^[0-9]+$ ]] || [ "$LOOP_COUNT" -le 0 ]; then echo "Error: LOOP_COUNT must be a positive integer" exit 1 fi # Determine name of pool by querying mempool.space backend # curl -X GET "http://localhost:8999/api/v1/mining/pool/marapool" | jq -r .pool.regexes export POOL_ID=${POOL_ID:-"MARA Pool"} echo -en "\nLoop_COUNT = $LOOP_COUNT\nBITCOIN_CONF_FILE_PATH=$BITCOIN_CONF_FILE_PATH\nBITCOIN_SOURCE_DIR=$BITCOIN_SOURCE_DIR\nPOOL_ID=$POOL_ID\n\n"; for ((i=1; i<=LOOP_COUNT; i++)) do echo "Iteration $i of $LOOP_COUNT" $BITCOIN_SOURCE_DIR/contrib/signet/miner --cli "bitcoin-cli -conf=$BITCOIN_CONF_FILE_PATH" generate \ --address $P2MR_ADDR \ --grind-cmd "$BITCOIN_SOURCE_DIR/build/bin/bitcoin-util grind" \ --poolid "$POOL_ID" \ --min-nbits --set-block-time $(date +%s) done ================================================ FILE: bip-0360/ref-impl/common/utils/workshop/Dockerfile.bcli ================================================ # podman build -f Dockerfile.bcli -t quay.io/jbride2000/p2mr_bcli:0.1 . # podman run -it --entrypoint /bin/bash quay.io/jbride200/p2mr_bcli:0.1 FROM rust:1-slim-bookworm AS builder # Install build dependencies RUN apt-get update && apt-get install -y \ build-essential \ cmake \ git \ autoconf \ automake \ libtool \ pkg-config \ zlib1g-dev \ libevent-dev \ libboost-dev \ libzmq3-dev \ bash \ python3 \ python3-pip \ libclang-dev \ clang \ && rm -rf /var/lib/apt/lists/* # Set working directory WORKDIR /bitcoin # Copy Bitcoin Core source (or clone) # COPY . /bitcoin RUN git clone --branch p2mr-pqc --single-branch https://github.com/jbride/bitcoin.git # Environment variables for musl ENV CC=gcc ENV CXX=g++ # Build Bitcoin Core WORKDIR bitcoin RUN apt-get update && apt-get install -y libsqlite3-dev && rm -rf /var/lib/apt/lists/* RUN mkdir build && cd build && \ cmake .. \ -DWITH_ZMQ=ON \ -DBUILD_BENCH=ON \ -DBUILD_DAEMON=ON && \ make -j$(nproc) bitcoin-cli # Runtime stage with Debian Slim FROM debian:bookworm-slim # Install minimal runtime dependencies RUN apt-get update && apt-get install -y --no-install-recommends \ bash \ ca-certificates \ libevent-core-2.1-7 \ libevent-pthreads-2.1-7 \ libevent-extra-2.1-7 \ libboost-filesystem1.74.0 \ libboost-thread1.74.0 \ libzmq5 \ libsqlite3-0 \ telnet \ && rm -rf /var/lib/apt/lists/* # Copy bitcoin-cli from builder COPY --from=builder /bitcoin/bitcoin/build/bin/bitcoin-cli /usr/local/bin/bitcoin-cli # Create non-root user and set permissions RUN groupadd --system bip360 && \ useradd --system --gid bip360 --shell /bin/bash --create-home bip360 && \ chmod +x /usr/local/bin/bitcoin-cli && \ ln -s /usr/local/bin/bitcoin-cli /usr/local/bin/b-cli && \ echo 'b-cli() { /usr/local/bin/bitcoin-cli -rpcconnect=${RPC_CONNECT:-192.168.122.1} -rpcport=${RPC_PORT:-18443} -rpcuser=${RPC_USER:-signet} -rpcpassword=${RPC_PASSWORD:-signet} "$@"; }' >> /home/bip360/.bashrc # Set default environment variables (can be overridden at runtime) ENV RPC_CONNECT=192.168.122.1 \ RPC_PORT=38332 \ RPC_USER=signet \ RPC_PASSWORD=signet # Switch to non-root user USER bip360 WORKDIR /home/bip360 ENTRYPOINT ["/usr/local/bin/bitcoin-cli"] ================================================ FILE: bip-0360/ref-impl/common/utils/workshop/Dockerfile.full ================================================ # podman build -f Dockerfile.full -t quay.io/jbride2000/p2mr_demo:0.1 . # podman run -it --entrypoint /bin/bash quay.io/jbride2000/p2mr_demo:0.1 FROM rust:1-slim-bookworm AS builder # Install build dependencies RUN apt-get update && apt-get install -y \ build-essential \ cmake \ git \ autoconf \ automake \ libtool \ pkg-config \ zlib1g-dev \ libevent-dev \ libboost-dev \ libzmq3-dev \ bash \ python3 \ python3-pip \ libclang-dev \ clang \ && rm -rf /var/lib/apt/lists/* # Set working directory WORKDIR /bitcoin # Copy Bitcoin Core source (or clone) # COPY . /bitcoin RUN git clone --branch p2mr-pqc --single-branch https://github.com/jbride/bitcoin.git # Environment variables for musl ENV CC=gcc ENV CXX=g++ # Build Bitcoin Core WORKDIR bitcoin RUN apt-get update && apt-get install -y libsqlite3-dev && rm -rf /var/lib/apt/lists/* RUN mkdir build && cd build && \ cmake .. \ -DWITH_ZMQ=ON \ -DBUILD_BENCH=ON \ -DBUILD_DAEMON=ON && \ make -j$(nproc) bitcoin-cli # Runtime stage with Debian Slim FROM rust:1-slim-bookworm # Install minimal runtime dependencies RUN apt-get update && apt-get install -y --no-install-recommends \ bash \ ca-certificates \ libevent-core-2.1-7 \ libevent-pthreads-2.1-7 \ libevent-extra-2.1-7 \ libboost-filesystem1.74.0 \ libboost-thread1.74.0 \ libzmq5 \ libsqlite3-0 \ && rm -rf /var/lib/apt/lists/* # Copy bitcoin-cli from builder COPY --from=builder /bitcoin/bitcoin/build/bin/bitcoin-cli /usr/local/bin/bitcoin-cli # Create non-root user and set permissions RUN groupadd --system bip360 && \ useradd --system --gid bip360 --shell /bin/bash --create-home bip360 && \ chmod +x /usr/local/bin/bitcoin-cli && \ ln -s /usr/local/bin/bitcoin-cli /usr/local/bin/b-cli && \ echo 'b-cli() { /usr/local/bin/bitcoin-cli -rpcconnect=${RPC_CONNECT:-192.168.122.1} -rpcport=${RPC_PORT:-18443} -rpcuser=${RPC_USER:-signet} -rpcpassword=${RPC_PASSWORD:-signet} "$@"; }' >> /home/bip360/.bashrc # Install additional tools needed for building Rust code (before switching to non-root user) RUN apt-get update && apt-get install -y --no-install-recommends \ libclang-dev \ clang \ git \ curl \ cmake \ build-essential \ jq \ gawk \ telnet \ && rm -rf /var/lib/apt/lists/* # Set default environment variables (can be overridden at runtime) ENV RPC_CONNECT=192.168.122.1 \ RPC_PORT=38332 \ RPC_USER=signet \ RPC_PASSWORD=signet # Switch to non-root user USER bip360 WORKDIR /home/bip360 RUN git clone --no-checkout --depth 1 --branch p2mr-pqc \ --single-branch https://github.com/jbride/bips.git bips && \ cd bips && \ git sparse-checkout init --cone && \ git sparse-checkout set bip-0360 && \ git checkout && \ cd bip-0360/ref-impl/rust && \ cargo build && \ rm -rf target WORKDIR /home/bip360/bips/bip-0360/ref-impl/rust ENV BITCOIN_NETWORK=signet \ USE_PQC=true ENTRYPOINT ["/usr/local/bin/bitcoin-cli"] ================================================ FILE: bip-0360/ref-impl/common/utils/workshop/bip360-workshop.drawio ================================================ ================================================ FILE: bip-0360/ref-impl/js/.gitignore ================================================ # Dependencies node_modules/ npm-debug.log* yarn-debug.log* yarn-error.log* pnpm-debug.log* lerna-debug.log* # Build outputs dist/ build/ *.tsbuildinfo # TypeScript *.js.map *.d.ts.map # Environment variables .env .env.local .env.*.local # IDE / Editor files .vscode/ .idea/ *.swp *.swo *~ .DS_Store # OS files Thumbs.db desktop.ini # Testing coverage/ .nyc_output/ *.lcov # Logs logs/ *.log # Temporary files *.tmp *.temp .cache/ # Optional npm cache directory .npm # Optional eslint cache .eslintcache # Optional REPL history .node_repl_history # Output of 'npm pack' *.tgz # Yarn Integrity file .yarn-integrity # parcel-bundler cache .parcel-cache # Next.js (if ever used) .next out # Vercel (if ever used) .vercel # Turbo (if ever used) .turbo ================================================ FILE: bip-0360/ref-impl/js/README.adoc ================================================ = BIP 360 Javascript Reference Implementation :numbered: == procedure ----- $ npm install # compile Typecript $ npx tsc # run tests $ node src/p2mr-example.ts $ node src/test-npm-pqc-package.js ----- ================================================ FILE: bip-0360/ref-impl/js/package.json ================================================ { "name": "js", "version": "1.0.0", "type": "module", "description": "", "main": "index.js", "scripts": { "test": "echo \"Error: no test specified\" && exit 1" }, "keywords": [], "author": "", "license": "ISC", "devDependencies": { "@types/node": "^24.10.0", "typescript": "^5.9.3" }, "dependencies": { "@jbride/bitcoinjs-lib": "^7.0.0-rc.0-p2mr-0.0", "@jbride/bitcoinpqc-wasm": "^0.1.1", "ecpair": "^3.0.0", "tiny-secp256k1": "^2.2.4" } } ================================================ FILE: bip-0360/ref-impl/js/src/p2mr-example.ts ================================================ // src/p2mr-example.ts // Example demonstrating P2MR (Pay-to-Taproot-Script-Hash) address construction import { payments } from '@jbride/bitcoinjs-lib'; import * as bitcoinCrypto from '@jbride/bitcoinjs-lib/src/crypto'; import * as bscript from '@jbride/bitcoinjs-lib/src/script'; import type { Taptree } from '@jbride/bitcoinjs-lib/src/types'; import ECPairFactory, { type ECPairInterface } from 'ecpair'; import * as ecc from 'tiny-secp256k1'; import { randomBytes } from 'crypto'; const { p2mr } = payments; // Initialize ECPair with the ECC library const ECPair = ECPairFactory(ecc); // Create a secure RNG function const rng = (size: number) => randomBytes(size); function signAndVerify( keyPair: ECPairInterface, xOnlyPubkey: Uint8Array, message: Buffer, ) { const hash = Buffer.from(bitcoinCrypto.hash256(message)); const schnorrSignature = Buffer.from(keyPair.signSchnorr(hash)); const signatureWithSighashDefault = Buffer.concat([schnorrSignature, Buffer.from([0x00])]); const verified = keyPair.verifySchnorr(hash, schnorrSignature); return { message, hash, signature: schnorrSignature, signatureWithSighashDefault, verified, }; } /** * Example 1: Construct a P2MR address from a script tree with a single leaf * This is the simplest case - a script tree containing one script. */ function example1_simpleScriptTree() { console.log('=== Example 1: P2MR from simple script tree ==='); // Generate a key pair const keyPair = ECPair.makeRandom({ rng }); const pubkey = keyPair.publicKey; const xOnlyPubkey = ecc.xOnlyPointFromPoint(pubkey); // Compile the script: x-only pubkey OP_CHECKSIG (BIP342 Schnorr signature) const script = bscript.compile([Buffer.from(xOnlyPubkey), bscript.OPS.OP_CHECKSIG]); // Create a script tree with one leaf const scriptTree = { output: script, }; // Construct the P2MR payment const payment = p2mr({ scriptTree: scriptTree, }); console.log('Generated compressed pubkey:', pubkey.toString('hex')); console.log('X-only pubkey:', Buffer.from(xOnlyPubkey).toString('hex')); console.log('Script tree:', { output: bscript.toASM(script) }); console.log('P2MR Address:', payment.address); console.log('Output script:', bscript.toASM(payment.output!)); console.log('Merkle root hash:', payment.hash ? Buffer.from(payment.hash).toString('hex') : undefined); const message = Buffer.from('P2MR demo - example 1', 'utf8'); const result = signAndVerify(keyPair, xOnlyPubkey, message); console.log('Message:', result.message.toString('utf8')); console.log('Hash256(message):', result.hash.toString('hex')); console.log('Schnorr signature (64-byte):', result.signature.toString('hex')); console.log('Signature + default sighash (65-byte witness element):', result.signatureWithSighashDefault.toString('hex')); console.log('Signature valid:', result.verified); console.log('Witness stack for spend:', [result.signatureWithSighashDefault.toString('hex'), bscript.toASM(script)]); console.log(); } /** * Example 2: Construct a P2MR address from a script tree with multiple leaves * This demonstrates a more complex script tree structure. */ function example2_multiLeafScriptTree() { console.log('=== Example 2: P2MR from multi-leaf script tree ==='); // Generate two different key pairs for the leaves const keyPair1 = ECPair.makeRandom({ rng }); const keyPair2 = ECPair.makeRandom({ rng }); const pubkey1 = keyPair1.publicKey; const pubkey2 = keyPair2.publicKey; const xOnlyPubkey1 = ecc.xOnlyPointFromPoint(pubkey1); const xOnlyPubkey2 = ecc.xOnlyPointFromPoint(pubkey2); const script1 = bscript.compile([Buffer.from(xOnlyPubkey1), bscript.OPS.OP_CHECKSIG]); const script2 = bscript.compile([Buffer.from(xOnlyPubkey2), bscript.OPS.OP_CHECKSIG]); // Create a script tree with two leaves (array of two leaf objects) const scriptTree: Taptree = [ { output: script1 }, { output: script2 }, ]; // Construct the P2MR payment const payment = p2mr({ scriptTree: scriptTree, }); console.log('Generated compressed public keys:'); console.log(' Pubkey 1:', pubkey1.toString('hex')); console.log(' Pubkey 2:', pubkey2.toString('hex')); console.log('X-only pubkeys:'); console.log(' X-only 1:', Buffer.from(xOnlyPubkey1).toString('hex')); console.log(' X-only 2:', Buffer.from(xOnlyPubkey2).toString('hex')); console.log('Script tree leaves:'); console.log(' Leaf 1:', bscript.toASM(script1)); console.log(' Leaf 2:', bscript.toASM(script2)); console.log('P2MR Address:', payment.address); console.log('Output script:', bscript.toASM(payment.output!)); console.log('Merkle root hash:', payment.hash ? Buffer.from(payment.hash).toString('hex') : undefined); const message1 = Buffer.from('P2MR demo - example 2 leaf 1', 'utf8'); const message2 = Buffer.from('P2MR demo - example 2 leaf 2', 'utf8'); const result1 = signAndVerify(keyPair1, xOnlyPubkey1, message1); const result2 = signAndVerify(keyPair2, xOnlyPubkey2, message2); console.log('Leaf 1 signature info:'); console.log(' Message:', result1.message.toString('utf8')); console.log(' Hash256(message):', result1.hash.toString('hex')); console.log(' Schnorr signature (64-byte):', result1.signature.toString('hex')); console.log(' Signature + default sighash (65-byte):', result1.signatureWithSighashDefault.toString('hex')); console.log(' Signature valid:', result1.verified); console.log(' Witness stack:', [result1.signatureWithSighashDefault.toString('hex'), bscript.toASM(script1)]); console.log('Leaf 2 signature info:'); console.log(' Message:', result2.message.toString('utf8')); console.log(' Hash256(message):', result2.hash.toString('hex')); console.log(' Schnorr signature (64-byte):', result2.signature.toString('hex')); console.log(' Signature + default sighash (65-byte):', result2.signatureWithSighashDefault.toString('hex')); console.log(' Signature valid:', result2.verified); console.log(' Witness stack:', [result2.signatureWithSighashDefault.toString('hex'), bscript.toASM(script2)]); console.log(); } /** * Example 4: Construct a P2MR address from a hash and redeem script * This demonstrates creating a P2MR when you have the hash directly. */ function example3_fromHashAndRedeem() { console.log('=== Example 3: P2MR from hash and redeem script ==='); // Generate a key pair const keyPair = ECPair.makeRandom({ rng }); const pubkey = keyPair.publicKey; const xOnlyPubkey = ecc.xOnlyPointFromPoint(pubkey); const redeemScript = bscript.compile([Buffer.from(xOnlyPubkey), bscript.OPS.OP_CHECKSIG]); // Use a known hash (from test fixtures) const hash = Buffer.from( 'b424dea09f840b932a00373cdcdbd25650b8c3acfe54a9f4a641a286721b8d26', 'hex', ); // Construct the P2MR payment const payment = p2mr({ hash: hash, redeem: { output: redeemScript, }, }); console.log('Generated compressed pubkey:', pubkey.toString('hex')); console.log('X-only pubkey:', Buffer.from(xOnlyPubkey).toString('hex')); console.log('Redeem script:', bscript.toASM(redeemScript)); console.log('Hash:', hash.toString('hex')); console.log('P2MR Address:', payment.address); console.log('Output script:', bscript.toASM(payment.output!)); const message = Buffer.from('P2MR demo - example 3', 'utf8'); const result = signAndVerify(keyPair, xOnlyPubkey, message); console.log('Message:', result.message.toString('utf8')); console.log('Hash256(message):', result.hash.toString('hex')); console.log('Schnorr signature (64-byte):', result.signature.toString('hex')); console.log('Signature + default sighash (65-byte):', result.signatureWithSighashDefault.toString('hex')); console.log('Signature valid:', result.verified); console.log('Witness stack:', [result.signatureWithSighashDefault.toString('hex'), bscript.toASM(redeemScript)]); console.log(); } // Run all examples console.log('P2MR Address Construction Examples\n'); console.log('=====================================\n'); example1_simpleScriptTree(); example2_multiLeafScriptTree(); example3_fromHashAndRedeem(); console.log('====================================='); console.log('All examples completed!'); ================================================ FILE: bip-0360/ref-impl/js/src/test-npm-pqc-package.js ================================================ #!/usr/bin/env node /** * Node.js test script for Bitcoin PQC WASM module (High-Level API) * * Usage: node test-npm-package.js * * This script tests the high-level TypeScript wrapper API (index.js) from the * command line, which provides a cleaner interface than the low-level API. */ import { randomBytes } from 'node:crypto'; // Load the high-level WASM module let bitcoinpqc; let Algorithm; try { const module = await import('@jbride/bitcoinpqc-wasm'); bitcoinpqc = module.bitcoinpqc || module.default; Algorithm = module.Algorithm; if (!bitcoinpqc || !Algorithm) { throw new Error('Failed to import bitcoinpqc or Algorithm from @jbride/bitcoinpqc-wasm'); } } catch (error) { console.error('Failed to load WASM module:', error); console.error('Make sure you have installed the @jbride/bitcoinpqc-wasm package before running this test.'); process.exit(1); } // Helper function to generate random bytes function generateRandomBytes(length) { const array = new Uint8Array(length); const bytes = randomBytes(length); array.set(bytes); return array; } // Test function async function testAlgorithm(algorithm, name) { console.log(`\nTesting ${name} algorithm:`); console.log('------------------------'); try { // Get key and signature sizes const pkSize = bitcoinpqc.publicKeySize(algorithm); const skSize = bitcoinpqc.secretKeySize(algorithm); const sigSize = bitcoinpqc.signatureSize(algorithm); console.log(`Public key size: ${pkSize} bytes`); console.log(`Secret key size: ${skSize} bytes`); console.log(`Signature size: ${sigSize} bytes`); // Generate random data for key generation const randomData = generateRandomBytes(128); // Generate a key pair const keygenStart = Date.now(); const keypair = bitcoinpqc.generateKeypair(algorithm, randomData); const keygenDuration = Date.now() - keygenStart; console.log(`Key generation time: ${keygenDuration} ms`); // Create a message to sign const messageText = 'This is a test message for PQC signature verification'; const message = Buffer.from(messageText, 'utf8'); const messageUint8 = new Uint8Array(message); console.log(`Message to sign: "${messageText}"`); console.log(`Message length: ${message.length} bytes`); // Sign the message const signStart = Date.now(); let signature; try { signature = bitcoinpqc.sign(keypair.secretKey, messageUint8, algorithm); const signDuration = Date.now() - signStart; console.log(`Signing time: ${signDuration} ms`); console.log(`Actual signature size: ${signature.size} bytes`); } catch (error) { const signDuration = Date.now() - signStart; console.log(`Signing failed after ${signDuration} ms`); console.log(`Error: ${error.message}`); if (algorithm === Algorithm.SLH_DSA_SHAKE_128S) { console.log(''); console.log('⚠️ NOTE: SLH-DSA-SHAKE-128s signing is currently experiencing'); console.log(' issues when compiled to WebAssembly. This appears to be a'); console.log(' bug in the SPHINCS+ reference implementation when compiled'); console.log(' to WASM. ML-DSA-44 (Dilithium) works correctly.'); console.log(''); console.log(' Key generation succeeded, but signing failed.'); console.log(' This is a known limitation of the browser/WASM build.'); } throw error; } // Verify the signature const verifyStart = Date.now(); const verifyResult = bitcoinpqc.verify( keypair.publicKey, messageUint8, signature, algorithm ); const verifyDuration = Date.now() - verifyStart; if (verifyResult) { console.log('Signature verified successfully!'); } else { console.log('ERROR: Signature verification failed!'); } console.log(`Verification time: ${verifyDuration} ms`); // Try to verify with a modified message const modifiedMessageText = 'This is a MODIFIED message for PQC signature verification'; const modifiedMessage = Buffer.from(modifiedMessageText, 'utf8'); const modifiedMessageUint8 = new Uint8Array(modifiedMessage); console.log(`Modified message: "${modifiedMessageText}"`); const modifiedVerifyResult = bitcoinpqc.verify( keypair.publicKey, modifiedMessageUint8, signature, algorithm ); if (modifiedVerifyResult) { console.log('ERROR: Signature verified for modified message!'); } else { console.log('Correctly rejected signature for modified message'); } console.log('✓ Test passed!\n'); return true; } catch (error) { console.error(`❌ Error: ${error.message}`); if (error.stack) { console.error(error.stack); } return false; } } async function runTests() { console.log('Bitcoin PQC Library Example (Node.js - High-Level API)'); console.log('======================================================\n'); console.log('This example tests the post-quantum signature algorithms designed for BIP-360 and the Bitcoin QuBit soft fork.'); console.log('Using the high-level TypeScript wrapper API (index.js).\n'); // Initialize the module try { console.log('Initializing WASM module...'); await bitcoinpqc.init({ onRuntimeInitialized: () => { console.log('✓ WASM module initialized successfully!\n'); }, print: (text) => { // Enable WASM print output for debugging console.log('WASM:', text); }, printErr: (text) => { console.error('WASM Error:', text); }, // Node.js-specific: provide crypto.getRandomValues getRandomValues: (arr) => { const bytes = randomBytes(arr.length); arr.set(bytes); return arr; } }); } catch (error) { console.error('Failed to initialize module:', error); if (error.stack) { console.error(error.stack); } process.exit(1); } const results = []; // Test ML-DSA-44 results.push(await testAlgorithm(Algorithm.ML_DSA_44, 'ML-DSA-44')); // Test SLH-DSA-Shake-128s results.push(await testAlgorithm(Algorithm.SLH_DSA_SHAKE_128S, 'SLH-DSA-Shake-128s')); // Summary console.log('\n======================================================'); console.log('Test Summary:'); console.log(` ML-DSA-44: ${results[0] ? '✓ PASSED' : '✗ FAILED'}`); console.log(` SLH-DSA-Shake-128s: ${results[1] ? '✓ PASSED' : '✗ FAILED'}`); console.log('======================================================\n'); const exitCode = results.every(r => r) ? 0 : 1; process.exit(exitCode); } // Start runTests(); ================================================ FILE: bip-0360/ref-impl/js/tsconfig.json ================================================ { // Visit https://aka.ms/tsconfig to read more about this file "include": [ "src/**/*" ], "compilerOptions": { // File Layout "rootDir": "./src", "outDir": "./dist", // Environment Settings // See also https://aka.ms/tsconfig/module "module": "nodenext", "target": "esnext", "types": ["node"], // For nodejs: // "lib": ["esnext"], // Other Outputs "sourceMap": true, "declaration": true, "declarationMap": true, // Stricter Typechecking Options "noUncheckedIndexedAccess": true, "exactOptionalPropertyTypes": true, // Style Options // "noImplicitReturns": true, // "noImplicitOverride": true, // "noUnusedLocals": true, // "noUnusedParameters": true, // "noFallthroughCasesInSwitch": true, // "noPropertyAccessFromIndexSignature": true, // Recommended Options "strict": true, "jsx": "react-jsx", "verbatimModuleSyntax": true, "isolatedModules": true, "noUncheckedSideEffectImports": true, "moduleDetection": "force", "skipLibCheck": true, } } ================================================ FILE: bip-0360/ref-impl/python/.gitignore ================================================ # Byte-compiled / optimized / DLL files __pycache__/ *.py[cod] *$py.class # C extensions *.so # Distribution / packaging .Python build/ develop-eggs/ dist/ downloads/ eggs/ .eggs/ lib/ lib64/ parts/ sdist/ var/ wheels/ pip-wheel-metadata/ share/python-wheels/ *.egg-info/ .installed.cfg *.egg MANIFEST # PyInstaller # Usually these files are written by a python script from a template # before PyInstaller builds the exe, so as to inject date/other infos into it. *.manifest *.spec # Installer logs pip-log.txt pip-delete-this-directory.txt # Unit test / coverage reports htmlcov/ .tox/ .nox/ .coverage .coverage.* .cache nosetests.xml coverage.xml *.cover *.py,cover .hypothesis/ .pytest_cache/ # Translations *.mo *.pot # Django stuff: *.log local_settings.py db.sqlite3 db.sqlite3-journal # Flask stuff: instance/ .webassets-cache # Scrapy stuff: .scrapy # Sphinx documentation docs/_build/ # PyBuilder target/ # Jupyter Notebook .ipynb_checkpoints # IPython profile_default/ ipython_config.py # pyenv .python-version # pipenv # According to pypa/pipenv#598, it is recommended to include Pipfile.lock in version control. # However, in case of collaboration, if having platform-specific dependencies or dependencies # having no cross-platform support, pipenv may install dependencies that don't work, or not # install all needed dependencies. #Pipfile.lock # PEP 582; used by e.g. github.com/David-OConnor/pyflow __pypackages__/ # Celery stuff celerybeat-schedule celerybeat.pid # SageMath parsed files *.sage.py # Environments .env .venv env/ venv/ ENV/ env.bak/ venv.bak/ # Spyder project settings .spyderproject .spyproject # Rope project settings .ropeproject # mkdocs documentation /site # mypy .mypy_cache/ .dmypy.json dmypy.json # Pyre type checker .pyre/ ================================================ FILE: bip-0360/ref-impl/rust/.cargo/config.toml ================================================ [registries.kellnr-denver-space] index = "sparse+https://crates.denver.space/api/v1/crates/" ================================================ FILE: bip-0360/ref-impl/rust/Cargo.toml ================================================ [package] name = "p2mr-ref" version = "0.1.0" edition = "2024" [dependencies] # Dev version of miniscript crate re-exports bitcoin 0.32.6 # view configuration for "kellnr-denver-space": # cat .cargo/config.toml miniscript = { version="=13.0.0-p2mr-pqc-1.0", registry="kellnr-denver-space" } bitcoin = { package = "bitcoin-p2mr-pqc", version="0.32.6-p2mr-pqc.1", features = ["rand-std", "serde", "base64"], registry = "kellnr-denver-space" } bitcoinpqc = { version="0.3.0", features = ["serde"], registry="kellnr-denver-space" } # BDK Wallet with P2MR support #bdk_wallet = { version = "=3.0.0-alpha.0-pqc-0.1", registry = "kellnr-denver-space" } env_logger = "0.11.5" log = "0.4.22" serde = { version = "1.0", features = ["derive"] } serde_json = "1.0" once_cell = "1.19" hex = "0.4.3" anyhow = "1.0.98" thiserror = "2.0.12" rand = "0.9" [patch.crates-io] #bitcoin = { git = "https://github.com/jbride/rust-bitcoin.git", branch = "p2mr" } # Verify: # cargo update # cargo tree -p bitcoin | more # bitcoin = { path = "./rust-bitcoin/bitcoin" } # cargo tree -p miniscript | more #miniscript = { path = "./rust-miniscript" } # bitcoinpqc = { path = "./libbitcoinpqc" } ================================================ FILE: bip-0360/ref-impl/rust/README.md ================================================ # p2mr test vectors This rust project contains the test vectors for BIP-360 ## Run Test Vectors These test vectors are being developed in conjunction with forks of [rust-bitcoin](https://github.com/jbride/rust-bitcoin/tree/p2mr) and [rust-miniscript](https://github.com/jbride/rust-miniscript/tree/p2mr-pqc) customized with p2mr functionality. 1. environment variables ``` // Specify Bitcoin network used when generating bip350 (bech32m) address // Options: regtest, testnet, signet // Default: mainnet $ export BITCOIN_NETWORK= ``` 1. run a specific test: ``` $ cargo test test_p2mr_single_leaf_script_tree -- --nocapture ``` ## Local Development All P2MR/PQC enabled bitcoin crates are temporarily available in a custom crate registry at: `https://crates.denver.space`. These crates will be made available in `crates.io` in the near future. Subsequently, you will need to execute the following at the root of your rust workspace: ```bash mkdir .cargo \ && echo '[registries.kellnr-denver-space] index = "sparse+https://crates.denver.space/api/v1/crates/"' > .cargo/config ``` Afterwards, for all P2MR/PQC enabled dependencies used in your project, include a "registry" similar to the following: ```bash bitcoin = { version="0.32.6", registry = "kellnr-denver-space" } ``` ================================================ FILE: bip-0360/ref-impl/rust/docs/development_notes.adoc ================================================ == bitcoin core === Two Different Size Limits: * *MAX_SCRIPT_ELEMENT_SIZE* (in interpreter.cpp line 1882) - This is a consensus rule that limits individual stack elements to 520 bytes. This is what's currently blocking your SLH-DSA signature. * *MAX_STANDARD_P2MR_STACK_ITEM_SIZE* (in policy.h) - This is a policy rule that limits P2MR stack items to 80 bytes (or 8000 bytes with your change) for standardness. == P2MR changes to rust-bitcoin # 1. p2mr module The p2mr branch of rust-bitcoin includes a new module: `p2mr`. Source code for this new module can be found [here](https://github.com/jbride/rust-bitcoin/blob/p2mr/bitcoin/src/p2mr/mod.rs). Highlights of this _p2mr_ module as follows: ## 1.1. p2mrBuilder This is struct inherits from the rust-bitcoin _TaprootBuilder_. It has an important modification in that it disables keypath spend. Similar to its Taproot parent, p2mrBuilder provides functionality to add leaves to a TapTree. One its TapTree has been fully populated with all leaves, an instance of _p2mrSpendInfo_ can be retrieved from p2mrBuilder. ``` pub struct p2mrBuilder { inner: TaprootBuilder } impl p2mrBuilder { /// Creates a new p2mr builder. pub fn new() -> Self { Self { inner: TaprootBuilder::new() } } /// Adds a leaf to the p2mr builder. pub fn add_leaf_with_ver( self, depth: u8, script: ScriptBuf, leaf_version: LeafVersion, ) -> Result { match self.inner.add_leaf_with_ver(depth, script, leaf_version) { Ok(builder) => Ok(Self { inner: builder }), Err(_) => Err(p2mrError::LeafAdditionError) } } /// Finalizes the p2mr builder. pub fn finalize(self) -> Result { let node_info: NodeInfo = self.inner.try_into_node_info().unwrap(); Ok(p2mrSpendInfo { merkle_root: Some(node_info.node_hash()), //script_map: self.inner.script_map().clone(), }) } /// Converts the p2mr builder into a Taproot builder. pub fn into_inner(self) -> TaprootBuilder { self.inner } } ``` ## 1.2. p2mrSpendInfo Provides merkle_root of a completed p2mr TapTree ``` /// A struct for p2mr spend information. #[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)] pub struct p2mrSpendInfo { /// The merkle root of the script path. pub merkle_root: Option } ``` ## 1.3. p2mrScriptBuf Allows for creation of a p2mr scriptPubKey UTXO using only the merkle root of a script tree only. ``` /// A wrapper around ScriptBuf for p2mr (Pay to Quantum Resistant Hash) scripts. pub struct p2mrScriptBuf { inner: ScriptBuf } impl p2mrScriptBuf { /// Creates a new p2mr script from a ScriptBuf. pub fn new(inner: ScriptBuf) -> Self { Self { inner } } /// Generates p2mr scriptPubKey output /// Only accepts the merkle_root (of type TapNodeHash) /// since keypath spend is disabled in p2mr pub fn new_p2mr(merkle_root: TapNodeHash) -> Self { // https://github.com/cryptoquick/bips/blob/p2mr/bip-0360.mediawiki#scriptpubkey let merkle_root_hash_bytes: [u8; 32] = merkle_root.to_byte_array(); let script = Builder::new() .push_opcode(OP_PUSHNUM_3) // automatically pre-fixes with OP_PUSHBYTES_32 (as per size of hash) .push_slice(&merkle_root_hash_bytes) .into_script(); p2mrScriptBuf::new(script) } /// Returns the script as a reference. pub fn as_script(&self) -> &Script { self.inner.as_script() } } ``` ## 1.4. p2mr Control Block Closely related to P2TR control block. Difference being that _internal public key_ is not included. ``` /// A control block for p2mr (Pay to Quantum Resistant Hash) script path spending. /// This is a simplified version of Taproot's control block that excludes key-related fields. #[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)] pub struct p2mrControlBlock { /// The version of the leaf. pub leaf_version: LeafVersion, /// The merkle branch of the leaf. pub merkle_branch: TaprootMerkleBranch, } ``` # 2. Witness Program New p2mr related functions that allow for creation of a new V3 _witness program_ given a merkle_root only. Found in bitcoin/src/blockdata/script/witness_program.rs ``` /// Creates a [`WitnessProgram`] from a 32 byte merkle root. fn new_p2mr(program: [u8; 32]) -> Self { WitnessProgram { version: WitnessVersion::V3, program: ArrayVec::from_slice(&program) } } /// Creates a pay to quantum resistant hash address from a merkle root. pub fn p2mr(merkle_root: Option) -> Self { let merkle_root = merkle_root.unwrap(); WitnessProgram::new_p2mr(merkle_root.to_byte_array()) } ``` # 3. Address New _p2mr_ function that allows for creation of a new _p2mr_ Address given a merkle_root only. Found in bitcoin/src/address/mod.rs ``` /// Creates a pay to quantum resistant hash address from a merkle root. pub fn p2mr(merkle_root: Option, hrp: impl Into) -> Address { let program = WitnessProgram::p2mr(merkle_root); Address::from_witness_program(program, hrp) } ``` ================================================ FILE: bip-0360/ref-impl/rust/docs/p2mr-end-to-end.adoc ================================================ :scrollbar: :data-uri: :toc2: :linkattrs: = P2MR End-to-End Tutorial :numbered: This tutorial is inspired by the link:https://learnmeabitcoin.com/technical/upgrades/taproot/#example-3-script-path-spend-signature[script-path-spend-signature] example of the _learnmeabitcoin_ tutorial. It is customized to create, fund and spend from a P2MR UTXO to a P2WPKH address. In addition, this tutorial allows for the (un)locking mechanism of the script to optionally use _Post Quantum Cryptography_ (PQC). The purpose of this tutorial is to demonstrate construction and spending of a link:https://github.com/cryptoquick/bips/blob/p2qrh/bip-0360.mediawiki[bip-360] `p2mr` UTXO (optionally using _Post-Quantum Cryptography_). The steps outlined in this tutorial are executed using a custom Bitcoin Core instance running either in `regtest` or `signet`. == Pre-reqs === Bitcoin Core If participating in a workshop, your instructor will provide a bitcoin environment. Related: your instructor should also provide you with a wallet. Otherwise, if running this tutorial on your own, follow the instructions in the appendix of this doc: <>. === Shell Environment . *docker / podman* + NOTE: If you have built the custom `p2mr` enabled Bitcoin Core, you do not need docker (nor podman) installed. Skip this section. + This tutorial makes use of a `p2mr` enabled _bitcoin-cli_ utility. This utility is made available as a docker (or podman) container. Ensure your host machine has either docker or podman installed. . *bitcoin-cli* command line utility: + NOTE: If you have built the custom `p2mr` enabled Bitcoin Core, you can simply use the `bitcoin-cli` utility found in the `build/bin/` directory. No need to use the _dockerized_ utility described below. .. You will need a `bitcoin-cli` binary that is `p2mr` enabled. For this purpose, a docker container with this `bitcoin-cli` utility is provided: + ----- docker pull quay.io/jbride2000/bitcoin-cli:p2mr-pqc-0.0.1 ----- .. Configure an alias to the `bitcoin-cli` command that connects to your customized bitcoin-core node. + ----- alias b-cli='docker run --rm --network host bitcoin-cli:p2mr-pqc-0.0.1 -rpcconnect=192.168.122.1 -rpcport=18443 -rpcuser=regtest -rpcpassword=regtest' ----- . *jq*: ensure json parsing utility is link:https://jqlang.org/download/[installed] and available via your $PATH. . *awk* : standard utility for all Linux distros (often packaged as `gawk`). . *Rust* development environment with _cargo_ utility. Use link:https://rustup[Rustup] to install. == Create & Fund P2MR UTXO The purpose of this workshop is to demonstrate construction and spending of a link:https://github.com/cryptoquick/bips/blob/p2qrh/bip-0360.mediawiki[bip-360] _P2MR_ address (optionally using _Post-Quantum Cryptography_). In this section of the workshop, you create and fund a P2MR address. The following depicts the construction of a P2MR _TapTree_ and computation its _scriptPubKey_. image::images/p2mr_construction.png[] A P2MR address is created by adding locking scripts to leaves of a _TapTree_. The locking scripts can use either _Schnorr_ (as per BIP-360) or _SLH-DSA_ (defined in a future BIP) cryptography. . Set an environment variable specific to your Bitcoin network environment (regtest, signet, etc) + [source,bash] ----- export BITCOIN_NETWORK=regtest ----- + Doing so influences the P2MR address that you'll create later in this tutorial. . Define number of total leaves in tap tree : + [source,bash] ----- export TOTAL_LEAF_COUNT=5 ----- . OPTIONAL: Indicate what type of cryptography to use in the locking scripts of your TapTree leaves. Valid options are: `MIXED`, `SCHNORR_ONLY`, `SLH_DSA_ONLY`, and `CONCATENATED_SCHNORR_AND_SLH_DSA`. Default is `MIXED`. + [source,bash] ----- export TAP_TREE_LOCK_TYPE=MIXED ----- .. If you set _TAP_TREE_LOCK_TYPE=SCHNORR_ONLY_, then the locking script of your TapTree leaves will utilize _Schnorr_ cryptography. + Schnorr is not quantum-resistant. However, its signature size is relatively small: 64 bytes. A _SCHNORR_ONLY_ tap tree with 5 leaves (aka: TOTAL_LEAF_COUNT) could be represented as follows: + image::images/tap_tree_schnorr_only.png[s,300] .. If you set _TAP_TREE_LOCK_TYPE=SLH_DSA_ONLY_, then the locking script of your TapTree leaves will utilize _SLH-DSA_ cryptography. A _SLH_DSA_ONLY_ tap tree with 5 leaves (aka: TOTAL_LEAF_COUNT) could be represented as follows: + image::images/tap_tree_slh_dsa_only.png[l,300] + SLH_DSA is quantum-resistant. However, the trade-off is the much larger signature size 7,856 bytes when spending. + image::images/crypto_key_characteristics.png[] + NOTE: PQC cryptography is made available to this BIP-360 reference implementation via the link:https://crates.io/crates/bitcoinpqc[libbitcoinpqc Rust bindings]. .. If you set _MIXED_, then each leaf of the taptree will consist of *either* a Schnorr based locking script or a SLH-DSA based locking script. A _MIXED_ tap tree with 5 leaves (aka: TOTAL_LEAF_COUNT) could be represented as follows: + image::images/tap_tree_mixed.png[t,300] + NOTE: The benefit of constructing a taptree with a mixed set of cryptography used as locking scripts in the leaves is articulated nicely in link:https://www.bitmex.com/blog/Taproot%20Quantum%20Spend%20Paths[this article from BitMex]. .. If you set _TAP_TREE_LOCK_TYPE=CONCATENATED_SCHNORR_AND_SLH_DSA_, then the locking script of your TapTree leaves will be secured using both SCHNORR and SLH-DSA cryptography in a concatenated / serial manner. Private keys for both SCHNORR and SLH-DSA will be needed when unlocking. A _CONCATENATED_SCHNORR_AND_SLH_DSA_ tap tree with 5 leaves (aka: TOTAL_LEAF_COUNT) could be represented as follows: + image::images/tap_tree_concatenated.png[p,300] . Set the tap leaf index to later use as the unlocking script (when spending) For example, to later spend from the 5th leaf of the tap tree: + [source,bash] ----- export LEAF_TO_SPEND_FROM=4 ----- . Generate a P2MR scripPubKey with multi-leaf taptree: + [source,bash] ----- export BITCOIN_ADDRESS_INFO=$( cargo run --example p2mr_construction ) \ && echo $BITCOIN_ADDRESS_INFO | jq -r . ----- + NOTE: In `regtest`, you can expect a P2MR address that starts with: `bcrt1z` . + [subs=+quotes] ++++
What just happened? The Rust based reference implementation for BIP-0360 is leveraged to construct a transaction with a `p2mr` UTXO as follows:
  • A configurable number of leaves are generated each with their own locking script.
  • Each of these leaves are added to a Huffman tree that sorts the leaves by weight.
  • The merkle root of the tree is calculated and subsequently used to generate the p2mr witness program and BIP0350 address.

The source code for the above logic is found in this project: src/lib.rs
++++ . Only if you previously set `TAP_TREE_LOCK_TYPE=MIXED`, set the environment variable `SPENDING_LEAF_TYPE`. Valid values are `SHNORR_ONLY` or `SLH_DSA_ONLY` based on the type of locking script that was used in the leaf you will spend from later in this lab. The logs from the previous step tell you the appropriate value to set. For instance: + ----- NOTE: TAP_TREE_LOCK_TYPE=MIXED requires setting SPENDING_LEAF_TYPE when spending (based on leaf_script_type in output above) as follows: export SPENDING_LEAF_TYPE=SCHNORR_ONLY ----- . Set some env vars (for use in later steps in this tutorial) based on previous result: + [source,bash] ----- export MERKLE_ROOT=$( echo $BITCOIN_ADDRESS_INFO | jq -r '.taptree_return.tree_root_hex' ) \ && export LEAF_SCRIPT_PRIV_KEYS_HEX=$( echo $BITCOIN_ADDRESS_INFO | jq -r '.taptree_return.leaf_script_priv_keys_hex' ) \ && export LEAF_SCRIPT_HEX=$( echo $BITCOIN_ADDRESS_INFO | jq -r '.taptree_return.leaf_script_hex' ) \ && export CONTROL_BLOCK_HEX=$( echo $BITCOIN_ADDRESS_INFO | jq -r '.taptree_return.control_block_hex' ) \ && export FUNDING_SCRIPT_PUBKEY=$( echo $BITCOIN_ADDRESS_INFO | jq -r '.utxo_return.script_pubkey_hex' ) \ && export P2MR_ADDR=$( echo $BITCOIN_ADDRESS_INFO | jq -r '.utxo_return.bech32m_address' ) ----- . View tapscript used in target leaf of taptree: + [source,bash] ----- b-cli decodescript $LEAF_SCRIPT_HEX | jq -r '.asm' ----- + NOTE: If not using PQC, notice that this script commits to a Schnorr 32-byte x-only public key. If using PQC, this script commits to a Schnorr 32-byte SLH-DSA pub key and a OP_SUCCESS127 (represented as `OP_SUBSTR`) opcode. . Fund this P2MR address with the coinbase reward of a newly generated block: + Choose from one of the following networks: .. Regtest + If on `regtest` network, execute the following: + [source,bash] ----- export COINBASE_REWARD_TX_ID=$( b-cli -named generatetoaddress nblocks=1 address="$P2MR_ADDR" maxtries=5 | jq -r '.[]' ) \ && echo $COINBASE_REWARD_TX_ID ----- + NOTE: Sometimes Bitcoin Core may not hit a block (even on regtest). If so, just try the above command again. .. Signet + If on `signet` network, then execute the following: + [source,bash] ----- $BITCOIN_SOURCE_DIR/contrib/signet/miner --cli "bitcoin-cli -conf=$HOME/anduro-360/configs/bitcoin.conf.signet" generate \ --address $P2MR_ADDR \ --grind-cmd "$BITCOIN_SOURCE_DIR/build/bin/bitcoin-util grind" \ --min-nbits --set-block-time $(date +%s) \ --poolid "MARA Pool" ----- . view summary of all txs that have funded P2MR address + [source,bash] ----- export P2MR_DESC=$( b-cli getdescriptorinfo "addr($P2MR_ADDR)" | jq -r '.descriptor' ) \ && echo $P2MR_DESC \ && b-cli scantxoutset start '[{"desc": "'''$P2MR_DESC'''"}]' ----- . grab txid of first tx with unspent funds: + [source,bash] ----- export FUNDING_TX_ID=$( b-cli scantxoutset start '[{"desc": "'''$P2MR_DESC'''"}]' | jq -r '.unspents[0].txid' ) \ && echo $FUNDING_TX_ID ----- . Set FUNDING_UTXO_INDEX env var (used later to correctly identify funding UTXO when generating the spending tx) + [source,bash] ----- export FUNDING_UTXO_INDEX=0 ----- . view details of funding UTXO to the P2MR address: + [source,bash] ----- export FUNDING_UTXO=$( b-cli getrawtransaction $FUNDING_TX_ID 1 | jq -r '.vout['''$FUNDING_UTXO_INDEX''']' ) \ && echo $FUNDING_UTXO | jq -r . ----- + NOTE: the above only works when Bitcoin Core is started with the following arg: -txindex == Spend P2MR UTXO In the previous section, you created and funded a P2MR UTXO. That UTXO includes a leaf script locked with a key-pair (optionally based on PQC) known to you. In this section, you spend from that P2MR UTXO. Specifically, you will generate an appropriate _SigHash_ and sign it (to create a signature) using the known private key that unlocks the known leaf script of the P2MR UTXO. For the purpose of this tutorial, you will spend funds to a new P2WPKH utxo. (there is nothing novel about this P2WPKH utxo). . Determine value (in sats) of the funding P2MR utxo: + [source,bash] ----- export FUNDING_UTXO_AMOUNT_SATS=$(echo $FUNDING_UTXO | jq -r '.value' | awk '{printf "%.0f", $1 * 100000000}') \ && echo $FUNDING_UTXO_AMOUNT_SATS ----- . Generate additional blocks. + This is necessary if you have only previously generated less than 100 blocks. + Otherwise, you may see an error from bitcoin core such as the following when attempting to spend: + _bad-txns-premature-spend-of-coinbase, tried to spend coinbase at depth 1_ .. regtest + [source,bash] ----- b-cli -generate 110 ----- .. signet + This will involve having the signet miner generate about 110 blocks .... which can take about 10 minutes. + The `common/utils` directory of this project provides a script called: link:../../common/utils/signet_miner_loop.sh[signet_miner_loop.sh]. . Referencing the funding tx (via $FUNDING_TX_ID and $FUNDING_UTXO_INDEX), create the spending tx: + [source,bash] ----- export SPEND_DETAILS=$( cargo run --example p2mr_spend ) ----- + [subs=+quotes] ++++
What just happened? The Rust based reference implementation for BIP-0360 is leveraged to construct a transaction that spends from the `p2mr` UTXO as follows:
  • Create a transaction template (aka: SigHash) that serves as the message to be signed.
  • Using the known private key and the SigHash, create a signature that is capable of unlocking one of the leaf scripts of the P2MR tree.
  • Add this signature to the witness section of the transaction.

The source code for the above logic is found in this project: src/lib.rs
++++ . Set environment variables passed to _bitcoin-cli_ when spending: + [source,bash] ----- export RAW_P2MR_SPEND_TX=$( echo $SPEND_DETAILS | jq -r '.tx_hex' ) \ && echo "RAW_P2MR_SPEND_TX = $RAW_P2MR_SPEND_TX" \ && export SIG_HASH=$( echo $SPEND_DETAILS | jq -r '.sighash' ) \ && echo "SIG_HASH = $SIG_HASH" \ && export SIG_BYTES=$( echo $SPEND_DETAILS | jq -r '.sig_bytes' ) \ && echo "SIG_BYTES = $SIG_BYTES" ----- . Inspect the spending tx: + [source,bash] ----- b-cli decoderawtransaction $RAW_P2MR_SPEND_TX ----- + Pay particular attention to the `vin.txinwitness` field. Do the three elements (script input, script and control block) of the witness stack for this script path spend make sense ? What do you observe as the first byte of the `control block` element ? . Test standardness of the spending tx by sending to local mempool of p2mr enabled Bitcoin Core: + [source,bash] ----- b-cli testmempoolaccept '["'''$RAW_P2MR_SPEND_TX'''"]' ----- . Submit tx: + [source,bash] ----- export P2MR_SPENDING_TX_ID=$( b-cli sendrawtransaction $RAW_P2MR_SPEND_TX ) \ && echo $P2MR_SPENDING_TX_ID ----- + NOTE: Should return same tx id as was included in $RAW_P2MR_SPEND_TX == Mine P2MR Spend TX . View tx in mempool: + [source,bash] ----- b-cli getrawtransaction $P2MR_SPENDING_TX_ID 1 ----- + NOTE: There will not yet be a field `blockhash` in the response. . Mine 1 block: .. regtest: + [source,bash] ----- b-cli -generate 1 ----- .. signet: + If on `signet` network, then execute the following: + [source,bash] ----- $BITCOIN_SOURCE_DIR/contrib/signet/miner --cli "bitcoin-cli -conf=$HOME/anduro-360/configs/bitcoin.conf.signet" generate \ --address $P2MR_ADDR \ --grind-cmd "$BITCOIN_SOURCE_DIR/build/bin/bitcoin-util grind" \ --min-nbits --set-block-time $(date +%s) \ --poolid "MARA Pool" ----- . Obtain `blockhash` field of mined tx: + [source,bash] ----- export BLOCK_HASH=$( b-cli getrawtransaction $P2MR_SPENDING_TX_ID 1 | jq -r '.blockhash' ) \ && echo $BLOCK_HASH ----- . View tx in block: + [source,bash] ----- b-cli getblock $BLOCK_HASH | jq -r .tx ----- == Appendix [[build_p2mr]] === Build P2MR / PQC Enabled Bitcoin Core The link:https://github.com/jbride/bitcoin/tree/p2mr[p2mr branch] of bitcoin core is needed. Build instructions for the `p2mr` branch are the same as `master` and is documented link:https://github.com/bitcoin/bitcoin/blob/master/doc/build-unix.md[here]. As such, the following is an example series of steps (on a Fedora 42 host) to compile and run the `p2mr` branch of bitcoin core: . Set BITCOIN_SOURCE_DIR + ----- export BITCOIN_SOURCE_DIR=/path/to/root/dir/of/cloned/bitcoin/source ----- . build + ----- cmake -B build \ -DWITH_ZMQ=ON \ -DCMAKE_EXPORT_COMPILE_COMMANDS=ON \ -DBUILD_BENCH=ON \ -DBUILD_DAEMON=ON \ -DSANITIZERS=address,undefined cmake --build build -j$(nproc) ----- . run in either `regtest` or `signet` mode: .. regtest: + ----- ./build/bin/bitcoind -daemon=0 -regtest=1 -txindex -prune=0 ----- .. signet: + ----- ./build/bin/bitcoind -daemon=0 -signet=1 -txindex -prune=0 ----- + NOTE: If running in `signet`, your bitcoin core will need to be configured with the `signetchallenge` property. link:https://edil.com.br/blog/creating-a-custom-bitcoin-signet[This tutorial] provides a nice overview of the topic. === libbitcoinpqc build The `p2mr-pqc` branch of this project includes a dependency on the link:https://crates.io/crates/libbitcoinpqc[libbitcoinpqc crate]. libbitcoinpqc contains native code (C/C++/ASM) and is made available to Rust projects via Rust bindings. This C/C++/ASM code is provided in the libbitcoinpqc crate as source code (not prebuilt binaries). Subsequently, the `Cargo` utility needs to build this libbitcoinpqc C native code on your local machine. You will need to have C development related libraries installed on your local machine. Every developer or CI machine building `p2mr-ref` must have cmake and a C toolchain installed locally. ==== Linux . Debian / Ubuntu + ----- sudo apt update sudo apt install cmake build-essential clang libclang-dev ----- . Fedora / RHEL + ----- sudo dnf5 update sudo dnf5 install cmake make gcc gcc-c++ clang clang-libs llvm-devel ----- ==== OSX [[bitcoin_core_wallet]] === Bitcoin Core Wallet This tutorial assumes that a bitcoin core wallet is available. . For example, the following would be sufficient: + ----- export W_NAME=anduro b-cli -named createwallet \ wallet_name=$W_NAME \ descriptors=true \ load_on_startup=true ----- === Schnorr + SLH-DSA ----- OP_CHECKSIG OP_SUBSTR OP_BOOLAND OP_VERIFY ----- The logic flow is: . OP_CHECKSIG: Verify Schnorr signature against Schnorr pubkey . OP_SUBSTR: Verify SLH-DSA signature against SLH-DSA pubkey (using OP_SUBSTR for the SLH-DSA verification) . OP_BOOLAND: Ensure both signature verifications succeeded . OP_VERIFY: Final verification that the script execution succeeded . This creates a "both signatures required" locking condition, which is exactly what you want for SCHNORR_AND_SLH_DSA scripts. ===== Sighash bytes Sighash bytes are appended to each signature, instead of being separate witness elements: . SlhDsaOnly: SLH-DSA signature + sighash byte appended . SchnorrOnly: Schnorr signature + sighash byte appended . SchnorrAndSlhDsa: Schnorr signature (no sighash) + SLH-DSA signature + sighash byte appended to the last signature ================================================ FILE: bip-0360/ref-impl/rust/docs/p2mr-signet-workshop.adoc ================================================ :scrollbar: :data-uri: :toc2: :linkattrs: = P2MR End-to-End workshop :numbered: Welcome to the BIP-360 / _Pay-To-Tap-Script-Hash_ (P2MR) workshop ! In this workshop, you will interact with a custom Signet environment to create, fund and spend from a _P2MR_ address. _P2MR_ is a new Bitcoin address type defined in link:https://bip360.org/bip360.html[bip-360]. In addition, this workshop allows for the (un)locking mechanism of the leaf scripts of your P2MR address to optionally use _Post Quantum Cryptography_ (PQC). The use of PQC is alluded to in BIP-360 and will be further defined in future BIPs. The steps outlined in this workshop are executed using a P2MR/PQC enabled Bitcoin Core instance running on a signet environment. *The target audience of the workshop is Bitcoin developers and ops personnel. As such, the workshop makes heavy use of the _bitcoin-cli_ at the command line.* == Pre-reqs === *docker / podman* This workshop environment is provided as a _docker_ container. Subsequently, ensure your host machine has either link:https://docs.docker.com/desktop/[docker] or link:https://podman.io/docs/installation[podman] installed. === *p2mr_demo* docker container ==== Obtain container Once docker or podman is installed on your machine, you can obtain the workshop docker container via any of the following: . Pull from _quay.io_ : + [source,bash] ----- sudo docker pull quay.io/jbride2000/p2mr_demo:0.1 ----- + NOTE: The container image is 1.76GB in size. This approach may be slow depending on network bandwidth. . Download container image archive file from local HTTP server: + *TO_DO* . Obtain container image archive file from instructor: .. Workshop instructors have the container image available via USB thumb drives. If you feel comfortable with this approach, ask an instructor for a thumb drive. ... Mount the USB thumb drive and copy for the file called: _p2mr_demo-image.tar_. ... Load the container image into your docker environment as per the following: + [source,bash] ----- docker load -i /path/to/p2mr_demo-image.tar ----- ==== Start container You will need to start the workshop container using the docker infrastructure on your machine. . If working at the command line, the following is an example to run the container and obtain a command prompt: + [source,bash] ----- sudo docker run -it --rm --entrypoint /bin/bash --network host \ -e RPC_CONNECT=10.21.3.194 \ quay.io/jbride2000/p2mr_demo:0.1 ----- . You should see a _bash_ shell command prompt similar to the following: + ----- bip360@0aa9edf3d201:~/bips/bip-0360/ref-impl/rust$ ls Cargo.lock Cargo.toml README.md docs examples src tests ----- + As per the `ls` command seen above, your command prompt path defaults to the link:https://github.com/jbride/bips/tree/p2mr/bip-0360/ref-impl/rust[Rust based reference implementation] for BIP-360. ==== Container contents Your docker environment already includes a P2MR/PQC enabled `bitcoin-cli` utility. In addition, an alias to this custom bitcoin-cli utility configured for the signet workshop environment has also been provided. . You can view this alias as follows (execute all commands within workshop container image): + [source,bash] ----- declare -f b-cli ----- + You should see a response similar to the following: + ----- b-cli () { /usr/local/bin/bitcoin-cli -rpcconnect=${RPC_CONNECT:-192.168.122.1} -rpcport=${RPC_PORT:-18443} -rpcuser=${RPC_USER:-signet} -rpcpassword=${RPC_PASSWORD:-signet} "$@" } ----- . Test interaction between your _b-cli_ utility and the workshop's signet node via the following: + [source,bash] ----- b-cli getnetworkinfo ----- + [source,bash] ----- b-cli getblockcount ----- . In addition, your docker environment also comes pre-installed with the following utilities needed for this workshop: . *jq*: json parsing utility . *awk* . *Rust* development environment with _cargo_ utility == Bitcoin Environment Your workshop instructors have provided you with a _P2MR/PQC_ enabled Bitcoin environment running in _signet_. You will send RPC commands to this custom Bitcoin node via the _b-cli_of your docker container. image::images/workshop_deployment_arch.png[] Via your browser, you will interact with the P2MR enabled _mempool.space_ for the workshop at: link:http://signet.bip360.org[signet.bip360.org]. == Create & Fund P2MR Address The purpose of this workshop is to demonstrate construction and spending of a link:https://github.com/cryptoquick/bips/blob/p2qrh/bip-0360.mediawiki[bip-360] _P2MR_ address (optionally using _Post-Quantum Cryptography_). In this section of the workshop, you create and fund a P2MR address. The following depicts the construction of a P2MR _TapTree_ and computation its _scriptPubKey_. image::images/p2mr_construction.png[] A P2MR address is created by adding locking scripts to leaves of a _TapTree_. The locking scripts can use either _Schnorr_ (as per BIP-360) or _SLH-DSA_ (defined in a future BIP) cryptography. . Define number of total leaves in tap tree : + [source,bash] ----- export TOTAL_LEAF_COUNT=5 ----- . In your container image, indicate what type of cryptography to use in the locking scripts of your TapTree leaves. Valid options are: `MIXED`, `SLH_DSA_ONLY`, `SCHNORR_ONLY`, `CONCATENATED_SCHNORR_AND_SLH_DSA`. Default is `MIXED`. + [source,bash] ----- export TAP_TREE_LOCK_TYPE=MIXED ----- .. If you set _TAP_TREE_LOCK_TYPE=SCHNORR_ONLY_, then the locking script of your TapTree leaves will utilize _Schnorr_ cryptography. + Schnorr is not quantum-resistant. However, its signature size is relatively small: 64 bytes. A _SCHNORR_ONLY_ tap tree with 5 leaves (aka: TOTAL_LEAF_COUNT) could be represented as follows: + image::images/tap_tree_schnorr_only.png[s,300] .. If you set _TAP_TREE_LOCK_TYPE=SLH_DSA_ONLY_, then the locking script of your TapTree leaves will utilize _SLH-DSA_ cryptography. A _SLH_DSA_ONLY_ tap tree with 5 leaves (aka: TOTAL_LEAF_COUNT) could be represented as follows: + image::images/tap_tree_slh_dsa_only.png[l,300] + SLH_DSA is quantum-resistant. However, the trade-off is the much larger signature size 7,856 bytes when spending. + image::images/crypto_key_characteristics.png[] + NOTE: PQC cryptography is made available to this BIP-360 reference implementation via the link:https://crates.io/crates/bitcoinpqc[libbitcoinpqc Rust bindings]. .. If you set _MIXED_, then each leaf of the taptree will consist of *either* a Schnorr based locking script or a SLH-DSA based locking script. A _MIXED_ tap tree with 5 leaves (aka: TOTAL_LEAF_COUNT) could be represented as follows: + image::images/tap_tree_mixed.png[t,300] + NOTE: The benefit of constructing a taptree with a mixed set of cryptography used as locking scripts in the leaves is articulated nicely in link:https://www.bitmex.com/blog/Taproot%20Quantum%20Spend%20Paths[this article from BitMex]. .. If you set _TAP_TREE_LOCK_TYPE=CONCATENATED_SCHNORR_AND_SLH_DSA_, then the locking script of your TapTree leaves will be secured using both SCHNORR and SLH-DSA cryptography in a concatenated / serial manner. Private keys for both SCHNORR and SLH-DSA will be needed when unlocking. A _CONCATENATED_SCHNORR_AND_SLH_DSA_ tap tree with 5 leaves (aka: TOTAL_LEAF_COUNT) could be represented as follows: + image::images/tap_tree_concatenated.png[p,300] . Set the tap leaf index to later use as the unlocking script (when spending) For example, to later spend from the 5th leaf of the tap tree: + [source,bash] ----- export LEAF_TO_SPEND_FROM=4 ----- . Generate a P2MR scripPubKey with multi-leaf taptree: + [source,bash] ----- export BITCOIN_ADDRESS_INFO=$( cargo run --example p2mr_construction ) \ && echo $BITCOIN_ADDRESS_INFO | jq -r . ----- + NOTE: In signet, you can expect a P2MR address that starts with the following prefix: `tb1z` . + [subs=+quotes] ++++
What just happened? The Rust based reference implementation for BIP-0360 is leveraged to construct a transaction with a P2MR UTXO as follows:
  • A configurable number of leaves are generated each with their own locking script.
  • Each of these leaves are added to a Huffman tree that sorts the leaves by weight.
  • The merkle root of the tree is calculated and subsequently used to generate the P2MR witness program and BIP0350 address.

++++ + The source code for the above logic is found in this project's source file: link:../src/lib.rs[src/lib.rs] . Only if you previously set `TAP_TREE_LOCK_TYPE=MIXED`, set the environment variable `SPENDING_LEAF_TYPE`. Valid values are `SHNORR_ONLY` or `SLH_DSA_ONLY` based on the type of locking script that was used in the leaf you will spend from later in this lab. The logs from the previous step tell you the appropriate value to set. For instance: + ----- NOTE: TAP_TREE_LOCK_TYPE=MIXED requires setting SPENDING_LEAF_TYPE when spending (based on leaf_script_type in output above) as follows: export SPENDING_LEAF_TYPE=SCHNORR_ONLY ----- . Fund this P2MR address using workshop's signet faucet .. In a browser tab, navigate to: link:http://faucet.bip360.org/[faucet.bip360.org]. .. Copy-n-paste the value of `bech32m_address` (found in the json response from the previous step) + image::images/faucet_1.png[] + Press the `Request` button. .. The faucet should allocate bitcoin to your address. + image::images/faucet_2.png[] .. Click on the link of your transaction id. This will take you a detailed view of the transaction. Scroll down to the the _Inputs & Outputs_ section of the transaction and identify the _vout_ index of funds sent to your _P2MR_ address. + image::images/funding_utxo_id.png[] .. Return back to your terminal and set a _FUNDING_UTXO_INDEX_ environment variable (used later to correctly identify funding UTXO when generating the spending tx) + [source,bash] ----- export FUNDING_UTXO_INDEX= ----- .. Return back to your browser tab at navigate to: link:https://signet.bip360.org[signet.bip360.org] and wait until a new block mines the transaction from the faucet that funded your P2MR address. + image::images/mempool_next_block.png[] . Set some env vars (for use in later steps in this workshop) based on previous json result: + [source,bash] ----- export MERKLE_ROOT=$( echo $BITCOIN_ADDRESS_INFO | jq -r '.taptree_return.tree_root_hex' ) \ && export LEAF_SCRIPT_PRIV_KEYS_HEX=$( echo $BITCOIN_ADDRESS_INFO | jq -r '.taptree_return.leaf_script_priv_keys_hex' ) \ && export LEAF_SCRIPT_HEX=$( echo $BITCOIN_ADDRESS_INFO | jq -r '.taptree_return.leaf_script_hex' ) \ && export CONTROL_BLOCK_HEX=$( echo $BITCOIN_ADDRESS_INFO | jq -r '.taptree_return.control_block_hex' ) \ && export FUNDING_SCRIPT_PUBKEY=$( echo $BITCOIN_ADDRESS_INFO | jq -r '.utxo_return.script_pubkey_hex' ) \ && export P2MR_ADDR=$( echo $BITCOIN_ADDRESS_INFO | jq -r '.utxo_return.bech32m_address' ) ----- . View tapscript used in target leaf of taptree: + [source,bash] ----- b-cli decodescript $LEAF_SCRIPT_HEX | jq -r '.asm' ----- + NOTE: If not using Schnorr crypto, this script commits to a Schnorr 32-byte x-only public key. If using SLH_DSA, this script commits to a 32-byte SLH-DSA pub key and a OP_SUCCESS127 (represented as `OP_SUBSTR`) opcode., If using SCHNORR + SLH_DSA, then you should see a locking script in the leaf similar to the following: + ----- 886fc1edb7a8a364da65aef57343de451c1449d8a6c5b766fe150667d50d3e80 OP_CHECKSIG 479f93fbd251863c3e3e72da6e26ea82f87313da13090de10e57eca1f8b5e0f3 OP_SUBSTR OP_BOOLAND OP_VERIFY ----- . view summary of all txs that have funded P2MR address + [source,bash] ----- export P2MR_DESC=$( b-cli getdescriptorinfo "addr($P2MR_ADDR)" | jq -r '.descriptor' ) \ && echo $P2MR_DESC \ && b-cli scantxoutset start '[{"desc": "'''$P2MR_DESC'''"}]' ----- + NOTE: You will likely have to wait a few minutes until a new block (containing the tx that funds your P2MR address) is mined. . grab txid of first tx with unspent funds: + [source,bash] ----- export FUNDING_TX_ID=$( b-cli scantxoutset start '[{"desc": "'''$P2MR_DESC'''"}]' | jq -r '.unspents[0].txid' ) \ && echo $FUNDING_TX_ID ----- . view details of funding UTXO to the P2MR address: + [source,bash] ----- export FUNDING_UTXO=$( b-cli getrawtransaction $FUNDING_TX_ID 1 | jq -r '.vout['''$FUNDING_UTXO_INDEX''']' ) \ && echo $FUNDING_UTXO | jq -r . ----- == Spend P2MR UTXO In the previous section, you created and funded a P2MR UTXO. That UTXO includes a leaf script locked with a key-pair (optionally based on PQC) known to you. In this section, you spend from that P2MR UTXO. Specifically, you will generate an appropriate _SigHash_ and sign it (to create a signature) using the known private key that unlocks the known leaf script of the P2MR UTXO. The target address type that you send funds to is: P2WPKH. . Determine value (in sats) of the funding P2MR utxo: + [source,bash] ----- export FUNDING_UTXO_AMOUNT_SATS=$(echo $FUNDING_UTXO | jq -r '.value' | awk '{printf "%.0f", $1 * 100000000}') \ && echo $FUNDING_UTXO_AMOUNT_SATS ----- . Referencing the funding tx (via $FUNDING_TX_ID and $FUNDING_UTXO_INDEX), create the spending tx: + [source,bash] ----- export SPEND_DETAILS=$( cargo run --example p2mr_spend ) ----- + [subs=+quotes] ++++
What just happened? The Rust based reference implementation for BIP-0360 is leveraged to construct a transaction that spends from the P2MR UTXO as follows:
  • Create a transaction template (aka: SigHash) that serves as the message to be signed.
  • Using the known private key and the SigHash, create a signature that is capable of unlocking one of the leaf scripts of the P2MR tree.
  • Add this signature to the witness section of the transaction.

++++ + The source code for the above logic is found in this project's source file: link:../src/lib.rs[src/lib.rs] . Set environment variables passed to _bitcoin-cli_ when spending: + [source,bash] ----- export RAW_P2MR_SPEND_TX=$( echo $SPEND_DETAILS | jq -r '.tx_hex' ) \ && echo "RAW_P2MR_SPEND_TX = $RAW_P2MR_SPEND_TX" \ && export SIG_HASH=$( echo $SPEND_DETAILS | jq -r '.sighash' ) \ && echo "SIG_HASH = $SIG_HASH" \ && export SIG_BYTES=$( echo $SPEND_DETAILS | jq -r '.sig_bytes' ) \ && echo "SIG_BYTES = $SIG_BYTES" ----- . Inspect the spending tx: + [source,bash] ----- b-cli decoderawtransaction $RAW_P2MR_SPEND_TX ----- + Pay particular attention to the `vin.txinwitness` field. The following depicts the elements of a P2MR witness stack. + image::images/p2mr_witness.png[] + Do the three elements (script input, script and control block) of the witness stack for this _script path spend_ correspond ? What do you observe as the first byte of the `control block` element ? . Test standardness of the spending tx by sending to local mempool of P2MR enabled Bitcoin Core: + [source,bash] ----- b-cli testmempoolaccept '["'''$RAW_P2MR_SPEND_TX'''"]' ----- . Submit tx: + [source,bash] ----- export P2MR_SPENDING_TX_ID=$( b-cli sendrawtransaction $RAW_P2MR_SPEND_TX ) \ && echo $P2MR_SPENDING_TX_ID ----- + NOTE: Should return same tx id as was included in $RAW_P2MR_SPEND_TX == Mine P2MR Spend TX . View tx in mempool: + [source,bash] ----- b-cli getrawtransaction $P2MR_SPENDING_TX_ID 1 ----- + NOTE: There will not yet be a field `blockhash` in the response. . Monitor the mempool.space instance at link:http://signet.bip360.org[signet.bip360.org] until a new block is mined. . While still in the mempool.space instance at link:http://signet.bip360.org[signet.bip360.org], lookup your tx (denoted by: $P2MR_SPENDING_TX_ID ) in the top-right search bar: + image::images/mempool_spending_tx_1.png[] + Click on the `Details` button at the top-right of the `Inputs & Outputs` section. .. Study the elements of the `Witness. Approximately how large is each element of the witness stack? .. View the values of the `Previous output script` and `Previous output type` fields: + image::images/mempool_spending_tx_2.png[] . Obtain `blockhash` field of mined tx: + [source,bash] ----- export BLOCK_HASH=$( b-cli getrawtransaction $P2MR_SPENDING_TX_ID 1 | jq -r '.blockhash' ) \ && echo $BLOCK_HASH ----- . View txs in block: + [source,bash] ----- b-cli getblock $BLOCK_HASH | jq -r .tx ----- + You should see your tx (as per $P2MR_SPENDING_TX_ID) in the list. + Congratulations!! You have created, funded and spent from a P2MR address. == Appendix [[build_p2mr]] === Build P2MR / PQC Enabled Bitcoin Core *FOR THE PURPOSE OF THE WORKSHOP, YOU CAN IGNORE THIS SECTION* The link:https://github.com/jbride/bitcoin/tree/p2mr[p2mr branch] of bitcoin core is needed. Build instructions for the `p2mr` branch are the same as `master` and is documented link:https://github.com/bitcoin/bitcoin/blob/master/doc/build-unix.md[here]. As such, the following is an example series of steps (on a Fedora 42 host) to compile and run the `p2mr` branch of bitcoin core: . Set BITCOIN_SOURCE_DIR + ----- export BITCOIN_SOURCE_DIR=/path/to/root/dir/of/cloned/bitcoin/source ----- . build + ----- cmake -B build \ -DWITH_ZMQ=ON \ -DCMAKE_EXPORT_COMPILE_COMMANDS=ON \ -DBUILD_BENCH=ON \ -DBUILD_DAEMON=ON \ -DSANITIZERS=address,undefined cmake --build build -j$(nproc) ----- . run bitcoind in signet mode: + ----- ./build/bin/bitcoind -daemon=0 -signet=1 -txindex -prune=0 ----- + NOTE: If running in `signet`, your bitcoin core will need to be configured with the `signetchallenge` property. link:https://edil.com.br/blog/creating-a-custom-bitcoin-signet[This workshop] provides a nice overview of the topic. === libbitcoinpqc Rust bindings *FOR THE PURPOSE OF THE WORKSHOP, YOU CAN IGNORE THIS SECTION* The `p2mr-pqc` branch of this project includes a dependency on the link:https://crates.io/crates/libbitcoinpqc[libbitcoinpqc crate]. libbitcoinpqc contains native code (C/C++/ASM) and is made available to Rust projects via Rust bindings. This C/C++/ASM code is provided in the libbitcoinpqc crate as source code (not prebuilt binaries). Subsequently, the `Cargo` utility needs to build this libbitcoinpqc C native code on your local machine. You will need to have C development related libraries installed on your local machine. Every developer or CI machine building `p2mr-ref` must have cmake and a C toolchain installed locally. ==== Linux . Debian / Ubuntu + ----- sudo apt update sudo apt install cmake build-essential clang libclang-dev ----- . Fedora / RHEL + ----- sudo dnf5 update sudo dnf5 install cmake make gcc gcc-c++ clang clang-libs llvm-devel ----- ================================================ FILE: bip-0360/ref-impl/rust/docs/p2tr-end-to-end.adoc ================================================ :scrollbar: :data-uri: :toc2: :linkattrs: = P2TR End-to-End Tutorial :numbered: This tutorial is inspired from the link:https://learnmeabitcoin.com/technical/upgrades/taproot/#example-3-script-path-spend-signature[script-path-spend-signature] example of the _learnmeabitcoin_ tutorial. It is customized to create, fund and spend from a P2TR UTXO to a P2WPKH address. Execute in Bitcoin Core `regtest` mode. == Pre-reqs === Bitcoin Core The link:https://github.com/jbride/bitcoin/tree/p2mr-pqc[p2mr branch] of bitcoin core is needed. Build instructions for the `p2mr` branch are the same as `master` and is documented link:https://github.com/bitcoin/bitcoin/blob/master/doc/build-unix.md[here]. As such, the following is an example series of steps (on a Fedora 42 host) to compile and run the `p2mr` branch of bitcoin core: . build + ----- $ cmake -B build \ -DWITH_ZMQ=ON \ -DCMAKE_EXPORT_COMPILE_COMMANDS=ON \ -DBUILD_BENCH=ON \ -DSANITIZERS=address,undefined $ cmake --build build -j$(nproc) ----- . run in `regtest` mode + ----- $ ./build/bin/bitcoind -daemon=0 -regtest=1 -txindex ----- === Shell Environment . *b-reg* command line alias: + Configure an alias to the `bitcoin-cli` command that connects to your customized bitcoin-core node running in `regtest` mode. . *jq*: ensure json parsing utility is installed and available via your $PATH. . *awk* : standard utility for all Linux distros (often packaged as `gawk`). === Bitcoin Core Wallet This tutorial assumes that a bitcoin core wallet is available. For example, the following would be sufficient: ----- $ export W_NAME=regtest \ && export WPASS=regtest $ b-reg -named createwallet \ wallet_name=$W_NAME \ descriptors=true \ passphrase="$WPASS" \ load_on_startup=true ----- == Fund P2TR UTXO . OPTIONAL: Define number of leaves in tap tree as well as the tap leaf to later use as the unlocking script: + ----- $ export TOTAL_LEAF_COUNT=5 \ && export LEAF_TO_SPEND_FROM=4 ----- + NOTE: Defaults are 4 leaves with the first leaf (leaf 0 ) as the script to later use as the unlocking script. . Generate a P2TR scripPubKey with multi-leaf taptree: + ----- $ export BITCOIN_NETWORK=regtest \ && export BITCOIN_ADDRESS_INFO=$( cargo run --example p2tr_construction ) \ && echo $BITCOIN_ADDRESS_INFO | jq -r . ----- + NOTE: In `regtest`, you can expect a P2TR address that starts with: `bcrt1q` . + NOTE: In the context of P2TR, the _tree_root_hex_ from the response is in reference to the _merkle_root_ used in this tutorial. . Set some env vars (for use in later steps in this tutorial) based on previous result: + ----- $ export MERKLE_ROOT=$( echo $BITCOIN_ADDRESS_INFO | jq -r '.taptree_return.tree_root_hex' ) \ && export LEAF_SCRIPT_PRIV_KEYS_HEX=$( echo $BITCOIN_ADDRESS_INFO | jq -r '.taptree_return.leaf_script_priv_keys_hex' ) \ && export LEAF_SCRIPT_HEX=$( echo $BITCOIN_ADDRESS_INFO | jq -r '.taptree_return.leaf_script_hex' ) \ && export CONTROL_BLOCK_HEX=$( echo $BITCOIN_ADDRESS_INFO | jq -r '.taptree_return.control_block_hex' ) \ && export FUNDING_SCRIPT_PUBKEY=$( echo $BITCOIN_ADDRESS_INFO | jq -r '.utxo_return.script_pubkey_hex' ) \ && export P2TR_ADDR=$( echo $BITCOIN_ADDRESS_INFO | jq -r '.utxo_return.bech32m_address' ) ----- . View tapscript used in target leaf of taptree: + ----- $ b-reg decodescript $LEAF_SCRIPT_HEX | jq -r '.asm' ----- + NOTE: Notice that this script commits to a Schnorr 32-byte x-only public key. . fund this P2TR address with the coinbase reward of a newly generated block: + ----- $ export COINBASE_REWARD_TX_ID=$( b-reg -named generatetoaddress 1 $P2TR_ADDR 5 | jq -r '.[]' ) \ && echo $COINBASE_REWARD_TX_ID ----- + NOTE: Sometimes Bitcoin Core may not hit a block (even on regtest). If so, just try the above command again. . view summary of all txs that have funded P2TR address + ----- $ export P2TR_DESC=$( b-reg getdescriptorinfo "addr($P2TR_ADDR)" | jq -r '.descriptor' ) \ && echo $P2TR_DESC \ && b-reg scantxoutset start '[{"desc": "'''$P2TR_DESC'''"}]' ----- . grab txid of first tx with unspent funds: + ----- $ export FUNDING_TX_ID=$( b-reg scantxoutset start '[{"desc": "'''$P2TR_DESC'''"}]' | jq -r '.unspents[0].txid' ) \ && echo $FUNDING_TX_ID ----- . Set FUNDING_UTXO_INDEX env var (used later to correctly identify funding UTXO when generating the spending tx) + ----- $ export FUNDING_UTXO_INDEX=0 ----- . view details of funding UTXO to the P2TR address: + ----- $ export FUNDING_UTXO=$( b-reg getrawtransaction $FUNDING_TX_ID 1 | jq -r '.vout['''$FUNDING_UTXO_INDEX''']' ) \ && echo $FUNDING_UTXO | jq -r . ----- + NOTE: the above only works when Bitcoin Core is started with the following arg: -txindex == Spend P2TR UTXO . Determine value (in sats) of funding utxo: + ----- $ export FUNDING_UTXO_AMOUNT_SATS=$(echo $FUNDING_UTXO | jq -r '.value' | awk '{printf "%.0f", $1 * 100000000}') \ && echo $FUNDING_UTXO_AMOUNT_SATS ----- . Generate additional blocks. + This is necessary if you have only previously generated less than 100 blocks. + ----- $ b-reg -generate 110 ----- + Otherwise, you may see an error from bitcoin core such as the following when attempting to spend: + _bad-txns-premature-spend-of-coinbase, tried to spend coinbase at depth 1_ . Referencing the funding tx (via $FUNDING_TX_ID and $FUNDING_UTXO_INDEX), create the spending tx: + ----- $ export SPEND_DETAILS=$( cargo run --example p2tr_spend ) $ export RAW_P2TR_SPEND_TX=$( echo $SPEND_DETAILS | jq -r '.tx_hex' ) \ && echo "RAW_P2TR_SPEND_TX = $RAW_P2TR_SPEND_TX" \ && export SIG_HASH=$( echo $SPEND_DETAILS | jq -r '.sighash' ) \ && echo "SIG_HASH = $SIG_HASH" \ && export SIG_BYTES=$( echo $SPEND_DETAILS | jq -r '.sig_bytes' ) \ && echo "SIG_BYTES = $SIG_BYTES" ----- . Inspect the spending tx: + ----- $ b-reg decoderawtransaction $RAW_P2TR_SPEND_TX ----- . Test standardness of the spending tx by sending to local mempool of p2tr enabled Bitcoin Core: ----- $ b-reg testmempoolaccept '["'''$RAW_P2TR_SPEND_TX'''"]' ----- . Submit tx: + ----- $ export P2TR_SPENDING_TX_ID=$( b-reg sendrawtransaction $RAW_P2TR_SPEND_TX ) \ && echo $P2TR_SPENDING_TX_ID ----- + NOTE: Should return same tx id as was included in $RAW_P2TR_SPEND_TX == Mine P2TR Spend TX . View tx in mempool: + ----- $ b-reg getrawtransaction $P2TR_SPENDING_TX_ID 1 ----- + NOTE: There will not yet be a field `blockhash` in the response. . Mine 1 block: + ----- $ b-reg -generate 1 ----- . Obtain `blockhash` field of mined tx: + ----- $ export BLOCK_HASH=$( b-reg getrawtransaction $P2TR_SPENDING_TX_ID 1 | jq -r '.blockhash' ) \ && echo $BLOCK_HASH ----- . View tx in block: + ----- $ b-reg getblock $BLOCK_HASH | jq -r .tx ----- == TO-DO ================================================ FILE: bip-0360/ref-impl/rust/docs/quantum_root_tap_tree.txt ================================================ ┌───────────────────────┐ │ tapleaf Merkle root │ │ │ └───────────────────────┘ | ┌───────────────────────┐ │ 5 tagged_hash │ │ QuantumRoot │ └───────────|───────────┘ ┌───────────|───────────┐ ┌───────────────────────────────►│ 4 tagged_hash ◄─────────────────────┐ │ │ TapBranch │ │ │ └───────────────────────┘ │ │ │ │ │ │ │ │ │ │ │ │ ┌─────────────┼───────────┐ │ │ 3 tagged_hash │ │ ┌──►│ TapBranch ◄───────┐ │ │ └─────────────────────────┘ │ │ │ │ │ │ │ ┌───────────┼────────────┐ ┌───────┼────────┐ │ ┌─────►│ 2 tagged_hash ◄────┐ ┌─────►│ 2 tagged_hash ◄────┐ │ │ │ TapBranch │ │ │ │ TapBranch │ │ │ │ └────────────────────────┘ │ │ └────────────────┘ │ │ │ │ │ │ │ │ │ ┌─────┼────────┐ ┌───────|───-─┐ ┌──────┴──────┐ ┌───┼──────────┐ ┌──────────┼──┐ │ 1 tagged_hash│ │1 tagged_hash│ │1 tagged_hash│ │1 tagged_hash │ │1 tagged_hash│ │ Tapleaf │ │ Tapleaf │ │ Tapleaf │ │ Tapleaf │ │ Tapleaf │ └──────────────┘ └─────────────┘ └─────────────┘ └──▲───────────┘ └──────▲──────┘ ▲ ▲ ▲ │ │ │ │ │ version | A script version | B script version | C script version | D script version|E script ================================================ FILE: bip-0360/ref-impl/rust/docs/stack_element_size_performance_tests.adoc ================================================ :scrollbar: :data-uri: :toc2: :linkattrs: = Stack Element Size Performance Tests :numbered: == Overview BIP-0360 proposes an increase in stack element size from current 520 bytes (v0.29) to 8kb. Subsequently, there is a need to determine the performance and stability related consequences of doing so. == Regression Tests The following regression tests failed with `MAX_SCRIPT_ELEMENT_SIZE` set to 8000 . [cols="1,1,2"] |=== |feature_taproot.py | line 1338 | Missing error message 'Push value size limit exceeded' from block response 'mandatory-script-verify-flag-failed (Stack size must be exactly one after execution)' |p2p_filter.py | lines 130-132 | Check that too large data element to add to the filter is rejected |p2p_segwit.py | lines 1047-1049 | mandatory-script-verify-flag-failed (Push value size limit exceeded) |rpc_createmultisig.py | lines 75-75 | No exception raised: redeemScript exceeds size limit: 684 > 520" |=== **Analysis** These 4 tests explicitly test for a stack element size of 520 and are expected to fail with a stack element size of 8Kb. Subsequently, no further action needed. == Performance Tests === OP_SHA256 The following Bitcoin script is used to conduct this performance test: ----- OP_SHA256 OP_DROP OP_1 ----- When executed, this script adds the pre-image array of arbitrary data to the stack. Immediately after, a SHA256 hash function pops the pre-image array off the stack, executes a hash and adds the result to the top of the stack. The `OP_DROP` operation removes the hash result from the stack. ==== Results Summary [cols="3,1,1,1,1,1,1,1,1,1", options="header"] |=== | Stack Element Size (Bytes) | ns/op | op/s | err% | ins/op | cyc/op | IPC | bra/op |miss% | total | 1 | 637.28 | 1,569,165.30 | 0.3% | 8,736.00 | 1,338.55 | 6.526 | 832.00 | 0.0% | 5.53 | 64 | 794.85 | 1,258,098.46 | 0.4% | 11,107.00 | 1,666.92 | 6.663 | 827.00 | 0.0% | 5.61 | 65 | 831.95 | 1,201,996.30 | 0.5% | 11,144.00 | 1,698.26 | 6.562 | 841.00 | 0.0% | 5.53 | 100 | 794.82 | 1,258,139.86 | 0.2% | 11,139.00 | 1,673.89 | 6.655 | 837.00 | 0.0% | 5.50 | 520 | 1,946.67 | 513,697.88 | 0.2% | 27,681.00 | 4,095.57 | 6.759 | 885.00 | 0.0% | 5.50 | 8000 | 20,958.63 | 47,713.05 | 2.7% | 304,137.02 | 43,789.86 | 6.945 | 1,689.02 | 0.4% | 5.63 |=== **Analysis** The following observations are made from the performance test: . **Performance Scaling**: The increase from 520 bytes to 8000 bytes (15.4x size increase) results in approximately 9.8x performance degradation (19,173 ns/op vs 1,947 ns/op). This represents sub-linear scaling, which suggests the implementation handles large data efficiently. . **Instruction Count Scaling**: Instructions per operation increase from 27,681 to 285,220 (10.3x increase), closely matching the performance degradation, indicating the bottleneck is primarily computational rather than memory bandwidth. . **Throughput Impact**: Operations per second decrease from 513,698 op/s to 52,158 op/s, representing a 9.8x reduction in throughput. . **Cache Efficiency**: The IPC (Instructions Per Cycle) remains relatively stable (6.759 to 7.094), suggesting good CPU pipeline utilization despite the increased data size. . **Memory Access Patterns**: The branch mis-prediction rate increases slightly (0.0% to 0.4%), indicating minimal impact on branch prediction accuracy. **key** [cols="1,6", options="header"] |=== | Metric | Description | ns/op | Nanoseconds per operation - average time it takes to complete one benchmark iteration | op/s | Operations per second - throughput rate showing how many benchmark iterations can be completed per second | err% | Error percentage - statistical margin of error in the measurement, indicating the reliability of the benchmark results | ins/op | Instructions per operation - the number of CPU instructions executed for each benchmark iteration | cyc/op | CPU cycles per operation - the number of CPU clock cycles consumed for each benchmark iteration | IPC | Instructions per cycle - the ratio of instructions executed per CPU cycle, indicating CPU efficiency and pipeline utilization | bra/op | Branches per operation - the number of conditional branch instructions executed for each benchmark iteration | miss% | Branch misprediction percentage - the rate at which the CPU incorrectly predicts branch outcomes, causing pipeline stalls | total | Total benchmark time - the total wall-clock time spent running the entire benchmark in seconds |=== ==== Detailed Results ===== Stack Element Size = 1 Byte [cols="2,1,1,1,1,1,1,1,1", options="header"] |=== |ns/op |op/s |err% |ins/op |cyc/op |IPC |bra/op |miss% |total |637.28 |1,569,165.30 |0.3% |8,736.00 |1,338.55 |6.526 |832.00 |0.0% |5.53 |=== ===== Stack Element Size = 64 Bytes [cols="2,1,1,1,1,1,1,1,1", options="header"] |=== | ns/op | op/s | err% | ins/op | cyc/op | IPC | bra/op | miss% | total | 794.85 | 1,258,098.46 | 0.4% | 11,107.00 | 1,666.92 | 6.663 | 827.00 | 0.0% | 5.61 |=== ====== Explanation Even though 64 bytes doesn't require padding (it's exactly one SHA256 block), the ins/op still increases from 8,736 to 11,107 instructions. Here's why: . Data Movement Overhead * 1 byte: Minimal data to copy into the SHA256 processing buffer * 64 bytes: 64x more data to move from the witness stack into the SHA256 input buffer * Memory copying operations add instructions . SHA256 State Initialization * 1 byte: The 1-byte input gets padded to 64 bytes internally, but the padding is mostly zeros * 64 bytes: All 64 bytes are actual data that needs to be processed * The SHA256 algorithm may have different code paths for handling "real" data vs padded data . Memory Access Patterns * 1 byte: Single byte access, likely cache-friendly * 64 bytes: Sequential access to 64 bytes, potentially different memory access patterns * May trigger different CPU optimizations or cache behavior . Bit Length Processing * 1 byte: The SHA256 algorithm needs to set the bit length field (8 bits) * 64 bytes: The bit length field is 512 bits * Different bit length values may cause different code paths in the SHA256 implementation . Loop Unrolling and Optimization * 1 byte: Compiler might optimize the single-block case differently * 64 bytes: May use different loop structures or optimization strategies * The SHA256 implementation might have specialized code paths for different input sizes . Witness Stack Operations * 1 byte: Small witness element, minimal stack manipulation * 64 bytes: Larger witness element, more complex stack operations * The Bitcoin script interpreter has to handle larger data on the stack The increase from 8,736 to 11,107 instructions (~27% increase) suggests that even without padding overhead, the additional data movement and processing of "real" data vs padded data adds significant instruction count. This is a good example of how seemingly small changes in input size can affect the underlying implementation's code paths and optimization strategies. ===== Stack Element Size = 65 Bytes 1 byte more than the SHA256 _block_ size [cols="2,1,1,1,1,1,1,1,1", options="header"] |=== |ns/op |op/s |err% |ins/op |cyc/op |IPC |bra/op | miss% | total | 831.95 | 1,201,996.30 |0.5% |11,144.00 |1,698.26 | 6.562 |841.00 | 0.0% | 5.53 |=== ===== Stack Element Size = 100 Bytes [cols="2,1,1,1,1,1,1,1,1", options="header"] |=== |ns/op |op/s |err% |ins/op |cyc/op |IPC |bra/op | miss% | total | 794.82 | 1,258,139.86 | 0.2% | 11,139.00 | 1,673.89 | 6.655 | 837.00 | 0.0% | 5.50 |=== ===== Stack Element Size = 520 Bytes [cols="2,1,1,1,1,1,1,1,1", options="header"] |=== |ns/op |op/s |err% |ins/op |cyc/op |IPC |bra/op | miss% | total | 1,946.67 | 513,697.88 | 0.2% | 27,681.00 | 4,095.57 | 6.759 | 885.00 | 0.0% | 5.50 |=== ===== Stack Element Size = 8000 Bytes [cols="2,1,1,1,1,1,1,1,1", options="header"] |=== |ns/op |op/s |err% |ins/op |cyc/op |IPC |bra/op | miss% | total | 20,958.63 | 47,713.05 | 2.7% | 304,137.02 | 43,789.86 | 6.945 | 1,689.02 | 0.4% | 5.63 |=== === OP_DUP OP_SHA256 NOTE: This test is likely irrelevant as per latest BIP-0360: _To prevent OP_DUP from creating an 8 MB stack by duplicating stack elements larger than 520 bytes we define OP_DUP to fail on stack elements larger than 520 bytes_. This test builds off the previous (involving the hashing of large stack element data) by duplicating that stack element data. The following Bitcoin script is used to conduct this performance test: ----- OP_DUP OP_SHA256 OP_DROP OP_1 ----- When executed, this script adds the pre-image array of arbitrary data to the stack. Immediately after, a `OP_DUP` operation duplicates the pre-image array on the stack. Then, a SHA256 hash function pops the pre-image array off the stack, executes a hash and adds the result to the top of the stack. The `OP_DROP` operation removes the hash result from the stack. ==== Results Summary [cols="3,1,1,1,1,1,1,1,1,1", options="header"] |=== | Stack Element Size (Bytes) | ns/op | op/s | err% | ins/op | cyc/op | IPC | bra/op |miss% | total | 1 | 714.83 | 1,398,937.33 | 0.7% | 9,548.00 | 1,488.22 | 6.416 | 1,012.00 | 0.0% | 5.57 | 64 | 858.44 | 1,164,905.19 | 0.4% | 11,911.00 | 1,800.87 | 6.614 | 999.00 | 0.0% | 5.11 | 65 | 868.40 | 1,151,539.31 | 0.8% | 11,968.00 | 1,814.31 | 6.596 | 1,019.00 | 0.0% | 5.56 | 100 | 864.33 | 1,156,966.91 | 0.4% | 11,963.00 | 1,809.16 | 6.612 | 1,015.00 | 0.0% | 5.49 | 520 | 2,036.64 | 491,005.94 | 0.7% | 28,615.00 | 4,266.27 | 6.707 | 1,073.00 | 0.0% | 5.52 | 8000 | 20,883.10 | 47,885.61 | 0.2% | 306,887.04 | 43,782.35 | 7.009 | 2,089.02 | 0.3% | 5.53 |=== ==== Analysis The following observations are made from the performance test (in comparison to the `OP_SHA256` test): . OP_DUP Overhead: The OP_DUP operation adds overhead by duplicating the stack element, which requires: * Memory allocation for the duplicate * Data copying from the original to the duplicate * Additional stack manipulation . Size-Dependent Impact on ns/op: * For small elements (1-100 bytes): Significant overhead (4.4% to 12.2%) * For medium elements (520 bytes): Moderate overhead (4.6%) * For large elements (8000 bytes): Negligible difference (-0.4%) . Instruction Count Impact: * 8000 bytes: 304,137 → 306,887 instructions (+2,750 instructions) * The additional instructions for OP_DUP are relatively small compared to the SHA256 computation . Memory Operations: + The OP_DUP operation primarily affects memory operations rather than computational complexity. This explains why the impact diminishes with larger data sizes where SHA256 computation dominates the performance. This analysis shows that the OP_DUP operation has a measurable but manageable performance impact, especially for larger stack elements where the computational overhead of SHA256 dominates the overall execution time. === Procedure * Testing is done using functionality found in the link:https://github.com/jbride/bitcoin/tree/p2mr-pqc[p2mr branch] of Bitcoin Core. * Compilation of Bitcoin Core is done using the following `cmake` flags: + ----- $ cmake \ -B build \ -DWITH_ZMQ=ON \ -DCMAKE_EXPORT_COMPILE_COMMANDS=ON \ -DBUILD_BENCH=ON $ cmake --build build -j$(nproc) ----- * Bench tests are conducted similar to the following : + ----- $ export PREIMAGE_SIZE_BYTES=8000 $ ./build/bin/bench_bitcoin --filter=VerifySHA256Bench -min-time=5000 ----- == Failure Analysis Goals: * Measure stack memory usage to detect overflows or excessive stack growth. * Monitor heap memory usage to identify increased allocations or leaks caused by larger elements. * Detect memory errors (e.g., invalid reads/writes, use-after-free) that might arise from modified stack handling. * Assess performance impacts (e.g., memory allocation overhead) in critical paths like transaction validation. === Memory Errors AddressSanitizer is a fast, compiler-based tool (available in GCC/Clang) for detecting memory errors with lower overhead than Valgrind. ==== Results No memory errors or leaks were revealed by AddressSanitizer when running the `OP_SHA256` bench test for 30 minutes. ==== Procedure AddressSanitizer is included with Clang/LLVM . Compilation of Bitcoin Core is done using the following `cmake` flags: + ----- $ cmake -B build \ -DWITH_ZMQ=ON \ -DBUILD_BENCH=ON \ -DCMAKE_C_COMPILER=clang \ -DCMAKE_CXX_COMPILER=clang++ \ -DCMAKE_EXPORT_COMPILE_COMMANDS=ON \ -DSANITIZERS=address,undefined $ cmake --build build -j$(nproc) ----- . Check that ASan is statically linked to the _bench_bitcoin_ executable: + ----- $ nm build/bin/bench_bitcoin | grep asan | more 0000000000148240 T __asan_address_is_poisoned 00000000000a2fe6 t __asan_check_load_add_16_R13 ... 000000000316c828 b _ZZN6__asanL18GlobalsByIndicatorEmE20globals_by_indicator 0000000003170ccc b _ZZN6__asanL7AsanDieEvE9num_calls ----- . Set the following environment variable: + ----- $ export ASAN_OPTIONS="halt_on_error=0:detect_leaks=1:log_path=/tmp/asan_logs/asan" ----- + Doing so ensures that _address sanitizer_ : .. avoids halting on the first error .. is enable memory leak detection .. writes ASAN related logs to a specified directory == Test Environment * Fedora 42 * 8 cores (Intel(R) Core(TM) i7-8665U CPU @ 1.90GHz) * 32 GB RAM * OS settings: + ----- $ ulimit -a real-time non-blocking time (microseconds, -R) unlimited core file size (blocks, -c) unlimited data seg size (kbytes, -d) unlimited scheduling priority (-e) 0 file size (blocks, -f) unlimited pending signals (-i) 126896 max locked memory (kbytes, -l) 8192 max memory size (kbytes, -m) unlimited open files (-n) 1024 pipe size (512 bytes, -p) 8 POSIX message queues (bytes, -q) 819200 real-time priority (-r) 0 stack size (kbytes, -s) 8192 cpu time (seconds, -t) unlimited max user processes (-u) 126896 virtual memory (kbytes, -v) unlimited file locks (-x) unlimited ----- == Notes . test with different thread stack sizes (ie: ulimit -s xxxx ) ================================================ FILE: bip-0360/ref-impl/rust/examples/p2mr-end-to-end.sh ================================================ export BITCOIN_SOURCE_DIR=$HOME/bitcoin export W_NAME=anduro export USE_PQC=false export TOTAL_LEAF_COUNT=5 export LEAF_TO_SPEND_FROM=4 b-cli -named createwallet \ wallet_name=$W_NAME \ descriptors=true \ load_on_startup=true export BITCOIN_ADDRESS_INFO=$( cargo run --example p2mr_construction ) \ && echo $BITCOIN_ADDRESS_INFO | jq -r . export QUANTUM_ROOT=$( echo $BITCOIN_ADDRESS_INFO | jq -r '.taptree_return.tree_root_hex' ) \ && export LEAF_SCRIPT_PRIV_KEY_HEX=$( echo $BITCOIN_ADDRESS_INFO | jq -r '.taptree_return.leaf_script_priv_key_hex' ) \ && export LEAF_SCRIPT_HEX=$( echo $BITCOIN_ADDRESS_INFO | jq -r '.taptree_return.leaf_script_hex' ) \ && export CONTROL_BLOCK_HEX=$( echo $BITCOIN_ADDRESS_INFO | jq -r '.taptree_return.control_block_hex' ) \ && export FUNDING_SCRIPT_PUBKEY=$( echo $BITCOIN_ADDRESS_INFO | jq -r '.utxo_return.script_pubkey_hex' ) \ && export P2MR_ADDR=$( echo $BITCOIN_ADDRESS_INFO | jq -r '.utxo_return.bech32m_address' ) b-cli decodescript $LEAF_SCRIPT_HEX | jq -r '.asm' export COINBASE_REWARD_TX_ID=$( b-cli -named generatetoaddress 1 $P2MR_ADDR 5 | jq -r '.[]' ) \ && echo $COINBASE_REWARD_TX_ID export P2MR_DESC=$( b-cli getdescriptorinfo "addr($P2MR_ADDR)" | jq -r '.descriptor' ) \ && echo $P2MR_DESC \ && b-cli scantxoutset start '[{"desc": "'''$P2MR_DESC'''"}]' ================================================ FILE: bip-0360/ref-impl/rust/examples/p2mr_construction.rs ================================================ use p2mr_ref::{create_p2mr_utxo, create_p2mr_multi_leaf_taptree, tap_tree_lock_type}; use p2mr_ref::data_structures::{UtxoReturn, TaptreeReturn, ConstructionReturn, LeafScriptType}; use std::env; use log::{info, error}; // Inspired by: https://learnmeabitcoin.com/technical/upgrades/taproot/#example-3-script-path-spend-signature fn main() -> ConstructionReturn { let _ = env_logger::try_init(); // Use try_init to avoid reinitialization error let tap_tree_lock_type = tap_tree_lock_type(); info!("tap_tree_lock_type: {:?}", tap_tree_lock_type); let taptree_return: TaptreeReturn = create_p2mr_multi_leaf_taptree(); let p2mr_utxo_return: UtxoReturn = create_p2mr_utxo(taptree_return.clone().tree_root_hex); // Alert user about SPENDING_LEAF_TYPE requirement when using MIXED mode if tap_tree_lock_type == LeafScriptType::Mixed { info!("NOTE: TAP_TREE_LOCK_TYPE=MIXED requires setting SPENDING_LEAF_TYPE when spending (based on leaf_script_type in output above) as follows:"); info!(" export SPENDING_LEAF_TYPE={}", taptree_return.leaf_script_type); } return ConstructionReturn { taptree_return: taptree_return, utxo_return: p2mr_utxo_return, }; } ================================================ FILE: bip-0360/ref-impl/rust/examples/p2mr_spend.rs ================================================ use p2mr_ref::{ pay_to_p2wpkh_tx, verify_schnorr_signature_via_bytes, verify_slh_dsa_via_bytes, tap_tree_lock_type }; use p2mr_ref::data_structures::{SpendDetails, LeafScriptType}; use std::env; use log::{info, error}; // Inspired by: https://learnmeabitcoin.com/technical/upgrades/taproot/#example-3-script-path-spend-signature fn main() -> SpendDetails { let _ = env_logger::try_init(); // Use try_init to avoid reinitialization error // FUNDING_TX_ID environment variable is required let funding_tx_id: String = env::var("FUNDING_TX_ID") .unwrap_or_else(|_| { error!("FUNDING_TX_ID environment variable is required but not set"); std::process::exit(1); }); let funding_tx_id_bytes: Vec = hex::decode(funding_tx_id.clone()).unwrap(); // FUNDING_UTXO_AMOUNT_SATS environment variable is required let funding_utxo_amount_sats: u64 = env::var("FUNDING_UTXO_AMOUNT_SATS") .unwrap_or_else(|_| { error!("FUNDING_UTXO_AMOUNT_SATS environment variable is required but not set"); std::process::exit(1); }) .parse::() .unwrap_or_else(|_| { error!("FUNDING_UTXO_AMOUNT_SATS must be a valid u64 integer"); std::process::exit(1); }); // The input index of the funding tx // Allow override via FUNDING_UTXO_INDEX environment variable let funding_utxo_index: u32 = env::var("FUNDING_UTXO_INDEX") .ok() .and_then(|s| s.parse::().ok()) .unwrap_or(0); info!("Funding tx id: {}, utxo index: {}", funding_tx_id, funding_utxo_index); // FUNDING_SCRIPT_PUBKEY environment variable is required let funding_script_pubkey_bytes: Vec = env::var("FUNDING_SCRIPT_PUBKEY") .map(|s| hex::decode(s).unwrap()) .unwrap_or_else(|_| { error!("FUNDING_SCRIPT_PUBKEY environment variable is required but not set"); std::process::exit(1); }); let control_block_bytes: Vec = env::var("CONTROL_BLOCK_HEX") .map(|s| hex::decode(s).unwrap()) .unwrap_or_else(|_| { error!("CONTROL_BLOCK_HEX environment variable is required but not set"); std::process::exit(1); }); info!("P2MR control block size: {}", control_block_bytes.len()); // TAP_TREE_LOCK_TYPE environment variable is required to determine key structure let leaf_script_type: LeafScriptType = tap_tree_lock_type(); info!("leaf_script_type: {:?}", leaf_script_type); // For Mixed trees, we need to determine the actual leaf type via SPENDING_LEAF_TYPE let effective_leaf_type: LeafScriptType = if leaf_script_type == LeafScriptType::Mixed { match env::var("SPENDING_LEAF_TYPE") { Ok(value) => match value.as_str() { "SCHNORR_ONLY" => { info!("SPENDING_LEAF_TYPE: SCHNORR_ONLY"); LeafScriptType::SchnorrOnly }, "SLH_DSA_ONLY" => { info!("SPENDING_LEAF_TYPE: SLH_DSA_ONLY"); LeafScriptType::SlhDsaOnly }, _ => { error!("Invalid SPENDING_LEAF_TYPE '{}'. Must be SCHNORR_ONLY or SLH_DSA_ONLY", value); std::process::exit(1); } }, Err(_) => { error!("SPENDING_LEAF_TYPE environment variable is required when TAP_TREE_LOCK_TYPE=MIXED"); error!("Set SPENDING_LEAF_TYPE to the actual type of the leaf being spent (SCHNORR_ONLY or SLH_DSA_ONLY)."); error!("The leaf type is returned in the 'leaf_script_type' field of the tree construction output."); std::process::exit(1); } } } else { leaf_script_type }; // Parse private keys based on effective script type let leaf_script_priv_keys_bytes: Vec> = match effective_leaf_type { LeafScriptType::SlhDsaOnly => { let priv_keys_hex_array = env::var("LEAF_SCRIPT_PRIV_KEYS_HEX") .unwrap_or_else(|_| { error!("LEAF_SCRIPT_PRIV_KEYS_HEX environment variable is required for SLH_DSA_ONLY"); std::process::exit(1); }); // Parse JSON array and extract the first (and only) hex string let priv_keys_hex: String = serde_json::from_str::>(&priv_keys_hex_array) .unwrap_or_else(|_| { error!("Failed to parse LEAF_SCRIPT_PRIV_KEYS_HEX as JSON array"); std::process::exit(1); }) .into_iter() .next() .unwrap_or_else(|| { error!("LEAF_SCRIPT_PRIV_KEYS_HEX array is empty"); std::process::exit(1); }); let priv_keys_bytes = hex::decode(priv_keys_hex).unwrap(); if priv_keys_bytes.len() != 64 { error!("SLH-DSA private key must be 64 bytes, got {}", priv_keys_bytes.len()); std::process::exit(1); } vec![priv_keys_bytes] }, LeafScriptType::SchnorrOnly => { let priv_keys_hex_array = env::var("LEAF_SCRIPT_PRIV_KEYS_HEX") .unwrap_or_else(|_| { error!("LEAF_SCRIPT_PRIV_KEYS_HEX environment variable is required for SCHNORR_ONLY"); std::process::exit(1); }); // Parse JSON array and extract the first (and only) hex string let priv_keys_hex: String = serde_json::from_str::>(&priv_keys_hex_array) .unwrap_or_else(|_| { error!("Failed to parse LEAF_SCRIPT_PRIV_KEYS_HEX as JSON array"); std::process::exit(1); }) .into_iter() .next() .unwrap_or_else(|| { error!("LEAF_SCRIPT_PRIV_KEYS_HEX array is empty"); std::process::exit(1); }); let priv_keys_bytes = hex::decode(priv_keys_hex).unwrap(); if priv_keys_bytes.len() != 32 { error!("Schnorr private key must be 32 bytes, got {}", priv_keys_bytes.len()); std::process::exit(1); } vec![priv_keys_bytes] }, LeafScriptType::ConcatenatedSchnorrAndSlhDsaSameLeaf => { let priv_keys_hex_array = env::var("LEAF_SCRIPT_PRIV_KEYS_HEX") .unwrap_or_else(|_| { error!("LEAF_SCRIPT_PRIV_KEYS_HEX environment variable is required for SCHNORR_AND_SLH_DSA"); std::process::exit(1); }); // Parse JSON array and extract the hex strings let priv_keys_hex_vec: Vec = serde_json::from_str(&priv_keys_hex_array) .unwrap_or_else(|_| { error!("Failed to parse LEAF_SCRIPT_PRIV_KEYS_HEX as JSON array"); std::process::exit(1); }); if priv_keys_hex_vec.len() != 2 { error!("For SCHNORR_AND_SLH_DSA, LEAF_SCRIPT_PRIV_KEYS_HEX must contain exactly 2 hex strings, got {}", priv_keys_hex_vec.len()); std::process::exit(1); } let schnorr_priv_key_hex = &priv_keys_hex_vec[0]; let slh_dsa_priv_key_hex = &priv_keys_hex_vec[1]; let schnorr_priv_key_bytes = hex::decode(schnorr_priv_key_hex).unwrap(); let slh_dsa_priv_key_bytes = hex::decode(slh_dsa_priv_key_hex).unwrap(); if schnorr_priv_key_bytes.len() != 32 { error!("Schnorr private key must be 32 bytes, got {}", schnorr_priv_key_bytes.len()); std::process::exit(1); } if slh_dsa_priv_key_bytes.len() != 64 { error!("SLH-DSA private key must be 64 bytes, got {}", slh_dsa_priv_key_bytes.len()); std::process::exit(1); } vec![schnorr_priv_key_bytes, slh_dsa_priv_key_bytes] }, LeafScriptType::Mixed => { // This case should never be reached because Mixed is resolved to effective_leaf_type above unreachable!("Mixed should have been resolved to effective_leaf_type"); }, LeafScriptType::NotApplicable => { panic!("LeafScriptType::NotApplicable is not applicable"); } }; // ie: OP_PUSHBYTES_32 6d4ddc0e47d2e8f82cbe2fc2d0d749e7bd3338112cecdc76d8f831ae6620dbe0 OP_CHECKSIG let leaf_script_bytes: Vec = env::var("LEAF_SCRIPT_HEX") .map(|s| hex::decode(s).unwrap()) .unwrap_or_else(|_| { error!("LEAF_SCRIPT_HEX environment variable is required but not set"); std::process::exit(1); }); // https://learnmeabitcoin.com/explorer/tx/797505b104b5fb840931c115ea35d445eb1f64c9279bf23aa5bb4c3d779da0c2#outputs let spend_output_pubkey_hash_bytes: Vec = hex::decode("0de745dc58d8e62e6f47bde30cd5804a82016f9e").unwrap(); // OUTPUT_AMOUNT_SATS env var is optional. Default is FUNDING_UTXO_AMOUNT_SATS - 5000 sats let spend_output_amount_sats: u64 = env::var("OUTPUT_AMOUNT_SATS") .ok() .and_then(|s| s.parse::().ok()) .unwrap_or(funding_utxo_amount_sats.saturating_sub(5000)); let result: SpendDetails = pay_to_p2wpkh_tx( funding_tx_id_bytes, funding_utxo_index, funding_utxo_amount_sats, funding_script_pubkey_bytes, control_block_bytes, leaf_script_bytes.clone(), leaf_script_priv_keys_bytes, // Now passing Vec> instead of Vec spend_output_pubkey_hash_bytes, spend_output_amount_sats, effective_leaf_type // Use effective type (resolved from SPENDING_LEAF_TYPE if Mixed) ); // Remove first and last byte from leaf_script_bytes to get tapleaf_pubkey_bytes let tapleaf_pubkey_bytes: Vec = leaf_script_bytes[1..leaf_script_bytes.len()-1].to_vec(); match effective_leaf_type { LeafScriptType::SlhDsaOnly => { let is_valid: bool = verify_slh_dsa_via_bytes(&result.sig_bytes, &result.sighash, &tapleaf_pubkey_bytes); info!("is_valid: {}", is_valid); }, LeafScriptType::SchnorrOnly => { let is_valid: bool = verify_schnorr_signature_via_bytes( &result.sig_bytes, &result.sighash, &tapleaf_pubkey_bytes); info!("is_valid: {}", is_valid); }, LeafScriptType::ConcatenatedSchnorrAndSlhDsaSameLeaf => { // For combined scripts, we need to separate the signatures // The sig_bytes contains: [schnorr_sig (64 bytes), slh_dsa_sig (7856 bytes)] (raw signatures without sighash) let schnorr_sig_len = 64; // Schnorr signature is 64 bytes let slh_dsa_sig_len = 7856; // SLH-DSA signature is 7856 bytes let expected_min_len = schnorr_sig_len + slh_dsa_sig_len; if result.sig_bytes.len() < expected_min_len { error!("Combined signature length is too short: expected at least {}, got {}", expected_min_len, result.sig_bytes.len()); return result; } // Extract Schnorr signature (first 64 bytes) let schnorr_sig = &result.sig_bytes[..schnorr_sig_len]; // Extract SLH-DSA signature (next 7856 bytes) let slh_dsa_sig = &result.sig_bytes[schnorr_sig_len..schnorr_sig_len + slh_dsa_sig_len]; // For SCHNORR_AND_SLH_DSA scripts, we need to extract the individual public keys // The script structure is: OP_PUSHBYTES_32 OP_CHECKSIG OP_PUSHBYTES_32 OP_SUBSTR OP_BOOLAND OP_VERIFY // So we need to extract the Schnorr pubkey (first 32 bytes after OP_PUSHBYTES_32) let schnorr_pubkey_bytes = &leaf_script_bytes[1..33]; // Skip OP_PUSHBYTES_32 (0x20), get next 32 bytes let slh_dsa_pubkey_bytes = &leaf_script_bytes[35..67]; // Skip OP_CHECKSIG (0xac), OP_PUSHBYTES_32 (0x20), get next 32 bytes // Verify Schnorr signature let schnorr_is_valid: bool = verify_schnorr_signature_via_bytes( schnorr_sig, &result.sighash, schnorr_pubkey_bytes); info!("Schnorr signature is_valid: {}", schnorr_is_valid); // Verify SLH-DSA signature let slh_dsa_is_valid: bool = verify_slh_dsa_via_bytes( slh_dsa_sig, &result.sighash, slh_dsa_pubkey_bytes); info!("SLH-DSA signature is_valid: {}", slh_dsa_is_valid); let both_valid = schnorr_is_valid && slh_dsa_is_valid; info!("Both signatures valid: {}", both_valid); } LeafScriptType::Mixed => { // This case should never be reached because Mixed is resolved to effective_leaf_type above unreachable!("Mixed should have been resolved to effective_leaf_type"); } LeafScriptType::NotApplicable => { panic!("LeafScriptType::NotApplicable is not applicable"); } } return result; } ================================================ FILE: bip-0360/ref-impl/rust/examples/p2tr_construction.rs ================================================ use p2mr_ref::{create_p2tr_utxo, create_p2tr_multi_leaf_taptree}; use p2mr_ref::data_structures::{UtxoReturn, TaptreeReturn, ConstructionReturn}; // Inspired by: https://learnmeabitcoin.com/technical/upgrades/taproot/#example-3-script-path-spend-signature fn main() -> ConstructionReturn { let _ = env_logger::try_init(); // Use try_init to avoid reinitialization error let internal_pubkey_hex = "924c163b385af7093440184af6fd6244936d1288cbb41cc3812286d3f83a3329".to_string(); let taptree_return: TaptreeReturn = create_p2tr_multi_leaf_taptree(internal_pubkey_hex.clone()); let utxo_return: UtxoReturn = create_p2tr_utxo(taptree_return.clone().tree_root_hex, internal_pubkey_hex); return ConstructionReturn { taptree_return: taptree_return, utxo_return: utxo_return, }; } ================================================ FILE: bip-0360/ref-impl/rust/examples/p2tr_spend.rs ================================================ use p2mr_ref::{ pay_to_p2wpkh_tx , verify_schnorr_signature_via_bytes}; use p2mr_ref::data_structures::{SpendDetails, LeafScriptType}; use std::env; use log::{info, error}; // Inspired by: https://learnmeabitcoin.com/technical/upgrades/taproot/#example-3-script-path-spend-signature fn main() -> SpendDetails { let _ = env_logger::try_init(); // Use try_init to avoid reinitialization error // FUNDING_TX_ID environment variable is required let funding_tx_id: String = env::var("FUNDING_TX_ID") .unwrap_or_else(|_| { error!("FUNDING_TX_ID environment variable is required but not set"); std::process::exit(1); }); let funding_tx_id_bytes: Vec = hex::decode(funding_tx_id.clone()).unwrap(); // FUNDING_UTXO_AMOUNT_SATS environment variable is required let funding_utxo_amount_sats: u64 = env::var("FUNDING_UTXO_AMOUNT_SATS") .unwrap_or_else(|_| { error!("FUNDING_UTXO_AMOUNT_SATS environment variable is required but not set"); std::process::exit(1); }) .parse::() .unwrap_or_else(|_| { error!("FUNDING_UTXO_AMOUNT_SATS must be a valid u64 integer"); std::process::exit(1); }); // The input index of the funding tx // Allow override via FUNDING_UTXO_INDEX environment variable let funding_utxo_index: u32 = env::var("FUNDING_UTXO_INDEX") .ok() .and_then(|s| s.parse::().ok()) .unwrap_or(0); info!("Funding tx id: {}, utxo index: {}", funding_tx_id, funding_utxo_index); // FUNDING_SCRIPT_PUBKEY environment variable is required let funding_script_pubkey_bytes: Vec = env::var("FUNDING_SCRIPT_PUBKEY") .map(|s| hex::decode(s).unwrap()) .unwrap_or_else(|_| { error!("FUNDING_SCRIPT_PUBKEY environment variable is required but not set"); std::process::exit(1); }); let control_block_bytes: Vec = env::var("CONTROL_BLOCK_HEX") .map(|s| hex::decode(s).unwrap()) .unwrap_or_else(|_| { error!("CONTROL_BLOCK_HEX environment variable is required but not set"); std::process::exit(1); }); info!("P2TR control block size: {}", control_block_bytes.len()); // P2TR only supports Schnorr signatures, so we only need one private key let leaf_script_priv_key_bytes: Vec = { let priv_keys_hex_array = env::var("LEAF_SCRIPT_PRIV_KEYS_HEX") .unwrap_or_else(|_| { error!("LEAF_SCRIPT_PRIV_KEYS_HEX environment variable is required but not set"); std::process::exit(1); }); // Parse JSON array and extract the first (and only) hex string let priv_keys_hex: String = serde_json::from_str::>(&priv_keys_hex_array) .unwrap_or_else(|_| { error!("Failed to parse LEAF_SCRIPT_PRIV_KEYS_HEX as JSON array"); std::process::exit(1); }) .into_iter() .next() .unwrap_or_else(|| { error!("LEAF_SCRIPT_PRIV_KEYS_HEX array is empty"); std::process::exit(1); }); hex::decode(priv_keys_hex).unwrap() }; // Validate that the private key is 32 bytes (Schnorr key size) if leaf_script_priv_key_bytes.len() != 32 { error!("P2TR private key must be 32 bytes (Schnorr), got {}", leaf_script_priv_key_bytes.len()); std::process::exit(1); } // Convert to Vec> format expected by the function let leaf_script_priv_keys_bytes: Vec> = vec![leaf_script_priv_key_bytes]; // ie: OP_PUSHBYTES_32 6d4ddc0e47d2e8f82cbe2fc2d0d749e7bd3338112cecdc76d8f831ae6620dbe0 OP_CHECKSIG let leaf_script_bytes: Vec = env::var("LEAF_SCRIPT_HEX") .map(|s| hex::decode(s).unwrap()) .unwrap_or_else(|_| { error!("LEAF_SCRIPT_HEX environment variable is required but not set"); std::process::exit(1); }); // https://learnmeabitcoin.com/explorer/tx/797505b104b5fb840931c115ea35d445eb1f64c9279bf23aa5bb4c3d779da0c2#outputs let spend_output_pubkey_hash_bytes: Vec = hex::decode("0de745dc58d8e62e6f47bde30cd5804a82016f9e").unwrap(); // OUTPUT_AMOUNT_SATS env var is optional. Default is FUNDING_UTXO_AMOUNT_SATS - 5000 sats let spend_output_amount_sats: u64 = env::var("OUTPUT_AMOUNT_SATS") .ok() .and_then(|s| s.parse::().ok()) .unwrap_or(funding_utxo_amount_sats.saturating_sub(5000)); let result: SpendDetails = pay_to_p2wpkh_tx( funding_tx_id_bytes, funding_utxo_index, funding_utxo_amount_sats, funding_script_pubkey_bytes, control_block_bytes, leaf_script_bytes.clone(), leaf_script_priv_keys_bytes, // Now passing Vec> format spend_output_pubkey_hash_bytes.clone(), spend_output_amount_sats, LeafScriptType::SchnorrOnly ); // Remove first and last byte from leaf_script_bytes to get tapleaf_pubkey_bytes let tapleaf_pubkey_bytes: Vec = leaf_script_bytes[1..leaf_script_bytes.len()-1].to_vec(); let is_valid: bool = verify_schnorr_signature_via_bytes( &result.sig_bytes, &result.sighash, &tapleaf_pubkey_bytes); info!("is_valid: {}", is_valid); return result; } ================================================ FILE: bip-0360/ref-impl/rust/examples/schnorr_example.rs ================================================ use std::env; use log::info; use once_cell::sync::Lazy; use bitcoin::key::{Secp256k1}; use bitcoin::hashes::{sha256::Hash, Hash as HashTrait}; use bitcoin::secp256k1::{Message}; use p2mr_ref::{ acquire_schnorr_keypair, verify_schnorr_signature }; /* Secp256k1 implements the Signing trait when it's initialized in signing mode. It's important to note that Secp256k1 has different capabilities depending on how it's constructed: * Secp256k1::new() creates a context capable of both signing and verification * Secp256k1::signing_only() creates a context that can only sign * Secp256k1::verification_only() creates a context that can only verify */ static SECP: Lazy> = Lazy::new(Secp256k1::new); fn main() { let _ = env_logger::try_init(); // acquire a schnorr keypair (leveraging OS provided random number generator) let keypair = acquire_schnorr_keypair(); let (secret_key, public_key) = keypair.as_schnorr().unwrap(); let message_bytes = b"hello"; // secp256k1 operates on a 256-bit (32-byte) field, so inputs must be exactly this size // subsequently, Schnorr signatures on secp256k1 require exactly a 32-byte input (the curve's scalar field size) let message_hash: Hash = Hash::hash(message_bytes); let message: Message = Message::from_digest_slice(&message_hash.to_byte_array()).unwrap(); /* The secp256k1 library internally generates a random scalar value (aka: nonce or k-value) for each signature * Every signature is unique - even if you sign the same message with the same private key multiple times * The randomness is handled automatically by the secp256k1 implementation * You get different signatures each time for the same inputs * The nonce is only needed during signing, not during verification Schnorr signatures require randomness for security reasons: * Prevents private key recovery - If the same nonce is used twice, an attacker could potentially derive your private key * Ensures signature uniqueness - Each signature should be cryptographically distinct * Protects against replay attacks - Different signatures for the same data */ let signature: bitcoin::secp256k1::schnorr::Signature = SECP.sign_schnorr(&message, &secret_key.keypair(&SECP)); info!("Signature created successfully, size: {}", signature.serialize().len()); //let pubkey = public_key; /* * The nonce provides security during signing (prevents private key recovery) * The nonce is mathematically eliminated during verification * The verifier only needs public information (signature, message, public key) */ let schnorr_valid = verify_schnorr_signature(signature, message, *public_key); info!("schnorr_valid: {}", schnorr_valid); let aux_rand = [0u8; 32]; // 32 zero bytes; fine for testing let signature_aux_rand: bitcoin::secp256k1::schnorr::Signature = SECP.sign_schnorr_with_aux_rand( &message, &secret_key.keypair(&SECP), &aux_rand ); info!("aux_rand signature created successfully, size: {}", signature_aux_rand.serialize().len()); let schnorr_valid_aux_rand = verify_schnorr_signature(signature_aux_rand, message, *public_key); info!("schnorr_valid_aux_rand: {}", schnorr_valid_aux_rand); } ================================================ FILE: bip-0360/ref-impl/rust/examples/slh_dsa_verification_example.rs ================================================ use std::env; use log::info; use once_cell::sync::Lazy; use bitcoin::hashes::{sha256::Hash, Hash as HashTrait}; use rand::{rng, RngCore}; use bitcoinpqc::{ generate_keypair, public_key_size, secret_key_size, sign, signature_size, verify, Algorithm, KeyPair, }; fn main() { let _ = env_logger::try_init(); /* In SPHINCS+ (underlying algorithm of SLH-DSA), the random data is used to: * Initialize hash function parameters within the key generation * Seed the Merkle tree construction that forms the public key * Generate the secret key components that enable signing */ let random_data = get_random_bytes(128); println!("Generated random data of size {}", random_data.len()); let keypair: KeyPair = generate_keypair(Algorithm::SLH_DSA_128S, &random_data) .expect("Failed to generate SLH-DSA-128S keypair"); let message_bytes = b"SLH-DSA-128S Test Message"; println!("Message to sign: {message_bytes:?}"); /* No need to hash the message 1. Variable Input Size: SPHINCS+ can handle messages of arbitrary length directly 2. Internal Hashing: The SPHINCS+ algorithm internally handles message processing and hashing as part of its design 3. Hash-Based Design: SPHINCS+ is built on hash functions and Merkle trees, so it's designed to work with variable-length inputs 4. No Curve Constraints: Unlike elliptic curve schemes, SPHINCS+ doesn't have fixed field size requirements SLH-DSA doesn't use nonces like Schnorr does. With SLH-DSA, randomness is built into the key generation process only ( and not the signing process; ie: SECP256K1) Thus, no need for aux_rand data fed to the signature function. The signing algorithm is deterministic and doesn't require random input during signing. */ let signature = sign(&keypair.secret_key, message_bytes).expect("Failed to sign with SLH-DSA-128S"); println!( "Signature created successfully, size: {}", signature.bytes.len() ); println!( "Signature prefix: {:02x?}", &signature.bytes[..8.min(signature.bytes.len())] ); // Verify the signature println!("Verifying signature..."); let result = verify(&keypair.public_key, message_bytes, &signature); println!("Verification result: {result:?}"); assert!(result.is_ok(), "SLH-DSA-128S signature verification failed"); // Try to verify with a modified message - should fail let modified_message = b"SLH-DSA-128S Modified Message"; println!("Modified message: {modified_message:?}"); let result = verify(&keypair.public_key, modified_message, &signature); println!("Verification with modified message result: {result:?}"); assert!( result.is_err(), "SLH-DSA-128S verification should fail with modified message" ); } fn get_random_bytes(size: usize) -> Vec { let mut bytes = vec![0u8; size]; rng().fill_bytes(&mut bytes); bytes } ================================================ FILE: bip-0360/ref-impl/rust/src/bin/slh_dsa_key_gen.rs ================================================ use std::env; use log::info; use rand::{rng, RngCore}; use bitcoinpqc::{ generate_keypair, public_key_size, secret_key_size, Algorithm, KeyPair, }; fn main() { let _ = env_logger::try_init(); /* In SPHINCS+ (underlying algorithm of SLH-DSA), the random data is used to: * Initialize hash function parameters within the key generation * Seed the Merkle tree construction that forms the public key * Generate the secret key components that enable signing */ let random_data = get_random_bytes(128); println!("Generated random data of size {}", random_data.len()); let keypair: KeyPair = generate_keypair(Algorithm::SLH_DSA_128S, &random_data) .expect("Failed to generate SLH-DSA-128S keypair"); info!("public key size / value = {}, {}", public_key_size(Algorithm::SLH_DSA_128S), hex::encode(&keypair.public_key.bytes)); info!("private key size / value = {}, {}", secret_key_size(Algorithm::SLH_DSA_128S), hex::encode(&keypair.secret_key.bytes)); } fn get_random_bytes(size: usize) -> Vec { let mut bytes = vec![0u8; size]; rng().fill_bytes(&mut bytes); bytes } ================================================ FILE: bip-0360/ref-impl/rust/src/data_structures.rs ================================================ use std::collections::HashMap; use serde::{Deserialize, Serialize}; use log::debug; // Add imports for the unified keypair use bitcoin::secp256k1::{SecretKey, XOnlyPublicKey}; use bitcoinpqc::{KeyPair, Algorithm}; /// Enum representing the type of leaf script to create #[derive(Debug, Clone, Copy, PartialEq, Eq)] pub enum LeafScriptType { /// Script requires only SLH-DSA signature SlhDsaOnly, /// Script requires only Schnorr signature SchnorrOnly, /// Script requires both Schnorr and SLH-DSA signatures (in that order) ConcatenatedSchnorrAndSlhDsaSameLeaf, /// Leaves of TapTree are mixed. Some leaves are locked using Schnorr and others are locked using SLH-DSA Mixed, /// Script type is not applicable NotApplicable, } impl LeafScriptType { /// Check if this script type uses SLH-DSA pub fn uses_slh_dsa(&self) -> bool { matches!(self, LeafScriptType::SlhDsaOnly | LeafScriptType::ConcatenatedSchnorrAndSlhDsaSameLeaf) } /// Check if this script type uses Schnorr pub fn uses_schnorr(&self) -> bool { matches!(self, LeafScriptType::SchnorrOnly | LeafScriptType::ConcatenatedSchnorrAndSlhDsaSameLeaf) } /// Check if this script type requires both signature types pub fn requires_both(&self) -> bool { matches!(self, LeafScriptType::ConcatenatedSchnorrAndSlhDsaSameLeaf) } /// Check if TapTree uses Schnorr for some leaves and SLH-DSA for others pub fn uses_mixed(&self) -> bool { matches!(self, LeafScriptType::Mixed) } /// Check if this script type is not applicable pub fn is_not_applicable(&self) -> bool { matches!(self, LeafScriptType::NotApplicable) } /// Convert to string representation for serialization pub fn to_string(&self) -> String { match self { LeafScriptType::SlhDsaOnly => "SLH_DSA_ONLY".to_string(), LeafScriptType::SchnorrOnly => "SCHNORR_ONLY".to_string(), LeafScriptType::ConcatenatedSchnorrAndSlhDsaSameLeaf => "CONCATENATED_SCHNORR_AND_SLH_DSA".to_string(), LeafScriptType::Mixed => "MIXED".to_string(), LeafScriptType::NotApplicable => "NOT_APPLICABLE".to_string(), } } /// Parse from string representation pub fn from_string(s: &str) -> Self { match s { "SLH_DSA_ONLY" => LeafScriptType::SlhDsaOnly, "SCHNORR_ONLY" => LeafScriptType::SchnorrOnly, "CONCATENATED_SCHNORR_AND_SLH_DSA" => LeafScriptType::ConcatenatedSchnorrAndSlhDsaSameLeaf, "MIXED" => LeafScriptType::Mixed, _ => LeafScriptType::NotApplicable, } } } #[derive(Debug, Serialize)] pub struct TestVectors { pub version: u32, #[serde(rename = "test_vectors")] pub test_vectors: Vec, #[serde(skip, default = "HashMap::new")] pub test_vector_map: HashMap, } impl<'de> Deserialize<'de> for TestVectors { fn deserialize(deserializer: D) -> Result where D: serde::Deserializer<'de>, { #[derive(Deserialize)] struct Helper { version: u32, #[serde(rename = "test_vectors")] test_vectors: Vec, } let helper = Helper::deserialize(deserializer)?; let mut test_vector_map = HashMap::new(); for test in helper.test_vectors.iter() { test_vector_map.insert(test.id.clone(), test.clone()); } Ok(TestVectors { version: helper.version, test_vectors: helper.test_vectors, test_vector_map, }) } } #[derive(Debug, Serialize, Deserialize, Clone)] pub struct TestVector { pub id: String, pub objective: String, pub given: TestVectorGiven, pub intermediary: TestVectorIntermediary, pub expected: TestVectorExpected, } #[derive(Debug, Serialize, Deserialize, Clone)] pub struct TestVectorGiven { #[serde(rename = "internalPubkey")] pub internal_pubkey: Option, #[serde(rename = "scriptTree")] pub script_tree: Option, #[serde(rename = "scriptInputs")] pub script_inputs: Option>, #[serde(rename = "scriptHex")] pub script_hex: Option, #[serde(rename = "controlBlock")] pub control_block: Option, } #[derive(Debug, Serialize, Deserialize, Clone)] pub struct TestVectorIntermediary { #[serde(default)] #[serde(rename = "leafHashes")] pub leaf_hashes: Vec, #[serde(rename = "merkleRoot")] pub merkle_root: Option } #[derive(Debug, Serialize, Deserialize, Clone)] pub struct TestVectorExpected { #[serde(rename = "scriptPubKey")] pub script_pubkey: Option, #[serde(rename = "bip350Address")] pub bip350_address: Option, #[serde(default)] #[serde(rename = "scriptPathControlBlocks")] pub script_path_control_blocks: Option>, #[serde(rename = "error")] pub error: Option, #[serde(rename = "address")] pub address: Option, #[serde(default)] pub witness: Option } #[derive(Debug, Serialize, Deserialize, Clone)] pub struct TVScriptLeaf { pub id: u8, pub script: String, #[serde(rename = "leafVersion")] pub leaf_version: u8, } // Taproot script trees are binary trees, so each branch should have exactly two children. #[derive(Debug, Serialize, Clone)] pub enum TVScriptTree { Leaf(TVScriptLeaf), Branch { // Box is used because Rust needs to know the exact size of types at compile time. // Without it, we'd have an infinitely size recursive type. // The enum itself is on the stack, but the Box fields within the Branch variant store pointers to heap-allocated ScriptTree values. left: Box, right: Box, }, } // Add custom deserialize implementation impl<'de> Deserialize<'de> for TVScriptTree { fn deserialize(deserializer: D) -> Result where D: serde::Deserializer<'de>, { #[derive(Deserialize)] #[serde(untagged)] enum Helper { Leaf(TVScriptLeaf), Branch(Vec), } match Helper::deserialize(deserializer)? { Helper::Leaf(leaf) => Ok(TVScriptTree::Leaf(leaf)), Helper::Branch(v) => { assert!(v.len() == 2, "Branch must have exactly two children"); let mut iter = v.into_iter(); Ok(TVScriptTree::Branch { left: Box::new(iter.next().unwrap()), right: Box::new(iter.next().unwrap()), }) } } } } // Add this enum before the TVScriptTree implementation #[derive(Debug, Copy, Clone, Eq, PartialEq)] pub enum Direction { Left, Right, Root, } impl TVScriptTree { /// Implements a "post-order" traversal as follows: left, right, branch pub fn traverse_with_depth(&self, depth: u8, direction: Direction, f: &mut F) { match self { TVScriptTree::Branch { left, right } => { right.traverse_with_depth(depth, Direction::Right, f); // Pass Right for right subtree left.traverse_with_depth(depth, Direction::Left, f); // Pass Left for left subtree f(self, depth, direction); // Pass the current node's direction } TVScriptTree::Leaf { .. } => { f(self, depth, direction); } } } /// Traverses the tree visiting right subtree leaves first, then left subtree leaves. /// Depth increases by 1 at each branch level. /* root (depth 0) / \ L0 (depth 1) (subtree) (depth 1) / \ L1 (depth 2) L2 (depth 2) The new traversal will visit: L1 at depth 2 -> L2 at depth 2 -> L0 at depth 1 */ pub fn traverse_with_right_subtree_first(&self, depth: u8, direction: Direction, f: &mut F) { match self { TVScriptTree::Branch { left, right } => { let next_depth = depth + 1; // Visit right subtree first right.traverse_with_right_subtree_first(next_depth, Direction::Right, f); // Then visit left subtree left.traverse_with_right_subtree_first(next_depth, Direction::Left, f); } TVScriptTree::Leaf { .. } => { f(self, depth, direction); } } } } impl std::fmt::Display for Direction { fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result { match self { Direction::Left => write!(f, "L"), Direction::Right => write!(f, "R"), Direction::Root => write!(f, "Root"), } } } pub struct ScriptTreeHashCache { pub leaf_hashes: HashMap, pub branch_hashes: HashMap, } impl ScriptTreeHashCache { pub fn new() -> Self { Self { leaf_hashes: HashMap::new(), branch_hashes: HashMap::new(), } } pub fn set_leaf_hash(&mut self, branch_id: u8, direction: Direction, hash: String) { let key = format!("{branch_id}_{direction}"); debug!("set_leaf_hash: key: {}, hash: {}", key, hash); self.leaf_hashes.insert(key, hash); } pub fn set_branch_hash(&mut self, branch_id: u8, hash: String) { self.branch_hashes.insert(branch_id, hash); } } fn serialize_hex(bytes: &Vec, s: S) -> Result where S: serde::Serializer, { s.serialize_str(&hex::encode(bytes)) } fn deserialize_hex<'de, D>(d: D) -> Result, D::Error> where D: serde::Deserializer<'de>, { let s = String::deserialize(d)?; hex::decode(s).map_err(serde::de::Error::custom) } #[derive(Debug, Clone, Serialize, Deserialize)] pub struct SpendDetails { pub tx_hex: String, #[serde(serialize_with = "serialize_hex")] #[serde(deserialize_with = "deserialize_hex")] pub sighash: Vec, #[serde(serialize_with = "serialize_hex")] #[serde(deserialize_with = "deserialize_hex")] pub sig_bytes: Vec, #[serde(serialize_with = "serialize_hex")] #[serde(deserialize_with = "deserialize_hex")] pub derived_witness_vec: Vec, } impl std::process::Termination for SpendDetails { fn report(self) -> std::process::ExitCode { if let Ok(json) = serde_json::to_string_pretty(&self) { println!("{}", json); } else { println!("{:?}", self); } std::process::ExitCode::SUCCESS } } #[derive(Debug, Clone, Serialize, Deserialize)] pub struct UtxoReturn { pub script_pubkey_hex: String, pub bech32m_address: String, pub bitcoin_network: bitcoin::Network, } impl std::process::Termination for UtxoReturn { fn report(self) -> std::process::ExitCode { if let Ok(json) = serde_json::to_string_pretty(&self) { println!("{}", json); } else { println!("{:?}", self); } std::process::ExitCode::SUCCESS } } #[derive(Debug, Clone, Serialize, Deserialize)] pub struct TaptreeReturn { pub leaf_script_priv_keys_hex: Vec, // Changed to support multiple private keys pub leaf_script_hex: String, pub tree_root_hex: String, pub control_block_hex: String, /// The script type of the leaf being returned (needed for spending) pub leaf_script_type: String, } impl std::process::Termination for TaptreeReturn { fn report(self) -> std::process::ExitCode { if let Ok(json) = serde_json::to_string_pretty(&self) { println!("{}", json); } else { println!("{:?}", self); } std::process::ExitCode::SUCCESS } } #[derive(Debug, Clone, Serialize, Deserialize)] pub struct ConstructionReturn { pub taptree_return: TaptreeReturn, pub utxo_return: UtxoReturn, } impl std::process::Termination for ConstructionReturn { fn report(self) -> std::process::ExitCode { if let Ok(json) = serde_json::to_string_pretty(&self) { println!("{}", json); } else { println!("{:?}", self); } std::process::ExitCode::SUCCESS } } /// A unified keypair that can contain either a Schnorr keypair or an SLH-DSA keypair #[derive(Debug, Clone)] pub enum UnifiedKeypair { Schnorr(SecretKey, XOnlyPublicKey), SlhDsa(KeyPair), } /// A container for multiple keypairs that can be used in a single leaf script #[derive(Debug, Clone)] pub struct MultiKeypair { pub schnorr_keypair: Option, pub slh_dsa_keypair: Option, } impl MultiKeypair { /// Create a new MultiKeypair with only a Schnorr keypair pub fn new_schnorr_only(schnorr_keypair: UnifiedKeypair) -> Self { Self { schnorr_keypair: Some(schnorr_keypair), slh_dsa_keypair: None, } } /// Create a new MultiKeypair with only an SLH-DSA keypair pub fn new_slh_dsa_only(slh_dsa_keypair: UnifiedKeypair) -> Self { Self { schnorr_keypair: None, slh_dsa_keypair: Some(slh_dsa_keypair), } } /// Create a new MultiKeypair with both keypairs pub fn new_combined(schnorr_keypair: UnifiedKeypair, slh_dsa_keypair: UnifiedKeypair) -> Self { Self { schnorr_keypair: Some(schnorr_keypair), slh_dsa_keypair: Some(slh_dsa_keypair), } } /// Get all secret key bytes for serialization (in order: schnorr, then slh_dsa if present) pub fn secret_key_bytes(&self) -> Vec> { let mut result = Vec::new(); if let Some(ref schnorr) = self.schnorr_keypair { result.push(schnorr.secret_key_bytes()); } if let Some(ref slh_dsa) = self.slh_dsa_keypair { result.push(slh_dsa.secret_key_bytes()); } result } /// Get all public key bytes for script construction (in order: schnorr, then slh_dsa if present) pub fn public_key_bytes(&self) -> Vec> { let mut result = Vec::new(); if let Some(ref schnorr) = self.schnorr_keypair { result.push(schnorr.public_key_bytes()); } if let Some(ref slh_dsa) = self.slh_dsa_keypair { result.push(slh_dsa.public_key_bytes()); } result } /// Check if this contains a Schnorr keypair pub fn has_schnorr(&self) -> bool { self.schnorr_keypair.is_some() } /// Check if this contains an SLH-DSA keypair pub fn has_slh_dsa(&self) -> bool { self.slh_dsa_keypair.is_some() } /// Get the Schnorr keypair if present pub fn schnorr_keypair(&self) -> Option<&UnifiedKeypair> { self.schnorr_keypair.as_ref() } /// Get the SLH-DSA keypair if present pub fn slh_dsa_keypair(&self) -> Option<&UnifiedKeypair> { self.slh_dsa_keypair.as_ref() } } /// Information about a single leaf in a mixed-type tree /// Used when different leaves in the same tree use different algorithms #[derive(Debug, Clone)] pub struct MixedLeafInfo { /// The leaf index in the tree pub leaf_index: u32, /// The script type for this specific leaf pub leaf_script_type: LeafScriptType, /// The keypairs for this leaf pub keypairs: MultiKeypair, /// The script for this leaf pub script: Vec, } impl MixedLeafInfo { /// Create a new MixedLeafInfo for a Schnorr-only leaf pub fn new_schnorr(leaf_index: u32, keypairs: MultiKeypair, script: Vec) -> Self { Self { leaf_index, leaf_script_type: LeafScriptType::SchnorrOnly, keypairs, script, } } /// Create a new MixedLeafInfo for an SLH-DSA-only leaf pub fn new_slh_dsa(leaf_index: u32, keypairs: MultiKeypair, script: Vec) -> Self { Self { leaf_index, leaf_script_type: LeafScriptType::SlhDsaOnly, keypairs, script, } } /// Create a new MixedLeafInfo for a combined Schnorr+SLH-DSA leaf pub fn new_combined(leaf_index: u32, keypairs: MultiKeypair, script: Vec) -> Self { Self { leaf_index, leaf_script_type: LeafScriptType::ConcatenatedSchnorrAndSlhDsaSameLeaf, keypairs, script, } } /// Get the secret key bytes for this leaf pub fn secret_key_bytes(&self) -> Vec> { self.keypairs.secret_key_bytes() } /// Get the public key bytes for this leaf pub fn public_key_bytes(&self) -> Vec> { self.keypairs.public_key_bytes() } } impl UnifiedKeypair { /// Create a new Schnorr keypair pub fn new_schnorr(secret_key: SecretKey, public_key: XOnlyPublicKey) -> Self { UnifiedKeypair::Schnorr(secret_key, public_key) } /// Create a new SLH-DSA keypair pub fn new_slh_dsa(keypair: KeyPair) -> Self { UnifiedKeypair::SlhDsa(keypair) } /// Get the secret key bytes for serialization pub fn secret_key_bytes(&self) -> Vec { match self { UnifiedKeypair::Schnorr(secret_key, _) => secret_key.secret_bytes().to_vec(), UnifiedKeypair::SlhDsa(keypair) => keypair.secret_key.bytes.clone(), } } /// Get the public key bytes for script construction pub fn public_key_bytes(&self) -> Vec { match self { UnifiedKeypair::Schnorr(_, public_key) => public_key.serialize().to_vec(), UnifiedKeypair::SlhDsa(keypair) => keypair.public_key.bytes.clone(), } } /// Get the algorithm type pub fn algorithm(&self) -> &'static str { match self { UnifiedKeypair::Schnorr(_, _) => "Schnorr", UnifiedKeypair::SlhDsa(_) => "SLH-DSA", } } /// Check if this is a Schnorr keypair pub fn is_schnorr(&self) -> bool { matches!(self, UnifiedKeypair::Schnorr(_, _)) } /// Check if this is an SLH-DSA keypair pub fn is_slh_dsa(&self) -> bool { matches!(self, UnifiedKeypair::SlhDsa(_)) } /// Get the underlying Schnorr keypair if this is a Schnorr keypair pub fn as_schnorr(&self) -> Option<(&SecretKey, &XOnlyPublicKey)> { match self { UnifiedKeypair::Schnorr(secret_key, public_key) => Some((secret_key, public_key)), _ => None, } } /// Get the underlying SLH-DSA keypair if this is an SLH-DSA keypair pub fn as_slh_dsa(&self) -> Option<&KeyPair> { match self { UnifiedKeypair::SlhDsa(keypair) => Some(keypair), _ => None, } } } ================================================ FILE: bip-0360/ref-impl/rust/src/error.rs ================================================ use thiserror::Error; #[derive(Error, Debug)] pub enum P2MRError { #[error("P2TR requires witness version of 1")] P2trRequiresWitnessVersion1, #[error("P2MR requires a script tree with at least one leaf")] MissingScriptTreeLeaf, // We can add more specific error variants here as needed #[error("Invalid script tree structure: {0}")] InvalidScriptTree(String), } ================================================ FILE: bip-0360/ref-impl/rust/src/lib.rs ================================================ pub mod data_structures; pub mod error; use log::{debug, info, error}; use std::env; use std::io::Write; use rand::{rng, RngCore}; use once_cell::sync::Lazy; use bitcoin::hashes::{sha256, Hash}; use bitcoin::key::{Secp256k1, Parity}; use bitcoin::secp256k1::{Message, SecretKey, Keypair, rand::rngs::OsRng, rand::thread_rng, rand::Rng, schnorr::Signature}; use bitcoin::{ Amount, TxOut, WPubkeyHash, Address, Network, OutPoint, blockdata::witness::Witness, Script, ScriptBuf, XOnlyPublicKey, PublicKey, sighash::{SighashCache, TapSighashType, Prevouts, TapSighash}, taproot::{LeafVersion, NodeInfo, TapLeafHash, TapNodeHash, TapTree, ScriptLeaves, TaprootMerkleBranch, TaprootBuilder, TaprootSpendInfo, ControlBlock}, transaction::{Transaction, Sequence} }; use bitcoin::p2mr::{P2mrScriptBuf, P2mrBuilder, P2mrSpendInfo, P2mrControlBlock, P2MR_LEAF_VERSION}; use bitcoinpqc::{ generate_keypair, public_key_size, secret_key_size, Algorithm, KeyPair, sign, verify, }; use data_structures::{SpendDetails, UtxoReturn, TaptreeReturn, UnifiedKeypair, MultiKeypair, LeafScriptType, MixedLeafInfo}; /* Secp256k1 implements the Signing trait when it's initialized in signing mode. It's important to note that Secp256k1 has different capabilities depending on how it's constructed: * Secp256k1::new() creates a context capable of both signing and verification * Secp256k1::signing_only() creates a context that can only sign * Secp256k1::verification_only() creates a context that can only verify */ static SECP: Lazy> = Lazy::new(Secp256k1::new); /// Creates a Huffman tree with leaves of the specified script type. /// /// For Mixed type, leaves alternate between Schnorr (even indices) and SLH-DSA (odd indices). /// The LEAF_TO_SPEND_FROM_TYPE env var can override the type for the leaf of interest. /// /// Returns: (huffman_entries, keypairs_of_interest, script_buf_of_interest, actual_leaf_type) fn create_huffman_tree(leaf_script_type: LeafScriptType) -> (Vec<(u32, ScriptBuf)>, MultiKeypair, ScriptBuf, LeafScriptType) { let mut total_leaf_count: u32 = 1; if let Ok(env_value) = env::var("TOTAL_LEAF_COUNT") { if let Ok(parsed_value) = env_value.parse::() { total_leaf_count = parsed_value; } } let mut leaf_to_spend_from: u32 = 0; if let Ok(env_value) = env::var("LEAF_TO_SPEND_FROM") { if let Ok(parsed_value) = env_value.parse::() { leaf_to_spend_from = parsed_value; } } // For Mixed mode, allow overriding the type of the leaf of interest let leaf_to_spend_from_type: Option = if leaf_script_type == LeafScriptType::Mixed { env::var("LEAF_TO_SPEND_FROM_TYPE").ok().map(|s| LeafScriptType::from_string(&s)) } else { None }; if total_leaf_count < 1 { panic!("total_leaf_count must be greater than 0"); } if leaf_to_spend_from >= total_leaf_count { panic!("leaf_to_spend_from must be less than total_leaf_count and greater than 0"); } debug!("Creating multi-leaf taptree with total_leaf_count: {}, leaf_to_spend_from: {}", total_leaf_count, leaf_to_spend_from); let mut huffman_entries: Vec<(u32, ScriptBuf)> = vec![]; let mut keypairs_of_interest: Option = None; let mut script_buf_of_interest: Option = None; let mut actual_leaf_type_of_interest: LeafScriptType = leaf_script_type; for leaf_index in 0..total_leaf_count { let keypairs: MultiKeypair; let script_buf: ScriptBuf; // Determine the effective script type for this leaf let effective_script_type = if leaf_script_type == LeafScriptType::Mixed { // For Mixed mode, check if this is the leaf of interest with an override if leaf_index == leaf_to_spend_from && leaf_to_spend_from_type.is_some() { leaf_to_spend_from_type.unwrap() } else { // Default pattern: even indices use Schnorr, odd indices use SLH-DSA if leaf_index % 2 == 0 { LeafScriptType::SchnorrOnly } else { LeafScriptType::SlhDsaOnly } } } else { leaf_script_type }; match effective_script_type { LeafScriptType::SchnorrOnly => { let schnorr_keypair = acquire_schnorr_keypair(); keypairs = MultiKeypair::new_schnorr_only(schnorr_keypair); let pubkey_bytes = keypairs.schnorr_keypair().unwrap().public_key_bytes(); // OP_PUSHBYTES_32 <32-byte xonly pubkey> OP_CHECKSIG let mut script_buf_bytes = vec![0x20]; script_buf_bytes.extend_from_slice(&pubkey_bytes); script_buf_bytes.push(0xac); // OP_CHECKSIG script_buf = ScriptBuf::from_bytes(script_buf_bytes); }, LeafScriptType::SlhDsaOnly => { let slh_dsa_keypair = acquire_slh_dsa_keypair(); keypairs = MultiKeypair::new_slh_dsa_only(slh_dsa_keypair); let pubkey_bytes = keypairs.slh_dsa_keypair().unwrap().public_key_bytes(); // OP_PUSHBYTES_32 <32-byte pubkey> OP_SUBSTR let mut script_buf_bytes = vec![0x20]; script_buf_bytes.extend_from_slice(&pubkey_bytes); script_buf_bytes.push(0x7f); // OP_SUBSTR script_buf = ScriptBuf::from_bytes(script_buf_bytes); }, LeafScriptType::ConcatenatedSchnorrAndSlhDsaSameLeaf => { // For combined scripts, we need both keypairs let schnorr_keypair = acquire_schnorr_keypair(); let slh_dsa_keypair = acquire_slh_dsa_keypair(); keypairs = MultiKeypair::new_combined(schnorr_keypair, slh_dsa_keypair); let schnorr_pubkey = keypairs.schnorr_keypair().unwrap().public_key_bytes(); let slh_dsa_pubkey = keypairs.slh_dsa_keypair().unwrap().public_key_bytes(); // Debug: Print the private key used for script construction info!("SLH-DSA DEBUG: Script construction using private key: {}", hex::encode(keypairs.slh_dsa_keypair().unwrap().secret_key_bytes())); info!("SLH-DSA DEBUG: Script construction using public key: {}", hex::encode(&slh_dsa_pubkey)); // Combined script: OP_CHECKSIG OP_SUBSTR OP_BOOLAND OP_VERIFY let mut script_buf_bytes = vec![0x20]; // OP_PUSHBYTES_32 script_buf_bytes.extend_from_slice(&schnorr_pubkey); script_buf_bytes.push(0xac); // OP_CHECKSIG script_buf_bytes.push(0x20); // OP_PUSHBYTES_32 script_buf_bytes.extend_from_slice(&slh_dsa_pubkey); script_buf_bytes.push(0x7f); // OP_SUBSTR script_buf_bytes.push(0x9a); // OP_BOOLAND script_buf_bytes.push(0x69); // OP_VERIFY script_buf = ScriptBuf::from_bytes(script_buf_bytes); } LeafScriptType::Mixed => { // This shouldn't happen as Mixed is resolved to a specific type above panic!("LeafScriptType::Mixed should have been resolved to a specific type"); } LeafScriptType::NotApplicable => { panic!("LeafScriptType::NotApplicable is not applicable"); } } let random_weight = thread_rng().gen_range(0..total_leaf_count); let huffman_entry = (random_weight, script_buf.clone()); huffman_entries.push(huffman_entry); if leaf_index == leaf_to_spend_from { keypairs_of_interest = Some(keypairs); script_buf_of_interest = Some(script_buf.clone()); actual_leaf_type_of_interest = effective_script_type; debug!("Selected leaf {}: type: {:?}, weight: {}, script: {:?}", leaf_index, effective_script_type, random_weight, script_buf); } } return (huffman_entries, keypairs_of_interest.unwrap(), script_buf_of_interest.unwrap(), actual_leaf_type_of_interest); } /// Parses the TAP_TREE_LOCK_TYPE environment variable and returns the corresponding LeafScriptType. /// Defaults to LeafScriptType::SchnorrOnly if the environment variable is not set. /// Exits with error code 1 if an invalid value is provided. /// /// Supported values: /// - SLH_DSA_ONLY: All leaves use SLH-DSA signatures /// - SCHNORR_ONLY: All leaves use Schnorr signatures /// - CONCATENATED_SCHNORR_AND_SLH_DSA: All leaves require both Schnorr and SLH-DSA signatures /// - MIXED: Different leaves use different algorithms (Schnorr or SLH-DSA) (default) pub fn tap_tree_lock_type() -> LeafScriptType { match env::var("TAP_TREE_LOCK_TYPE") { Ok(value) => match value.as_str() { "SLH_DSA_ONLY" => LeafScriptType::SlhDsaOnly, "SCHNORR_ONLY" => LeafScriptType::SchnorrOnly, "CONCATENATED_SCHNORR_AND_SLH_DSA" => LeafScriptType::ConcatenatedSchnorrAndSlhDsaSameLeaf, "MIXED" => LeafScriptType::Mixed, _ => { error!("Invalid TAP_TREE_LOCK_TYPE '{}'. Must be one of: SLH_DSA_ONLY, SCHNORR_ONLY, CONCATENATED_SCHNORR_AND_SLH_DSA, MIXED", value); std::process::exit(1); } }, Err(_) => { // Default to Mixed if not set LeafScriptType::Mixed } } } pub fn create_p2mr_multi_leaf_taptree() -> TaptreeReturn { let leaf_script_type = tap_tree_lock_type(); let (huffman_entries, keypairs_of_interest, script_buf_of_interest, actual_leaf_type) = create_huffman_tree(leaf_script_type); let p2mr_builder: P2mrBuilder = P2mrBuilder::with_huffman_tree(huffman_entries).unwrap(); let p2mr_spend_info: P2mrSpendInfo = p2mr_builder.clone().finalize().unwrap(); let merkle_root:TapNodeHash = p2mr_spend_info.merkle_root.unwrap(); let tap_tree: TapTree = p2mr_builder.clone().into_inner().try_into_taptree().unwrap(); let mut script_leaves: ScriptLeaves = tap_tree.script_leaves(); let script_leaf = script_leaves .find(|leaf| leaf.script() == script_buf_of_interest.as_script()) .expect("Script leaf not found"); let merkle_root_node_info: NodeInfo = p2mr_builder.clone().into_inner().try_into_node_info().unwrap(); let merkle_root: TapNodeHash = merkle_root_node_info.node_hash(); let leaf_hash: TapLeafHash = TapLeafHash::from_script(script_leaf.script(), LeafVersion::from_consensus(P2MR_LEAF_VERSION).unwrap()); // Convert leaf hash to big-endian for display (like Bitcoin Core) let mut leaf_hash_bytes = leaf_hash.as_raw_hash().to_byte_array().to_vec(); leaf_hash_bytes.reverse(); info!("leaf_hash: {}, merkle_root: {}, merkle_root: {}", hex::encode(leaf_hash_bytes), merkle_root, merkle_root); let leaf_script = script_leaf.script(); let merkle_branch: &TaprootMerkleBranch = script_leaf.merkle_branch(); info!("Leaf script: {}, merkle branch: {:?}", leaf_script, merkle_branch); let control_block: P2mrControlBlock = P2mrControlBlock{ merkle_branch: merkle_branch.clone(), }; // Not a requirement here but useful to demonstrate what Bitcoin Core does as the verifier when spending from a p2mr UTXO control_block.verify_script_in_merkle_root_path(leaf_script, merkle_root); let control_block_hex: String = hex::encode(control_block.serialize()); return TaptreeReturn { leaf_script_priv_keys_hex: keypairs_of_interest.secret_key_bytes() .into_iter() .map(|bytes| hex::encode(bytes)) .collect(), leaf_script_hex: leaf_script.to_hex_string(), tree_root_hex: hex::encode(merkle_root.to_byte_array()), control_block_hex: control_block_hex, leaf_script_type: actual_leaf_type.to_string(), }; } pub fn create_p2tr_multi_leaf_taptree(p2tr_internal_pubkey_hex: String) -> TaptreeReturn { let (huffman_entries, keypairs_of_interest, script_buf_of_interest, actual_leaf_type) = create_huffman_tree(LeafScriptType::SchnorrOnly); let pub_key_string = format!("02{}", p2tr_internal_pubkey_hex); let internal_pubkey: PublicKey = pub_key_string.parse::().unwrap(); let internal_xonly_pubkey: XOnlyPublicKey = internal_pubkey.inner.into(); let p2tr_builder: TaprootBuilder = TaprootBuilder::with_huffman_tree(huffman_entries).unwrap(); let p2tr_spend_info: TaprootSpendInfo = p2tr_builder.clone().finalize(&SECP, internal_xonly_pubkey).unwrap(); let merkle_root: TapNodeHash = p2tr_spend_info.merkle_root().unwrap(); // During taproot construction, the internal key is "tweaked" by adding a scalar (the tap tweak hash) to it. // If this tweaking operation results in a public key w/ an odd Y-coordinate, the parity bit is set to 1. // When spending via script path, the verifier needs to know whether the output key has an even or odd Y-coordinate to properly reconstruct & verify the internal key. // The internal key can be recovered from the output key using the parity bit and the merkle root. let output_key_parity: Parity = p2tr_spend_info.output_key_parity(); let output_key: XOnlyPublicKey = p2tr_spend_info.output_key().into(); info!("keypairs_of_interest: \n\tsecret_bytes: {:?} \n\tpubkeys: {:?} \n\tmerkle_root: {}", keypairs_of_interest.secret_key_bytes().iter().map(|bytes| hex::encode(bytes)).collect::>(), // secret_bytes returns big endian keypairs_of_interest.public_key_bytes().iter().map(|bytes| hex::encode(bytes)).collect::>(), // serialize returns little endian merkle_root); let tap_tree: TapTree = p2tr_builder.clone().try_into_taptree().unwrap(); let mut script_leaves: ScriptLeaves = tap_tree.script_leaves(); let script_leaf = script_leaves .find(|leaf| leaf.script() == script_buf_of_interest.as_script()) .expect("Script leaf not found"); let leaf_script = script_leaf.script().to_hex_string(); let merkle_branch: &TaprootMerkleBranch = script_leaf.merkle_branch(); debug!("Leaf script: {}, merkle branch: {:?}", leaf_script, merkle_branch); let control_block: ControlBlock = ControlBlock{ leaf_version: LeafVersion::TapScript, output_key_parity: output_key_parity, internal_key: internal_xonly_pubkey, merkle_branch: merkle_branch.clone(), }; let control_block_hex: String = hex::encode(control_block.serialize()); // Not a requirement but useful to demonstrate what Bitcoin Core does as the verifier when spending from a p2tr UTXO let verify: bool = verify_taproot_commitment(control_block_hex.clone(), output_key, script_leaf.script()); info!("verify_taproot_commitment: {}", verify); return TaptreeReturn { leaf_script_priv_keys_hex: keypairs_of_interest.secret_key_bytes() .into_iter() .map(|bytes| hex::encode(bytes)) .collect(), leaf_script_hex: leaf_script, tree_root_hex: hex::encode(merkle_root.to_byte_array()), control_block_hex: control_block_hex, leaf_script_type: actual_leaf_type.to_string(), }; } /// Parses the BITCOIN_NETWORK environment variable and returns the corresponding Network. /// Defaults to Network::Regtest if the environment variable is not set or has an invalid value. pub fn get_bitcoin_network() -> Network { let mut bitcoin_network: Network = Network::Regtest; // Check for BITCOIN_NETWORK environment variable and override if set if let Ok(network_str) = std::env::var("BITCOIN_NETWORK") { bitcoin_network = match network_str.to_lowercase().as_str() { "regtest" => Network::Regtest, "testnet" => Network::Testnet, "signet" => Network::Signet, _ => { debug!("Invalid BITCOIN_NETWORK value '{}', using default Regtest network", network_str); Network::Regtest } }; } bitcoin_network } pub fn create_p2mr_utxo(merkle_root_hex: String) -> UtxoReturn { let merkle_root_bytes= hex::decode(merkle_root_hex.clone()).unwrap(); let merkle_root: TapNodeHash = TapNodeHash::from_byte_array(merkle_root_bytes.try_into().unwrap()); /* commit (in scriptPubKey) to the merkle root of all the script path leaves. ie: This output key is what gets committed to in the final P2MR address (ie: scriptPubKey) */ let script_buf: P2mrScriptBuf = P2mrScriptBuf::new_p2mr(merkle_root); let script: &Script = script_buf.as_script(); let script_pubkey = script.to_hex_string(); let bitcoin_network = get_bitcoin_network(); // derive bech32m address and verify against test vector // p2mr address is comprised of network HRP + WitnessProgram (version + program) let bech32m_address = Address::p2mr(Some(merkle_root), bitcoin_network); return UtxoReturn { script_pubkey_hex: script_pubkey, bech32m_address: bech32m_address.to_string(), bitcoin_network, }; } // Given script path p2tr or p2mr UTXO details, spend to p2wpkh pub fn pay_to_p2wpkh_tx( funding_tx_id_bytes: Vec, funding_utxo_index: u32, funding_utxo_amount_sats: u64, funding_script_pubkey_bytes: Vec, control_block_bytes: Vec, leaf_script_bytes: Vec, leaf_script_priv_keys_bytes: Vec>, // Changed to support multiple private keys spend_output_pubkey_hash_bytes: Vec, spend_output_amount_sats: u64, leaf_script_type: LeafScriptType ) -> SpendDetails { let mut txid_little_endian = funding_tx_id_bytes.clone(); // initially in big endian format txid_little_endian.reverse(); // convert to little endian format // vin: Create TxIn from the input utxo // Details of this input tx are not known at this point let input_tx_in = bitcoin::TxIn { previous_output: OutPoint { txid: bitcoin::Txid::from_slice(&txid_little_endian).unwrap(), // bitcoin::Txid expects the bytes in little-endian format vout: funding_utxo_index, }, script_sig: ScriptBuf::new(), // Empty for segwit transactions - script goes in witness sequence: Sequence::MAX, // Default sequence, allows immediate spending (no RBF or timelock) witness: bitcoin::Witness::new(), // Empty for now, will be filled with signature and pubkey after signing }; let spend_wpubkey_hash = WPubkeyHash::from_byte_array(spend_output_pubkey_hash_bytes.try_into().unwrap()); let spend_output: TxOut = TxOut { value: Amount::from_sat(spend_output_amount_sats), script_pubkey: ScriptBuf::new_p2wpkh(&spend_wpubkey_hash), }; // The spend tx to eventually be signed and broadcast let mut unsigned_spend_tx = Transaction { version: bitcoin::transaction::Version::TWO, lock_time: bitcoin::locktime::absolute::LockTime::ZERO, input: vec![input_tx_in], output: vec![spend_output], }; // Create the leaf hash let leaf_script = ScriptBuf::from_bytes(leaf_script_bytes.clone()); let leaf_hash: TapLeafHash = TapLeafHash::from_script(&leaf_script, LeafVersion::TapScript); /* prevouts parameter tells the sighash algorithm: 1. The value of each input being spent (needed for fee calculation and sighash computation) 2. The scriptPubKey of each input being spent (ie: type of output & how to validate the spend) */ let prevouts = vec![TxOut { value: Amount::from_sat(funding_utxo_amount_sats), script_pubkey: ScriptBuf::from_bytes(funding_script_pubkey_bytes.clone()), }]; info!("prevouts: {:?}", prevouts); let spending_tx_input_index = 0; // Create SighashCache // At this point, sighash_cache does not know the values and type of input UTXO let mut tapscript_sighash_cache = SighashCache::new(&mut unsigned_spend_tx); // Compute the sighash let tapscript_sighash: TapSighash = tapscript_sighash_cache.taproot_script_spend_signature_hash( spending_tx_input_index, // input_index &Prevouts::All(&prevouts), leaf_hash, TapSighashType::All ).unwrap(); info!("sighash: {:?}", tapscript_sighash); let spend_msg = Message::from(tapscript_sighash); let mut derived_witness: Witness = Witness::new(); let mut sig_bytes = Vec::new(); match leaf_script_type { LeafScriptType::SlhDsaOnly => { if leaf_script_priv_keys_bytes.len() != 1 { panic!("SlhDsaOnly requires exactly one private key"); } let secret_key: bitcoinpqc::SecretKey = bitcoinpqc::SecretKey::try_from_slice( Algorithm::SLH_DSA_128S, &leaf_script_priv_keys_bytes[0]).unwrap(); let signature = sign(&secret_key, spend_msg.as_ref()).expect("Failed to sign with SLH-DSA-128S"); debug!("SlhDsaOnly signature.bytes: {:?}", signature.bytes.len()); let mut sig_bytes_with_sighash = signature.bytes.clone(); sig_bytes_with_sighash.push(TapSighashType::All as u8); derived_witness.push(&sig_bytes_with_sighash); sig_bytes = signature.bytes; }, LeafScriptType::SchnorrOnly => { if leaf_script_priv_keys_bytes.len() != 1 { panic!("SchnorrOnly requires exactly one private key"); } // assumes bytes are in big endian format let secret_key = SecretKey::from_slice(&leaf_script_priv_keys_bytes[0]).unwrap(); // Spending a p2tr UTXO thus using Schnorr signature // The aux_rand parameter ensures that signing the same message with the same key produces the same signature // Otherwise (without providing aux_rand), the secp256k1 library internally generates a random nonce for each signature let signature: bitcoin::secp256k1::schnorr::Signature = SECP.sign_schnorr_with_aux_rand( &spend_msg, &secret_key.keypair(&SECP), &[0u8; 32] // 32 zero bytes of auxiliary random data ); sig_bytes = signature.serialize().to_vec(); let mut sig_bytes_with_sighash = sig_bytes.clone(); sig_bytes_with_sighash.push(TapSighashType::All as u8); derived_witness.push(&sig_bytes_with_sighash); debug!("SchnorrOnly signature bytes: {:?}", sig_bytes.len()); }, LeafScriptType::ConcatenatedSchnorrAndSlhDsaSameLeaf => { if leaf_script_priv_keys_bytes.len() != 2 { panic!("SchnorrAndSlhDsa requires exactly two private keys (Schnorr first, then SLH-DSA)"); } // Generate Schnorr signature (first key) let schnorr_secret_key = SecretKey::from_slice(&leaf_script_priv_keys_bytes[0]).unwrap(); let schnorr_signature: bitcoin::secp256k1::schnorr::Signature = SECP.sign_schnorr_with_aux_rand( &spend_msg, &schnorr_secret_key.keypair(&SECP), &[0u8; 32] // 32 zero bytes of auxiliary random data ); // Build combined signature for return value (without sighash bytes) let mut combined_sig_bytes = schnorr_signature.serialize().to_vec(); debug!("SchnorrAndSlhDsa schnorr_sig_bytes: {:?}", combined_sig_bytes.len()); // Generate SLH-DSA signature (second key) let slh_dsa_secret_key: bitcoinpqc::SecretKey = bitcoinpqc::SecretKey::try_from_slice( Algorithm::SLH_DSA_128S, &leaf_script_priv_keys_bytes[1]).unwrap(); // Debug: Print the private key being used for signature creation info!("SLH-DSA DEBUG: Using private key for signature creation: {}", hex::encode(&leaf_script_priv_keys_bytes[1])); let slh_dsa_signature = sign(&slh_dsa_secret_key, spend_msg.as_ref()).expect("Failed to sign with SLH-DSA-128S"); debug!("SchnorrAndSlhDsa slh_dsa_signature.bytes: {:?}", slh_dsa_signature.bytes.len()); // Add SLH-DSA signature to combined signature for return value combined_sig_bytes.extend_from_slice(&slh_dsa_signature.bytes); sig_bytes = combined_sig_bytes; // Build witness with sighash bytes let mut witness_sig_bytes = schnorr_signature.serialize().to_vec(); witness_sig_bytes.push(TapSighashType::All as u8); witness_sig_bytes.extend_from_slice(&slh_dsa_signature.bytes); witness_sig_bytes.push(TapSighashType::All as u8); derived_witness.push(&witness_sig_bytes); } LeafScriptType::Mixed => { // Mixed is not a valid type for spending - the actual leaf type should be used panic!("LeafScriptType::Mixed is not valid for spending. Use the actual leaf type (SchnorrOnly or SlhDsaOnly)."); } LeafScriptType::NotApplicable => { panic!("LeafScriptType::NotApplicable is not applicable"); } } // Note: sighash byte is now appended to signatures, not as separate witness element derived_witness.push(&leaf_script_bytes); derived_witness.push(&control_block_bytes); let derived_witness_vec: Vec = derived_witness.iter().flatten().cloned().collect(); // Update the witness data for the tx's first input (index 0) *tapscript_sighash_cache.witness_mut(spending_tx_input_index).unwrap() = derived_witness; // Get the signed transaction. let signed_tx_obj: &mut Transaction = tapscript_sighash_cache.into_transaction(); let tx_hex = bitcoin::consensus::encode::serialize_hex(&signed_tx_obj); return SpendDetails { tx_hex, sighash: tapscript_sighash.as_byte_array().to_vec(), sig_bytes: sig_bytes, derived_witness_vec: derived_witness_vec, }; } pub fn create_p2tr_utxo(merkle_root_hex: String, internal_pubkey_hex: String) -> UtxoReturn { let merkle_root_bytes= hex::decode(merkle_root_hex.clone()).unwrap(); let merkle_root: TapNodeHash = TapNodeHash::from_byte_array(merkle_root_bytes.try_into().unwrap()); let pub_key_string = format!("02{}", internal_pubkey_hex); let internal_pubkey: PublicKey = pub_key_string.parse::().unwrap(); let internal_xonly_pubkey: XOnlyPublicKey = internal_pubkey.inner.into(); let script_buf: ScriptBuf = ScriptBuf::new_p2tr(&SECP, internal_xonly_pubkey, Option::Some(merkle_root)); let script: &Script = script_buf.as_script(); let script_pubkey = script.to_hex_string(); let bitcoin_network = get_bitcoin_network(); // 4) derive bech32m address and verify against test vector // p2mr address is comprised of network HRP + WitnessProgram (version + program) let bech32m_address = Address::p2tr( &SECP, internal_xonly_pubkey, Option::Some(merkle_root), bitcoin_network ); return UtxoReturn { script_pubkey_hex: script_pubkey, bech32m_address: bech32m_address.to_string(), bitcoin_network, }; } // https://learnmeabitcoin.com/technical/upgrades/taproot/#examples pub fn tagged_hash(tag: &str, data: &[u8]) -> String { // Create a hash of the tag first let tag_hash = sha256::Hash::hash(tag.as_bytes()); // Create preimage: tag_hash || tag_hash || message // tag_hash is prefixed twice so that the prefix is 64 bytes in total let mut preimage = sha256::Hash::engine(); preimage.write_all(&tag_hash.to_byte_array()).unwrap(); // First tag hash preimage.write_all(&tag_hash.to_byte_array()).unwrap(); // Second tag hash preimage.write_all(data).unwrap(); // Message data let hash = sha256::Hash::from_engine(preimage).to_byte_array(); hex::encode(hash) } pub fn serialize_script(script: &Vec) -> Vec { // get length of script as number of bytes let length = script.len(); // return script with compact size prepended let mut result = compact_size(length as u64); result.extend_from_slice(&script); result } /// Encodes an integer into Bitcoin's compact size format /// Returns a Vec containing the encoded bytes fn compact_size(n: u64) -> Vec { if n <= 252 { vec![n as u8] } else if n <= 0xffff { let mut result = vec![0xfd]; result.extend_from_slice(&(n as u16).to_le_bytes()); result } else if n <= 0xffffffff { let mut result = vec![0xfe]; result.extend_from_slice(&(n as u32).to_le_bytes()); result } else { let mut result = vec![0xff]; result.extend_from_slice(&n.to_le_bytes()); result } } pub fn acquire_schnorr_keypair() -> UnifiedKeypair { /* OsRng typically draws from the OS's entropy pool (hardware random num generators, system events, etc), ie: * 1. $ cat /proc/sys/kernel/random/entropy_avail * 2. $ sudo dmesg | grep -i "random\|rng\|entropy" The Linux kernel's RNG (/dev/random and /dev/urandom) typically combines multiple entropy sources: ie: * Hardware RNG (if available) * CPU RNG instructions (RDRAND/RDSEED) * Hardware events (disk I/O, network packets, keyboard/mouse input) * Timer jitter * Interrupt timing */ let keypair = Keypair::new(&SECP, &mut OsRng); let privkey: SecretKey = keypair.secret_key(); let pubkey: (XOnlyPublicKey, Parity) = XOnlyPublicKey::from_keypair(&keypair); UnifiedKeypair::new_schnorr(privkey, pubkey.0) } pub fn verify_schnorr_signature_via_bytes(signature: &[u8], message: &[u8], pubkey_bytes: &[u8]) -> bool { // schnorr is 64 bytes so remove possible trailing Sighash Type byte if present let mut sig_bytes = signature.to_vec(); if sig_bytes.len() == 65 { sig_bytes.pop(); // Remove the last byte } let signature = bitcoin::secp256k1::schnorr::Signature::from_slice(&sig_bytes).unwrap(); let message = Message::from_digest_slice(message).unwrap(); let pubkey = XOnlyPublicKey::from_slice(pubkey_bytes).unwrap(); verify_schnorr_signature(signature, message, pubkey) } pub fn verify_slh_dsa_via_bytes(signature: &[u8], message: &[u8], pubkey_bytes: &[u8]) -> bool { // Remove possible trailing Sighash Type byte if present (SLH-DSA-128S is 7856 bytes, so 7857 would indicate SIGHASH byte) let mut sig_bytes = signature.to_vec(); if sig_bytes.len() == 7857 { sig_bytes.pop(); // Remove the last byte } info!("verify_slh_dsa_via_bytes: signature length: {:?}, message: {:?}, pubkey_bytes: {:?}", sig_bytes.len(), hex::encode(message), hex::encode(pubkey_bytes)); let signature = bitcoinpqc::Signature::try_from_slice(Algorithm::SLH_DSA_128S, &sig_bytes).unwrap(); let public_key: bitcoinpqc::PublicKey = bitcoinpqc::PublicKey::try_from_slice(Algorithm::SLH_DSA_128S, pubkey_bytes).unwrap(); verify(&public_key, message, &signature).is_ok() } pub fn verify_schnorr_signature(mut signature: Signature, message: Message, pubkey: XOnlyPublicKey) -> bool { // schnorr is 64 bytes so remove possible trailing Sighash Type byte if present if signature.serialize().to_vec().len() == 65 { let mut sig_bytes = signature.serialize().to_vec(); sig_bytes.pop(); // Remove the last byte signature = bitcoin::secp256k1::schnorr::Signature::from_slice(&sig_bytes).unwrap(); } let is_valid: bool = SECP.verify_schnorr(&signature, &message, &pubkey).is_ok(); if !is_valid { error!("verify schnorr failed:\n\tsignature: {:?}\n\tmessage: {:?}\n\tpubkey: {:?}", signature, message, hex::encode(pubkey.serialize())); } is_valid } /* 1. Re-constructs merkle_root from merkle_path (found in control_block) and provided script. 2. Determines the parity of the output key via the control byte (found in the control block). - the parity bit indicates whether the output key has an even or odd Y-coordinate 3. Computes the tap tweak hash using the internal key and reconstructed merkle root. - tap_tweak_hash = tagged_hash("TapTweak", internal_key || merkle_root) 4. Verifies that the provided output key can be derived from the internal key using the tweak. - tap_tweak_hash = tagged_hash("TapTweak", internal_key || merkle_root) 5. This proves the script is committed to in the taptree described by the output key. */ pub fn verify_taproot_commitment(control_block_hex: String, output_key: XOnlyPublicKey, script: &Script) -> bool { let control_block_bytes = hex::decode(control_block_hex).unwrap(); let control_block: ControlBlock = ControlBlock::decode(&control_block_bytes).unwrap(); return control_block.verify_taproot_commitment(&SECP, output_key, script); } fn acquire_slh_dsa_keypair() -> UnifiedKeypair { /* In SPHINCS+ (underlying algorithm of SLH-DSA), the random data is used to: * Initialize hash function parameters within the key generation * Seed the Merkle tree construction that forms the public key * Generate the secret key components that enable signing */ let random_data = get_random_bytes(128); let keypair: KeyPair = generate_keypair(Algorithm::SLH_DSA_128S, &random_data) .expect("Failed to generate SLH-DSA-128S keypair"); UnifiedKeypair::new_slh_dsa(keypair) } fn get_random_bytes(size: usize) -> Vec { let mut bytes = vec![0u8; size]; rng().fill_bytes(&mut bytes); bytes } ================================================ FILE: bip-0360/ref-impl/rust/tests/p2mr_construction.rs ================================================ use std::collections::HashSet; use bitcoin::{Network, ScriptBuf}; use bitcoin::taproot::{LeafVersion, TapTree, ScriptLeaves, TapLeafHash, TaprootMerkleBranch, TapNodeHash}; use bitcoin::p2mr::{P2mrBuilder, P2mrControlBlock, P2mrSpendInfo}; use bitcoin::hashes::Hash; use hex; use log::debug; use once_cell::sync::Lazy; use p2mr_ref::data_structures::{TVScriptTree, TestVector, Direction, TestVectors, UtxoReturn}; use p2mr_ref::error::P2MRError; use p2mr_ref::{create_p2mr_utxo, tagged_hash}; // This file contains tests that execute against the BIP360 script-path-only test vectors. static TEST_VECTORS: Lazy = Lazy::new(|| { let bip360_test_vectors = include_str!("../../common/tests/data/p2mr_construction.json"); let test_vectors: TestVectors = serde_json::from_str(bip360_test_vectors).unwrap(); assert_eq!(test_vectors.version, 1); test_vectors }); static P2TR_USING_V2_WITNESS_VERSION_ERROR: &str = "p2tr_using_v2_witness_version_error"; static P2MR_MISSING_LEAF_SCRIPT_TREE_ERROR_TEST: &str = "p2mr_missing_leaf_script_tree_error"; static P2MR_SINGLE_LEAF_SCRIPT_TREE_TEST: &str = "p2mr_single_leaf_script_tree"; static P2MR_DIFFERENT_VERSION_LEAVES_TEST: &str = "p2mr_different_version_leaves"; static P2MR_TWO_LEAF_SAME_VERSION_TEST: &str = "p2mr_two_leaf_same_version"; static P2MR_THREE_LEAF_COMPLEX_TEST: &str = "p2mr_three_leaf_complex"; static P2MR_THREE_LEAF_ALTERNATIVE_TEST: &str = "p2mr_three_leaf_alternative"; static P2MR_SIMPLE_LIGHTNING_CONTRACT_TEST: &str = "p2mr_simple_lightning_contract"; #[test] fn test_p2tr_using_v2_witness_version_error() { let _ = env_logger::try_init(); // Use try_init to avoid reinitialization error let test_vectors = &*TEST_VECTORS; let test_vector = test_vectors.test_vector_map.get(P2TR_USING_V2_WITNESS_VERSION_ERROR).unwrap(); let test_result: anyhow::Result<()> = process_test_vector_p2tr(test_vector); assert!(matches!(test_result.unwrap_err().downcast_ref::(), Some(P2MRError::P2trRequiresWitnessVersion1))); } // https://learnmeabitcoin.com/technical/upgrades/taproot/#example-2-script-path-spend-simple #[test] fn test_p2mr_missing_leaf_script_tree_error() { let _ = env_logger::try_init(); // Use try_init to avoid reinitialization error let test_vectors = &*TEST_VECTORS; let test_vector = test_vectors.test_vector_map.get(P2MR_MISSING_LEAF_SCRIPT_TREE_ERROR_TEST).unwrap(); let test_result: anyhow::Result<()> = process_test_vector_p2mr(test_vector); assert!(matches!(test_result.unwrap_err().downcast_ref::(), Some(P2MRError::MissingScriptTreeLeaf))); } // https://learnmeabitcoin.com/technical/upgrades/taproot/#example-2-script-path-spend-simple #[test] fn test_p2mr_single_leaf_script_tree() { let _ = env_logger::try_init(); // Use try_init to avoid reinitialization error let test_vectors = &*TEST_VECTORS; let test_vector = test_vectors.test_vector_map.get(P2MR_SINGLE_LEAF_SCRIPT_TREE_TEST).unwrap(); process_test_vector_p2mr(test_vector).unwrap(); } #[test] fn test_p2mr_different_version_leaves() { let _ = env_logger::try_init(); // Use try_init to avoid reinitialization error let test_vectors = &*TEST_VECTORS; let test_vector = test_vectors.test_vector_map.get(P2MR_DIFFERENT_VERSION_LEAVES_TEST).unwrap(); process_test_vector_p2mr(test_vector).unwrap(); } #[test] fn test_p2mr_simple_lightning_contract() { let _ = env_logger::try_init(); // Use try_init to avoid reinitialization error let test_vectors = &*TEST_VECTORS; let test_vector = test_vectors.test_vector_map.get(P2MR_SIMPLE_LIGHTNING_CONTRACT_TEST).unwrap(); process_test_vector_p2mr(test_vector).unwrap(); } #[test] fn test_p2mr_two_leaf_same_version() { let _ = env_logger::try_init(); // Use try_init to avoid reinitialization error let test_vectors = &*TEST_VECTORS; let test_vector = test_vectors.test_vector_map.get(P2MR_TWO_LEAF_SAME_VERSION_TEST).unwrap(); process_test_vector_p2mr(test_vector).unwrap(); } #[test] fn test_p2mr_three_leaf_complex() { let _ = env_logger::try_init(); // Use try_init to avoid reinitialization error let test_vectors = &*TEST_VECTORS; let test_vector = test_vectors.test_vector_map.get(P2MR_THREE_LEAF_COMPLEX_TEST).unwrap(); process_test_vector_p2mr(test_vector).unwrap(); } #[test] fn test_p2mr_three_leaf_alternative() { let _ = env_logger::try_init(); // Use try_init to avoid reinitialization error let test_vectors = &*TEST_VECTORS; let test_vector = test_vectors.test_vector_map.get(P2MR_THREE_LEAF_ALTERNATIVE_TEST).unwrap(); process_test_vector_p2mr(test_vector).unwrap(); } fn process_test_vector_p2tr(test_vector: &TestVector) -> anyhow::Result<()> { let script_pubkey_hex = test_vector.expected.script_pubkey.as_ref().unwrap(); let script_pubkey_bytes = hex::decode(script_pubkey_hex).unwrap(); if script_pubkey_bytes[0] != 0x51 { return Err(P2MRError::P2trRequiresWitnessVersion1.into()); } Ok(()) } fn process_test_vector_p2mr(test_vector: &TestVector) -> anyhow::Result<()> { let tv_script_tree: Option<&TVScriptTree> = test_vector.given.script_tree.as_ref(); let mut tv_leaf_count: u8 = 0; let mut current_branch_id: u8 = 0; // TaprootBuilder expects the addition of each leaf script with its associated depth // It then constructs the binary tree in DFS order, sorting siblings lexicographically & combining them via BIP341's tapbranch_hash // Use of TaprootBuilder avoids user error in constructing branches manually and ensures Merkle tree correctness and determinism let mut p2mr_builder: P2mrBuilder = P2mrBuilder::new(); let mut control_block_data: Vec<(ScriptBuf, LeafVersion)> = Vec::new(); // 1) traverse test vector script tree and add leaves to P2MR builder if let Some(script_tree) = tv_script_tree { script_tree.traverse_with_right_subtree_first(0, Direction::Root,&mut |node, depth, direction| { if let TVScriptTree::Leaf(tv_leaf) = node { let tv_leaf_script_bytes = hex::decode(&tv_leaf.script).unwrap(); // NOTE: IOT to execute script_info.control_block(..), will add these to a vector let tv_leaf_script_buf = ScriptBuf::from_bytes(tv_leaf_script_bytes.clone()); let tv_leaf_version = LeafVersion::from_consensus(tv_leaf.leaf_version).unwrap(); control_block_data.push((tv_leaf_script_buf.clone(), tv_leaf_version)); let mut modified_depth = depth + 1; if direction == Direction::Root { modified_depth = depth; } debug!("traverse_with_depth: leaf_count: {}, depth: {}, modified_depth: {}, direction: {}, tv_leaf_script: {}", tv_leaf_count, depth, modified_depth, direction, tv_leaf.script); // NOTE: Some of the the test vectors in this project specify leaves with non-standard versions (ie: 250 / 0xfa) p2mr_builder = p2mr_builder.clone().add_leaf_with_ver(depth, tv_leaf_script_buf.clone(), tv_leaf_version) .unwrap_or_else(|e| { panic!("Failed to add leaf: {:?}", e); }); tv_leaf_count += 1; } else if let TVScriptTree::Branch { left, right } = node { // No need to calculate branch hash. // TaprootBuilder does this for us. debug!("branch_count: {}, depth: {}, direction: {}", current_branch_id, depth, direction); current_branch_id += 1; } }); }else { return Err(P2MRError::MissingScriptTreeLeaf.into()); } let spend_info: P2mrSpendInfo = p2mr_builder.clone() .finalize() .unwrap_or_else(|e| { panic!("finalize failed: {:?}", e); }); let derived_merkle_root: TapNodeHash = spend_info.merkle_root.unwrap(); // 2) verify derived merkle root against test vector let test_vector_merkle_root = test_vector.intermediary.merkle_root.as_ref().unwrap(); assert_eq!( derived_merkle_root.to_string(), *test_vector_merkle_root, "Merkle root mismatch" ); debug!("just passed merkle root validation: {}", test_vector_merkle_root); let test_vector_leaf_hashes_vec: Vec = test_vector.intermediary.leaf_hashes.clone(); let test_vector_leaf_hash_set: HashSet = test_vector_leaf_hashes_vec.iter().cloned().collect(); let test_vector_control_blocks_vec = &test_vector.expected.script_path_control_blocks; let test_vector_control_blocks_set: HashSet = test_vector_control_blocks_vec.as_ref().unwrap().iter().cloned().collect(); let tap_tree: TapTree = p2mr_builder.clone().into_inner().try_into_taptree().unwrap(); let script_leaves: ScriptLeaves = tap_tree.script_leaves(); // TO-DO: Investigate why the ordering of script leaves seems to be reverse of test vectors. // 3) Iterate through leaves of derived script tree and verify both script leaf hashes and control blocks for derived_leaf in script_leaves { let version = derived_leaf.version(); let script = derived_leaf.script(); let merkle_branch: &TaprootMerkleBranch = derived_leaf.merkle_branch(); let derived_leaf_hash: TapLeafHash = TapLeafHash::from_script(script, version); let leaf_hash = hex::encode(derived_leaf_hash.as_raw_hash().to_byte_array()); assert!( test_vector_leaf_hash_set.contains(&leaf_hash), "Leaf hash not found in expected set for {}", leaf_hash ); debug!("just passed leaf_hash validation: {}", leaf_hash); // Each leaf in the script tree has a corresponding control block. // Specific to P2TR, the 3 sections of the control block (control byte, public key & merkle path) are highlighted here: // https://learnmeabitcoin.com/technical/upgrades/taproot/#script-path-spend-control-block // The control block, which includes the Merkle path, must be 33 + 32 * n bytes, where n is the number of Merkle path hashes (n ≥ 0). // There is no consensus limit on n, but large Merkle trees increase the witness size, impacting block weight. // NOTE: Control blocks could have also been obtained from spend_info.control_block(..) using the data in control_block_data debug!("merkle_branch nodes: {:?}", merkle_branch); let derived_control_block: P2mrControlBlock = P2mrControlBlock{ merkle_branch: merkle_branch.clone(), }; let serialized_control_block = derived_control_block.serialize(); debug!("derived_control_block: {:?}, merkle_branch size: {}, control_block size: {}, serialized size: {}", derived_control_block, merkle_branch.len(), derived_control_block.size(), serialized_control_block.len()); let derived_serialized_control_block = hex::encode(serialized_control_block); assert!( test_vector_control_blocks_set.contains(&derived_serialized_control_block), "Control block mismatch: {}, expected: {:?}", derived_serialized_control_block, test_vector_control_blocks_set ); debug!("leaf_hash: {}, derived_serialized_control_block: {}", leaf_hash, derived_serialized_control_block); } let p2mr_utxo_return: UtxoReturn = create_p2mr_utxo(derived_merkle_root.to_string()); assert_eq!( p2mr_utxo_return.script_pubkey_hex, *test_vector.expected.script_pubkey.as_ref().unwrap(), "Script pubkey mismatch" ); debug!("just passed script_pubkey validation. script_pubkey = {}", p2mr_utxo_return.script_pubkey_hex); let bech32m_address: String = p2mr_utxo_return.bech32m_address; debug!("derived bech32m address for bitcoin_network: {} : {}", p2mr_utxo_return.bitcoin_network, bech32m_address); if p2mr_utxo_return.bitcoin_network == Network::Bitcoin { assert_eq!(bech32m_address, *test_vector.expected.bip350_address.as_ref().unwrap(), "Bech32m address mismatch."); } Ok(()) } ================================================ FILE: bip-0360/ref-impl/rust/tests/p2mr_pqc_construction.rs ================================================ use std::collections::HashSet; use bitcoin::{Network, ScriptBuf}; use bitcoin::taproot::{LeafVersion, TapTree, ScriptLeaves, TapLeafHash, TaprootMerkleBranch, TapNodeHash}; use bitcoin::p2mr::{P2mrBuilder, P2mrControlBlock, P2mrSpendInfo}; use bitcoin::hashes::Hash; use hex; use log::debug; use once_cell::sync::Lazy; use p2mr_ref::data_structures::{TVScriptTree, TestVector, Direction, TestVectors, UtxoReturn}; use p2mr_ref::error::P2MRError; use p2mr_ref::{create_p2mr_utxo, tagged_hash}; // This file contains tests that execute against the BIP360 script-path-only test vectors. static TEST_VECTORS: Lazy = Lazy::new(|| { let bip360_test_vectors = include_str!("../../common/tests/data/p2mr_pqc_construction.json"); let test_vectors: TestVectors = serde_json::from_str(bip360_test_vectors).unwrap(); assert_eq!(test_vectors.version, 1); test_vectors }); static P2MR_MISSING_LEAF_SCRIPT_TREE_ERROR_TEST: &str = "p2mr_missing_leaf_script_tree_error"; static P2MR_SINGLE_LEAF_SCRIPT_TREE_TEST: &str = "p2mr_single_leaf_script_tree"; static P2MR_DIFFERENT_VERSION_LEAVES_TEST: &str = "p2mr_different_version_leaves"; static P2MR_TWO_LEAF_SAME_VERSION_TEST: &str = "p2mr_two_leaf_same_version"; static P2MR_THREE_LEAF_COMPLEX_TEST: &str = "p2mr_three_leaf_complex"; static P2MR_THREE_LEAF_ALTERNATIVE_TEST: &str = "p2mr_three_leaf_alternative"; static P2MR_SIMPLE_LIGHTNING_CONTRACT_TEST: &str = "p2mr_simple_lightning_contract"; // https://learnmeabitcoin.com/technical/upgrades/taproot/#example-2-script-path-spend-simple #[test] fn test_p2mr_pqc_missing_leaf_script_tree_error() { let _ = env_logger::try_init(); // Use try_init to avoid reinitialization error let test_vectors = &*TEST_VECTORS; let test_vector = test_vectors.test_vector_map.get(P2MR_MISSING_LEAF_SCRIPT_TREE_ERROR_TEST).unwrap(); let test_result: anyhow::Result<()> = process_test_vector_p2mr(test_vector); assert!(matches!(test_result.unwrap_err().downcast_ref::(), Some(P2MRError::MissingScriptTreeLeaf))); } // https://learnmeabitcoin.com/technical/upgrades/taproot/#example-2-script-path-spend-simple #[test] fn test_p2mr_pqc_single_leaf_script_tree() { let _ = env_logger::try_init(); // Use try_init to avoid reinitialization error let test_vectors = &*TEST_VECTORS; let test_vector = test_vectors.test_vector_map.get(P2MR_SINGLE_LEAF_SCRIPT_TREE_TEST).unwrap(); process_test_vector_p2mr(test_vector).unwrap(); } #[test] fn test_p2mr_pqc_different_version_leaves() { let _ = env_logger::try_init(); // Use try_init to avoid reinitialization error let test_vectors = &*TEST_VECTORS; let test_vector = test_vectors.test_vector_map.get(P2MR_DIFFERENT_VERSION_LEAVES_TEST).unwrap(); process_test_vector_p2mr(test_vector).unwrap(); } #[test] fn test_p2mr_pqc_simple_lightning_contract() { let _ = env_logger::try_init(); // Use try_init to avoid reinitialization error let test_vectors = &*TEST_VECTORS; let test_vector = test_vectors.test_vector_map.get(P2MR_SIMPLE_LIGHTNING_CONTRACT_TEST).unwrap(); process_test_vector_p2mr(test_vector).unwrap(); } #[test] fn test_p2mr_pqc_two_leaf_same_version() { let _ = env_logger::try_init(); // Use try_init to avoid reinitialization error let test_vectors = &*TEST_VECTORS; let test_vector = test_vectors.test_vector_map.get(P2MR_TWO_LEAF_SAME_VERSION_TEST).unwrap(); process_test_vector_p2mr(test_vector).unwrap(); } #[test] fn test_p2mr_pqc_three_leaf_complex() { let _ = env_logger::try_init(); // Use try_init to avoid reinitialization error let test_vectors = &*TEST_VECTORS; let test_vector = test_vectors.test_vector_map.get(P2MR_THREE_LEAF_COMPLEX_TEST).unwrap(); process_test_vector_p2mr(test_vector).unwrap(); } #[test] fn test_p2mr_pqc_three_leaf_alternative() { let _ = env_logger::try_init(); // Use try_init to avoid reinitialization error let test_vectors = &*TEST_VECTORS; let test_vector = test_vectors.test_vector_map.get(P2MR_THREE_LEAF_ALTERNATIVE_TEST).unwrap(); process_test_vector_p2mr(test_vector).unwrap(); } fn process_test_vector_p2mr(test_vector: &TestVector) -> anyhow::Result<()> { let tv_script_tree: Option<&TVScriptTree> = test_vector.given.script_tree.as_ref(); let mut tv_leaf_count: u8 = 0; let mut current_branch_id: u8 = 0; // TaprootBuilder expects the addition of each leaf script with its associated depth // It then constructs the binary tree in DFS order, sorting siblings lexicographically & combining them via BIP341's tapbranch_hash // Use of TaprootBuilder avoids user error in constructing branches manually and ensures Merkle tree correctness and determinism let mut p2mr_builder: P2mrBuilder = P2mrBuilder::new(); let mut control_block_data: Vec<(ScriptBuf, LeafVersion)> = Vec::new(); // 1) traverse test vector script tree and add leaves to P2MR builder if let Some(script_tree) = tv_script_tree { script_tree.traverse_with_right_subtree_first(0, Direction::Root,&mut |node, depth, direction| { if let TVScriptTree::Leaf(tv_leaf) = node { let tv_leaf_script_bytes = hex::decode(&tv_leaf.script).unwrap(); // NOTE: IOT to execute script_info.control_block(..), will add these to a vector let tv_leaf_script_buf = ScriptBuf::from_bytes(tv_leaf_script_bytes.clone()); let tv_leaf_version = LeafVersion::from_consensus(tv_leaf.leaf_version).unwrap(); control_block_data.push((tv_leaf_script_buf.clone(), tv_leaf_version)); let mut modified_depth = depth + 1; if direction == Direction::Root { modified_depth = depth; } debug!("traverse_with_depth: leaf_count: {}, depth: {}, modified_depth: {}, direction: {}, tv_leaf_script: {}", tv_leaf_count, depth, modified_depth, direction, tv_leaf.script); // NOTE: Some of the the test vectors in this project specify leaves with non-standard versions (ie: 250 / 0xfa) p2mr_builder = p2mr_builder.clone().add_leaf_with_ver(depth, tv_leaf_script_buf.clone(), tv_leaf_version) .unwrap_or_else(|e| { panic!("Failed to add leaf: {:?}", e); }); tv_leaf_count += 1; } else if let TVScriptTree::Branch { left, right } = node { // No need to calculate branch hash. // TaprootBuilder does this for us. debug!("branch_count: {}, depth: {}, direction: {}", current_branch_id, depth, direction); current_branch_id += 1; } }); }else { return Err(P2MRError::MissingScriptTreeLeaf.into()); } let spend_info: P2mrSpendInfo = p2mr_builder.clone() .finalize() .unwrap_or_else(|e| { panic!("finalize failed: {:?}", e); }); let derived_merkle_root: TapNodeHash = spend_info.merkle_root.unwrap(); // 2) verify derived merkle root against test vector let test_vector_merkle_root = test_vector.intermediary.merkle_root.as_ref().unwrap(); assert_eq!( derived_merkle_root.to_string(), *test_vector_merkle_root, "Merkle root mismatch" ); debug!("just passed merkle root validation: {}", test_vector_merkle_root); let test_vector_leaf_hashes_vec: Vec = test_vector.intermediary.leaf_hashes.clone(); let test_vector_leaf_hash_set: HashSet = test_vector_leaf_hashes_vec.iter().cloned().collect(); let test_vector_control_blocks_vec = &test_vector.expected.script_path_control_blocks; let test_vector_control_blocks_set: HashSet = test_vector_control_blocks_vec.as_ref().unwrap().iter().cloned().collect(); let tap_tree: TapTree = p2mr_builder.clone().into_inner().try_into_taptree().unwrap(); let script_leaves: ScriptLeaves = tap_tree.script_leaves(); // TO-DO: Investigate why the ordering of script leaves seems to be reverse of test vectors. // 3) Iterate through leaves of derived script tree and verify both script leaf hashes and control blocks for derived_leaf in script_leaves { let version = derived_leaf.version(); let script = derived_leaf.script(); let merkle_branch: &TaprootMerkleBranch = derived_leaf.merkle_branch(); let derived_leaf_hash: TapLeafHash = TapLeafHash::from_script(script, version); let leaf_hash = hex::encode(derived_leaf_hash.as_raw_hash().to_byte_array()); assert!( test_vector_leaf_hash_set.contains(&leaf_hash), "Leaf hash not found in expected set for {}", leaf_hash ); debug!("just passed leaf_hash validation: {}", leaf_hash); // Each leaf in the script tree has a corresponding control block. // Specific to P2TR, the 3 sections of the control block (control byte, public key & merkle path) are highlighted here: // https://learnmeabitcoin.com/technical/upgrades/taproot/#script-path-spend-control-block // The control block, which includes the Merkle path, must be 33 + 32 * n bytes, where n is the number of Merkle path hashes (n ≥ 0). // There is no consensus limit on n, but large Merkle trees increase the witness size, impacting block weight. // NOTE: Control blocks could have also been obtained from spend_info.control_block(..) using the data in control_block_data debug!("merkle_branch nodes: {:?}", merkle_branch); let derived_control_block: P2mrControlBlock = P2mrControlBlock{ merkle_branch: merkle_branch.clone(), }; let serialized_control_block = derived_control_block.serialize(); debug!("derived_control_block: {:?}, merkle_branch size: {}, control_block size: {}, serialized size: {}", derived_control_block, merkle_branch.len(), derived_control_block.size(), serialized_control_block.len()); let derived_serialized_control_block = hex::encode(serialized_control_block); assert!( test_vector_control_blocks_set.contains(&derived_serialized_control_block), "Control block mismatch: {}, expected: {:?}", derived_serialized_control_block, test_vector_control_blocks_set ); debug!("leaf_hash: {}, derived_serialized_control_block: {}", leaf_hash, derived_serialized_control_block); } let p2mr_utxo_return: UtxoReturn = create_p2mr_utxo(derived_merkle_root.to_string()); assert_eq!( p2mr_utxo_return.script_pubkey_hex, *test_vector.expected.script_pubkey.as_ref().unwrap(), "Script pubkey mismatch" ); debug!("just passed script_pubkey validation. script_pubkey = {}", p2mr_utxo_return.script_pubkey_hex); let bech32m_address: String = p2mr_utxo_return.bech32m_address; debug!("derived bech32m address for bitcoin_network: {} : {}", p2mr_utxo_return.bitcoin_network, bech32m_address); if p2mr_utxo_return.bitcoin_network == Network::Bitcoin { assert_eq!(bech32m_address, *test_vector.expected.bip350_address.as_ref().unwrap(), "Bech32m address mismatch."); } Ok(()) } ================================================ FILE: bip-0360/ref-impl/rust/tests/p2mr_spend.rs ================================================ use log::info; use bitcoin::blockdata::witness::Witness; use p2mr_ref::{ pay_to_p2wpkh_tx, serialize_script }; use p2mr_ref::data_structures::{SpendDetails, LeafScriptType}; /* The rust-bitcoin crate does not provide a single high-level API that builds the full Taproot script-path witness stack for you. It does expose all the necessary types and primitives to build it manually and correctly. */ // https://learnmeabitcoin.com/technical/upgrades/taproot/#example-2-script-path-spend-simple #[test] fn test_script_path_spend_simple() { let _ = env_logger::try_init(); // Use try_init to avoid reinitialization error let script_inputs_count = hex::decode("03").unwrap(); let script_inputs_bytes: Vec = hex::decode("08").unwrap(); let leaf_script_bytes: Vec = hex::decode("5887").unwrap(); let control_block_bytes: Vec = hex::decode("c1924c163b385af7093440184af6fd6244936d1288cbb41cc3812286d3f83a3329").unwrap(); let test_witness_bytes: Vec = hex::decode( "03010802588721c1924c163b385af7093440184af6fd6244936d1288cbb41cc3812286d3f83a3329", ) .unwrap(); let mut derived_witness: Witness = Witness::new(); derived_witness.push(script_inputs_count); derived_witness.push(serialize_script(&script_inputs_bytes)); derived_witness.push(serialize_script(&leaf_script_bytes)); derived_witness.push(serialize_script(&control_block_bytes)); info!("witness: {:?}", derived_witness); let derived_witness_vec: Vec = derived_witness.iter().flatten().cloned().collect(); assert_eq!(derived_witness_vec, test_witness_bytes); } // Inspired by: https://learnmeabitcoin.com/technical/upgrades/taproot/#example-3-script-path-spend-signature // Spends from a p2mr UTXO to a p2wpk UTXO #[test] fn test_script_path_spend_signatures() { let _ = env_logger::try_init(); // Use try_init to avoid reinitialization error let funding_tx_id_bytes: Vec = hex::decode("d1c40446c65456a9b11a9dddede31ee34b8d3df83788d98f690225d2958bfe3c").unwrap(); // The input index of the funding tx let funding_tx_index: u32 = 0; let funding_utxo_amount_sats: u64 = 20000; // OP_PUSHBYTES_32 6d4ddc0e47d2e8f82cbe2fc2d0d749e7bd3338112cecdc76d8f831ae6620dbe0 OP_CHECKSIG let input_leaf_script_bytes: Vec = hex::decode("206d4ddc0e47d2e8f82cbe2fc2d0d749e7bd3338112cecdc76d8f831ae6620dbe0ac").unwrap(); // Modified from learnmeabitcoin example // Changed from c0 to c1 control byte to reflect p2mr specification: The parity bit of the control byte is always 1 since P2MR does not have a key-spend path. let input_control_block_bytes: Vec = hex::decode("c1924c163b385af7093440184af6fd6244936d1288cbb41cc3812286d3f83a3329").unwrap(); let input_script_pubkey_bytes: Vec = hex::decode("5120f3778defe5173a9bf7169575116224f961c03c725c0e98b8da8f15df29194b80") .unwrap(); let input_script_priv_key_bytes: Vec = hex::decode("9b8de5d7f20a8ebb026a82babac3aa47a008debbfde5348962b2c46520bd5189").unwrap(); // Convert to Vec> format expected by the function let input_script_priv_keys_bytes: Vec> = vec![input_script_priv_key_bytes]; // https://learnmeabitcoin.com/explorer/tx/797505b104b5fb840931c115ea35d445eb1f64c9279bf23aa5bb4c3d779da0c2#outputs let spend_output_pubkey_bytes: Vec = hex::decode("0de745dc58d8e62e6f47bde30cd5804a82016f9e").unwrap(); let spend_output_amount_sats: u64 = 15000; let test_sighash_bytes: Vec = hex::decode("752453d473e511a0da2097d664d69fe5eb89d8d9d00eab924b42fc0801a980c9").unwrap(); let test_signature_bytes: Vec = hex::decode("01769105cbcbdcaaee5e58cd201ba3152477fda31410df8b91b4aee2c4864c7700615efb425e002f146a39ca0a4f2924566762d9213bd33f825fad83977fba7f").unwrap(); // Modified from learnmeabitcoin example // Changed from c0 to c1 control byte to reflect p2mr specification: The parity bit of the control byte is always 1 since P2MR does not have a key-spend path. let test_witness_bytes: Vec = hex::decode("01769105cbcbdcaaee5e58cd201ba3152477fda31410df8b91b4aee2c4864c7700615efb425e002f146a39ca0a4f2924566762d9213bd33f825fad83977fba7f01206d4ddc0e47d2e8f82cbe2fc2d0d749e7bd3338112cecdc76d8f831ae6620dbe0acc1924c163b385af7093440184af6fd6244936d1288cbb41cc3812286d3f83a3329").unwrap(); let result: SpendDetails = pay_to_p2wpkh_tx(funding_tx_id_bytes, funding_tx_index, funding_utxo_amount_sats, input_script_pubkey_bytes, input_control_block_bytes, input_leaf_script_bytes, input_script_priv_keys_bytes, // Now passing Vec> format spend_output_pubkey_bytes, spend_output_amount_sats, LeafScriptType::SchnorrOnly // This test uses a Schnorr signature ); assert_eq!(result.sighash.as_slice(), test_sighash_bytes.as_slice(), "sighash mismatch"); assert_eq!(result.sig_bytes, test_signature_bytes, "signature mismatch"); assert_eq!(result.derived_witness_vec, test_witness_bytes, "derived_witness mismatch"); } ================================================ FILE: bip-0360.mediawiki ================================================
  BIP: 360
  Layer: Consensus (soft fork)
  Title: Pay-to-Merkle-Root (P2MR)
  Authors: Hunter Beast 
           Ethan Heilman 
           Isabel Foxen Duke 
  Status: Draft
  Type: Specification
  Assigned: 2024-12-18
  License: BSD-3-Clause
  Version: 0.11.0
  Requires: 340, 341, 342
==Introduction== ===Abstract=== This document proposes a new output type: Pay-to-Merkle-Root (P2MR), via a soft fork. P2MR outputs operate with nearly the same functionality as P2TR (Pay-to-Taproot) outputs, but with the key path spend removed. Through this modification, P2MR outputs allow developers to use script trees and tapscript in a manner that is: # resistant to long exposure attacks by Cryptographically Relevant Quantum Computers (CRQCs), and # resistant to future cryptanalytic approaches that may compromise the elliptic curve cryptography (ECC) used by Bitcoin. It is worth noting that proposed P2MR outputs are only resistant to "long exposure attacks" on elliptic curve cryptography; that is, attacks on keys exposed for time periods longer than needed to confirm a spending transaction. Protection against more sophisticated quantum attacks, including protection against private key recovery from public keys exposed in the mempool while a transaction is waiting to be confirmed (a.k.a. "short exposure attacks"), may require the introduction of post-quantum signatures in Bitcoin. We believe it's worth considering this path in the future and intend to offer a separate proposal for this purpose upon further research. This document additionally defines "long exposure" and "short exposure" attacks, and other new terminology in the Glossary. ===Copyright=== This document is licensed under the 3-clause BSD license. ===Motivation=== The primary threat to Bitcoin from Cryptographically Relevant Quantum Computers (CRQCs) is their potential to break the key cryptographic assumption which secures the digital signatures used in Bitcoin.A Cryptographically Relevant Quantum Computer is an ''object'' which is only loosely defined by ''characteristics'' in quantum physics as of today. It could be understood in the context of this BIP and in Bitcoin that it's a ''hardware-agnostic'' computer supposed to have the architecture to keep ''coherent'' a sufficient number of logical qubits to be able to run Shor's algorithm in an efficient fashion. More specifically, [https://arxiv.org/pdf/quant-ph/0301141 Shor's algorithm] enables a CRQC to solve the Discrete Logarithm Problem (DLP) exponentially faster than classical methods.Shor's algorithm is believed to need 10^8 operations to break a 256-bit elliptic curve public key. This allows the derivation of private keys from public keys — a process referred to here as quantum key recovery.Meaning, deriving private keys from public keys via Shor's algorithm While it is unclear when or if CRQCs will become viable in the future, we propose the addition of a quantum-resistant, [[#script-tree-output-type|script tree output type]] for those interested in this level of protection. While some may balk at the potential threat of quantum computers to Bitcoin given their limited functionality to date, some others — including governments, corporations and some existing and potential Bitcoin users — are concerned about their potential for advancement. The Commercial National Security Algorithm Suite (CNSA) 2.0, for instance, has mandated software and networking equipment to be upgraded to post-quantum schemes by 2030, with browsers and operating systems fully upgraded by 2033. Additionally, according to NIST IR 8547, Elliptic Curve Cryptography (ECC) is planned to be disallowed within the US federal government after 2035 (with an exception made for hybrid cryptography, or the use of ECC and post-quantum algorithms together). These kinds of mandates have triggered concern by some ECC users, including some Bitcoin users who prefer to be prepared out of an abundance of caution. In the most optimistic case, wherein quantum computers never pose a significant risk to ECC, we understand that the possibility of quantum advancement alone may be influencing adoption and broad confidence in the Bitcoin network. In other words, we believe users' fear of quantum computers may be worth addressing regardless of CRQC viability. Given these concerns, we think it's worth considering simple low risk changes that create options for using Bitcoin in a quantum-resistant way. As a conservative first step in this effort, we propose Pay-to-Merkle-Root (P2MR), a script tree output that can be used in a quantum resistant manner. ===Long Exposure vs Short Exposure Attacks=== For clarity, this proposal specifically mitigates the risk of long exposure attacks on outputs that support tapscript and script trees. While some other Bitcoin output types, such as P2SH, are safe against long exposure attacks, taproot is not and taproot is the only currently activated output type that supports tapscript and script trees. A long exposure attack is an attack performed on exposed blockchain data, such as exposed public keys, or the scripts of spent outputs. These are likely to be the earliest quantum attacks made possible on Bitcoin, because attackers will have ample time — as much time as vulnerable keys are exposed — to carry out quantum key recovery. Short exposure attacks, however, require faster quantum computers, because they must occur within the relatively short time that a transaction is unconfirmed in the mempool. Bitcoin outputs are generally vulnerable to short exposure attacks, as most Bitcoin transactions require revealing the associated public key when spending. Full protection of outputs from short exposure attacks may require the use of post-quantum signature schemes. Since long exposure attacks on public keys are likely to be the first quantum-enabled threat to Bitcoin, we propose a script tree output that is resistant to long exposure attacks as a first step in hardening Bitcoin against the potential threat of quantum computers. The following list of output types describes their long exposure attack vulnerability: {| class="wikitable" |- ! Type ! Vulnerable ! Prefix ! Example |- | P2PK | Yes | Varies | 02103203b768951584fe9af6d9d9e6ff26a5f76e453212f19ba163774182ab8057f3eac |- | P2PKH | No* | 1 | 1A1zP1eP5QGefi2DMPTfTL5SLmv7DivfNa |- | P2MS | Yes | Varies | 52410496ec45f878b62c46c4be8e336dff7cc58df9b502178cc240e... |- | P2SH | No* | 3 | 3FkhZo7sGNue153xhgqPBcUaBsYvJW6tTx |- | P2WPKH | No* | bc1q | bc1qsnh5ktku9ztqeqfr89yrqjd05eh58nah884mku |- | P2WSH | No* | bc1q | bc1qvhu3557twysq2ldn6dut6rmaj3qk04p60h9l79wk4lzgy0ca8mfsnffz65 |- | P2TR | Yes | bc1p | bc1p92aslsnseq786wxfk3ekra90ds9ku47qttupfjsqmmj4z82xdq4q3rr58u |- | P2MR | No* | bc1z | bc1zzmv50jjgxxhww6ve4g5zpewrkjqhr06fyujpm20tuezdlxmfphcqfc80ve |} The following output types are fundamentally vulnerable to long exposure attacks: * P2PK outputs (e.g. Satoshi's coins, CPU miners) * Reused outputs* * Taproot outputs (starts with bc1p) * Funds in P2PKH, P2SH, P2WPKH, P2WSH, and P2MR outputs can become vulnerable to long exposure quantum attacks anytime their script reveals a public key. Note: Extended public keys, commonly known as "xpubs," and wallet descriptors also reveal quantum vulnerable public key information. For further clarification on quantum attack vectors, please refer to the [[#Glossary|Glossary of Terms]]. ==Design== Pay-to-Merkle-Root (P2MR) is a proposed new output type that commits to the root of a script tree. It operates with nearly the same functionality as P2TR (Pay-to-Taproot) outputs, but with the quantum vulnerable key path spend removed. In other words, P2MR outputs commit to the Merkle root of a script tree without committing to an internal key. The script(s) being committed to, however, may contain a key or key-hash. This output type is designed to offer users protection against long exposure quantum attacks as well as a practical output type with which post-quantum signatures may be used if such signatures are adopted in the future. Since P2MR outputs have no key path spend, they omit the Taproot internal key. Instead, a P2MR output includes the 32-byte root of the script tree as defined in [[bip-0341.mediawiki|BIP 341]] hashed with the tag "TapBranch" as shown below. [[File:bip-0360/media/merkletree.png|thumb|Construction of P2MR script tree root, scriptPubkey, and Witness]] To construct a P2MR output, we follow the process outlined in [[bip-0341.mediawiki|BIP 341]] to compute the final tapbranch hash, which is the merkle root of the script leaves; however, instead of tweaking the internal key with the root of the Merkle tree (as is the case with P2TR outputs), P2MR outputs commit only to final tapbranch hash, which is tagged, "TapBranch". D = tagged_hash("TapLeaf", bytes([leaf_version]) + ser_script(script)) CD = tagged_hash("TapBranch", C + D) CDE = tagged_hash("TapBranch", CD + E) ABCDE = tagged_hash("TapBranch", AB + CDE) A P2MR input witness provides the following: initial stack element 0, ..., initial stack element N, leaf script, control block = [control byte, 32*m byte Merkle path] # m is the depth of the script in the Merkle tree The initial stack elements of P2MR follow the same rules as P2TR script path spends. That is, they place elements on the stack to be evaluated by the leaf script. The control block is a ''1 + 32 * m'' byte array, where the first byte is the control byte and the next ''32 * m'' bytes are the Merkle path to the leaf script. The control byte is the same as the control byte in a P2TR control block, including the 7 bits which are used to specify the leaf version. The parity bit of the control byte is always 1, since P2MR does not have a key path spend. Unlike P2TR, we omit the public key from the control block as it is not needed in P2MR. We maintain support for the optional annex in the witness (see Specification section below for more details). ==Rationale== Design of the P2MR output type is guided by the following intentions: 1. Minimize changes to the network. We should reuse existing Bitcoin code and preserve existing software behavior, workflows, user expectations and compatibility whenever possible. P2MR leverages the battle tested P2TR, tapleaf and tapscript code already in Bitcoin, reducing the implementation burden on wallets, exchanges, and libraries that can reuse code they already have. This approach reduces complexity and minimizes implementation risks. 2. Create the safest possible path for the addition of post-quantum signature integrations, in the event that they are used in the future. Importantly, we are proposing a script tree output, i.e. an output type that supports tapscript, that is resistant to long exposure attacks. While some existing output types are already resistant to long exposure attacks (e.g. P2WSH), no such output type supports tapscript — a feature that may be required for practical implementation of post-quantum signature opcodes. P2WSH, for instance, does not support tapscript and as such does not support the OP_SUCCESSx opcode update path that will be critical for the integration of post-quantum OP_CHECKSIG opcodes into Bitcoin.OP_SUCCESSx is a mechanism to upgrade tapscript 3. Facilitate gradual integration of quantum resistant features that can be carried out iteratively as quantum computers evolve. This approach encourages responsiveness to the current threat-level, while avoiding heavy-handedness in our reactions to a potential threat. We designed P2MR with an eye towards integrating post-quantum signatures in the future, without proposing more complex changes while CRQCs are still in their infancy. ===P2MR Trade-Offs=== While P2TR outputs (and the use of key path spend) will remain an option for folks wishing to use them, we aim to be clear about the tradeoffs of using P2MR outputs, which disable the key path spend for the benefit of quantum resistance. The witness to a P2MR spend is always larger than the witness to a P2TR key path spend. This is because a P2TR key path spend requires only a Schnorr signature in the witness. For P2MR, the witness must include the chosen leaf script, the initial stack, and a control block consisting of the control byte and Merkle path (if any). That said, the witness to a P2MR spend will always be smaller than the witness to an equivalent P2TR script path spend, because there is no longer any internal key in P2MR that must be revealed in the control block. For a more complete comparison of output type transaction sizes, the "Transaction Size and Fees" section may be reviewed later in this proposal. Additionally, there is a privacy tradeoff when comparing P2MR and P2TR, which is that users reveal they are spending to a script tree whenever they are using P2MR outputs, since P2MR outputs can only be spent via script path spend. In P2TR when you spend an output as a key path spend, you don't reveal if you have any script path spends. This trade-off only exists when comparing P2TR key path spends to P2MR script path spends; P2TR and P2MR provide the same level of privacy when both are script path spends. '''Note:''' P2MR and P2TR both provide greater script privacy than P2SH [[bip-0016.mediawiki|BIP 16]] because unused script paths are not revealed. ==Specification== We define the Pay-to-Merkle-Root (P2MR) output structure as follows: A P2MR output is similar to a P2TR output (as defined in [[bip-0341.mediawiki|BIP 341]]); however, unlike P2TR outputs, we disable the key path spend for the benefit of quantum resistance by omitting the internal key and the tap tweak step. A P2MR output is then a SegWit version 2 byte followed by the Merkle root of the script tree as the witness program. ===Address Format=== P2MR outputs use SegWit version 2, resulting in mainnet addresses that start with bc1z, following [[bip-0173.mediawiki|BIP 173]]. Bech32m encoding maps version 2 to the prefix z. Example P2MR address: bc1zzmv50jjgxxhww6ve4g5zpewrkjqhr06fyujpm20tuezdlxmfphcqfc80ve This commits to a 32-byte script tree Merkle root. ===ScriptPubKey=== The scriptPubKey for a P2MR output is: OP_2 OP_PUSHBYTES_32 Where: * OP_2 indicates SegWit version 2. * is the 32-byte Merkle root of the script tree. ===Script Validation=== A P2MR output is a native SegWit output (see [[bip-0141.mediawiki|BIP 141]]) with version 2 and a 32-byte witness program. For the sake of comparison, we have — as much as possible — copied the language verbatim from the script validation section of [[bip-0341.mediawiki|BIP 341]]. * Let ''q'' be the 32-byte array containing the witness program (the second push in the scriptPubKey) which represents the Merkle root of the script tree. * Fail if the witness stack does not have two or more elements. * Fail if the witness stack has exactly two elements and the first byte of the last element is 0x50. * If there are at least three witness elements, and the first byte of the last element is 0x50, this last element is called ''annex a'' and is removed from the witness stack. The annex (or the lack thereof) is always covered by the signature and contributes to transaction weight, but is otherwise ignored during P2MR validation. * There must be at least two witness elements left. ** Call the second-to-last stack element ''s'', the script (as defined in [[bip-0341.mediawiki|BIP 341]]). ** The last stack element is called the control block ''c'', and must have length ''1 + 32 * m'', for a value of ''m'' that is an integer between 0 and 128, inclusive. Fail if it does not have such a length. ** Let ''v = c[0] & 0xfe'' be the ''leaf version'' (as defined in [[bip-0341.mediawiki|BIP 341]]). To maintain ''leaf version'' encoding compatibility the last bit of c[0] is unused and must be 1.Why set the last bit of c[0] to one? Consider a faulty implementation that deserializes the ''leaf version'' as c[0] rather than c[0] & 0xfe for both P2TR and P2MR. If they test against P2MR outputs and require that last bit is 1, this deserialization bug will cause an immediate error. ** Let ''k0 = hashTapLeaf(v || compact_size(size of s) || s)''; also call it the ''tapleaf hash''. ** For ''j'' in ''[0,1,...,m-1]'': *** Let ''ej = c[1+32j:33+32j]''. *** Let ''kj+1'' depend on whether ''kj < ej'' (lexicographically): **** If ''kj < ej'': ''kj+1 = hashTapBranch(kj || ej)''. **** If ''kj ≥ ej'': ''kj+1 = hashTapBranch(ej || kj)''. ** Let ''r = km''. ** If ''q ≠ r'', fail. ** Execute the script, according to the script rules specified in BIP 342, using the witness stack elements excluding the script ''s'', the control block ''c'', and the annex ''a'' if present, as initial stack. This implies that for the future leaf versions (non-''0xC0'') the execution must succeed. The steps above follow the script path spend logic from [[bip-0341.mediawiki|BIP 341]] with the following changes: * The witness program is the the Merkle root of the script tree and not a tweaked public key. This means that we skip directly to the BIP 341 script path validation. * We compute the script tree Merkle root ''r'' and compare it directly to the witness program ''q''. * The control block is ''1 + 32*m'' bytes, instead of ''33 + 32*m'' bytes. ===Common Signature Message Construction=== The [https://learnmeabitcoin.com/technical/upgrades/taproot/#common-signature-message common signature message] construction for P2MR outputs is exactly the same procedure as defined in [[bip-0342.mediawiki#user-content-Common_Signature_Message_Extension|BIP342 Common Signature Message]]. === Compatibility with BIP 141 === By adhering to the SegWit transaction structure and versioning, P2MR outputs are compatible with existing transaction processing rules. Nodes that do not recognize SegWit version 2 will treat these outputs as anyone-can-spend but generally will not relay or mine such transactions. ===Transaction Size and Fees=== All P2MR and P2TR outputs are always the same size. P2MR inputs can be slightly larger or smaller than their equivalent P2TR inputs, depending on the use of key path vs script path spend in the case of P2TR. Let's consider the cases. ====Comparison with P2TR key path spend==== A P2MR witness will be larger than a P2TR witness when the P2TR output is spent via the key path spend. A witness to a P2TR key path spend is simply a signature. P2MR quantum resistance comes from removing the P2TR key path spend. Every P2MR spend is a P2TR script path spend and so requires a script, its input stack and a control block. Consequently, P2MR loses this size advantage of P2TR key path spends in order to gain quantum resistance. If the script tree only has a single leaf script, no Merkle path is needed in the control block, giving us a minimal size control block of 1 byte. P2MR witness for depth-0 tree (103 bytes): [count] (1 byte), # Number of elements in the witness [size] signature (1 + 64 bytes = 65 bytes), leaf script = [size] [OP_PUSHBYTES_32, 32-byte public key, OP_CHECKSIG] (1 + 1 + 32 + 1 bytes = 35 bytes), control block = [size] [control byte] [merkle path (empty)] (1 + 1 + 0 bytes = 2 bytes) P2TR key path spend witness (66 bytes): [count] (1 byte), # Number of elements in the witness [size] signature (1 + 64 bytes = 65 bytes) Thus, the P2MR witness would be 103 - 66 = 37 bytes larger than a P2TR key path spend witness. If the Merkle tree has more than a single leaf, then the Merkle path must be included in the control block, increasing the size by ''32 * m'' bytes, where m is the depth of the Merkle tree. While script trees do support leaf scripts of different depths, here we assume the Merkle tree has been constructed such that each leaf is at the same depth. This would make such witness 37 + 32 * m bytes larger than a P2TR key path spend witness.If ''m >= 8'', then the compact size will use 3 bytes rather than 1 byte P2MR witness ''(103 + 32*m bytes)'': [count] (1 byte), # Number of elements in the witness [size] signature (64 + 1 bytes = 65 bytes), leaf script = [size] [OP_PUSHBYTES_32, 32-byte public key, OP_CHECKSIG] (34 + 1 bytes = 35 bytes), control block = [size] [control byte] [Merkle path] (1 + 1 + 32*m = 2 + 32*m bytes) ====Comparison with P2TR script path spend==== A P2MR witness will be smaller than the witness to an equivalent P2TR script path spend. This is because P2MR does not require inclusion of an internal public key in the control block to unlock and spend an output. For this reason, a P2MR witness will always be 32 bytes smaller than an equivalent P2TR script path spend witness. ==Performance Impact== P2MR is slightly more computationally performant than P2TR script path spends, as the operations to spend a P2MR output is a strict subset of the operations needed to perform a script path spend on a P2TR output. ==Backward Compatibility== Older wallets and nodes that have not been made compatible with SegWit version 2 and P2MR will not understand these outputs. Per [[bip-0350.mediawiki|BIP 350]] older wallets should be able to spend funds to SegWit version 2 outputs. Users should ensure they are using updated wallets and nodes to receive P2MR outputs and validate transactions using P2MR outputs. P2MR is fully compatible with tapscript and existing tapscript programs can be used in P2MR outputs without modification. P2MR can also support future scripts with new leaf versions. ==Security== P2MR outputs provide the same tapscript functionality as P2TR outputs, but with the quantum-vulnerable key path spend removed. The similarity between these output types enables users to easily migrate script trees from P2TR outputs to P2MR outputs for protection against long exposure quantum attacks. Wallets supporting only P2TR key path spends would need to migrate to using script trees. This is a straightforward migration as it only requires moving to a simple OP_CHECKSIG leaf script. Protection from long exposure quantum attacks does not depend on the activation of post-quantum signatures in Bitcoin, but requires that users do not expose their public keys to attackers via public key reuse or other unsafe practices. P2MR uses a 256-bit hash output, providing 128 bits of collision resistance and 256 bits of preimage resistance. This is the same level of security as P2WSH specified in [[bip-0141.mediawiki|BIP 141]], which also uses a 256-bit hash output. P2MR does not, by itself, protect against short exposure quantum attacks, but these attacks can be mitigated by future activation of post-quantum signatures. Combined with P2MR, post-quantum signature schemes can provide comprehensive quantum resistance to P2MR outputs, including protection from short exposure attacks. That said, protection against long exposure quantum attacks alone should not be underestimated. It's unlikely that early CRQCs will be fast enough to perform short exposure attacks, making preparedness against long exposure attacks more time-critical. ==Security Considerations for Post-Quantum Signature Schemes== While this proposal does not include the introduction of post-quantum signature schemes, we think it's worth commenting on security considerations related to this possibility. Quantum-resistant signature algorithms (e.g. ML-DSA or SLH-DSA) offer different levels of protection and should be scrutinized before use. We are currently researching options for the potential proposal of post-quantum signatures into Bitcoin and encourage others to engage in this research as well. We also imagine the possibility of introducing multiple post-quantum signatures for redundancy. Balancing the risks of additional complexity with the benefits of signature-type redundancy will be the challenge here. ==Test Vectors and Reference Code== Test vector data for creation of P2MR UTXOs can be found [https://github.com/bitcoin/bips/blob/master/bip-0360/ref-impl/common/tests/data/P2MR_construction.json here]. These test vectors build off of the test vectors for [[bip-0341.mediawiki|BIP 341]] (Taproot). One important distinction is that the P2MR test vectors do not include keypath spend scenarios. Also included are test vectors in [https://github.com/bitcoin/bips/tree/master/bip-0360/ref-impl/rust rust implementation] and [https://github.com/bitcoin/bips/tree/master/bip-0360/ref-impl/python python implementation]. One of these tests demonstrates a tapscript that requires a secp256k1 signature to spend the P2MR UTXO (modeled after one of the extremely valuable examples provided by [https://learnmeabitcoin.com/technical/upgrades/taproot/#example-3-script-path-spend-signature this Taproot script path spend example]. Similar to BIP 341 test vectors, all signatures are created with an all-zero (0x0000...0000) [[bip-0340.mediawiki|BIP 340]] auxiliary randomness array. ==Related Work== Below we attempt to summarize some of the ideas discussed on the Bitcoin Development Mailing List that relate to P2MR. The idea of Taproot with key path spend removed has been discussed a number of times in the Bitcoin community. For instance, [https://gnusha.org/pi/bitcoindev/CAD5xwhgzR8e5r1e4H-5EH2mSsE1V39dd06+TgYniFnXFSBqLxw@mail.gmail.com/ OP_CAT Makes Bitcoin Quantum Secure] notes that if we disable the key path spend in Taproot and activate OP_CAT [[bip-0347.mediawiki|BIP 347]], we could achieve quantum resistance by using Lamport signatures with OP_CAT. Lamport and WOTS (Winternitz One-Time Signatures) built from CAT are quantum resistant, but are one-time signatures — meaning, if you sign twice for the same public key, you risk leaking your private key, which is a significant security concern for everyday users. This would require major changes to wallet behavior and would represent a significant security downgrade. Common practices, such as RBF and CPFP, could risk revealing private keys if no stateless signature scheme is used. [https://groups.google.com/g/bitcoindev/c/8O857bRSVV8/m/rTrpeFjWDAAJ Trivial QC signatures with clean upgrade path] and [https://groups.google.com/g/bitcoindev/c/oQKezDOc4us/m/T1vSMkZNAAAJ Re: P2QRH / BIP 360 Update] also discuss the possibility of Taproot with key path spend removed. The design of P2MR was partly inspired by these discussions. Commit-reveal schemes such as [https://gnusha.org/pi/bitcoindev/1518710367.3550.111.camel@mmci.uni-saarland.de/ Re: Transition to post-quantum (2018)] and [https://groups.google.com/g/bitcoindev/c/LpWOcXMcvk8/m/YEiH-kTHAwAJ Post-Quantum commit / reveal Fawkescoin variant as a soft fork (2025)] have been proposed as a way to create cryptocurrencies without public key cryptography. The ideas in this paper were more recently expanded upon by Tadge Dryja in his "[https://www.youtube.com/watch?v=4bzOwYPf1yo Lifeboat]" proposal, which effectively quantum-proofs Bitcoin transactions through a similar pre-commitment scheme designed for Bitcoin. ==Other Methods of Addressing Quantum Vulnerabilities for Cryptocurrencies== It is worth noting, by way of comparison, that [https://ethresear.ch/t/how-to-hard-fork-to-save-most-users-funds-in-a-quantum-emergency/18901 Vitalik Buterin's proposed solution] to Ethereum's quantum vulnerability is quite different from the approach in this BIP. His plan involves a hard fork of the chain, reverting all blocks after some sufficient amount of theft, and using STARKs based on BIP 32 seeds to act as the authoritative secret when signing. We believe rollbacks of any kind are an untenable approach for Bitcoin and would likely be impractical to implement. That said, we believe the use of STARKs (which are quantum-resistant) may prove useful as a method of proving access to external private keys, in the event that the community chooses to burn vulnerable coins as proposed by Jameson Lopp and others in [https://qbip.org/ QBIP]. Discussions related to the burning of coins, and other attempts to slow a potential supply shock caused by quantum-retrieval of vulnerable coins, are out of scope for this proposal. That said, members of our team have separately proposed [https://github.com/cryptoquick/bips/blob/hourglass/bip-hourglass.mediawiki Hourglass] to address this concern and are continuing research on this subject. ==Conclusion== In this proposal, we adopt a "prepared not scared" approach to the possible advancement of quantum computing and offer Bitcoin users an option for increased protection if they so choose. This BIP does not take a position on any specific quantum computing timeline, but rather proposes a flexible and unobtrusive option for users that wish to mitigate this risk according to their own estimate of the timeline. This is an issue that has been discussed with some regularity in [https://bitcointalk.org/index.php?topic=133425.0 Bitcoin forums] since at least 2012, and there is clearly user demand for increased quantum protection. ==Glossary== '''Quantum Key Recovery''' The derivation of private keys from public keys in elliptic curve cryptography (ECC), made possible by solving the discrete logarithm problem (DLP). Shor's algorithm, developed by Peter Shor in 1994, is a quantum algorithm that efficiently solves the discrete logarithm problem — potentially made possible by the future viability of cryptographically relevant quantum computers (CRQCs). '''Long Exposure Attacks''' Attempts to derive private keys from public keys that are exposed for an extended period of time; that is, longer than the window of time that a public key is generally exposed in the mempool while waiting to be confirmed. Long exposure attacks give attackers an unlimited amount of time to perform quantum key recovery, as long as funds remain in the output. Poor wallet hygiene (e.g. from address reuse) or use of outputs with exposed public keys (e.g. P2TR outputs) increases vulnerability to long exposure attacks. '''Short Exposure Attacks''' Attempts to derive private keys from public keys during the brief period when funds are unconfirmed in the mempool. These attacks cannot be prevented through wallet hygiene, as revealing a public key is necessary for spending. Protection against short exposure attacks may require post-quantum signature schemes; that said, executing these attacks requires faster CRQCs than those capable of executing long exposure attacks and are therefore viewed as lower-risk than long exposure attacks in the nearer term. '''Script Tree Output Type''' Script tree output types are a category of output type that support a script tree consisting of leaf scripts. Script tree output types support tapscript and would support any new script language added to bitcoin which is able to be used as a leaf script in a script trees. If Pay-to-Merkle-Root (P2MR) is activated, P2MR would be the second script tree output type in Bitcoin, the other being Pay-to-Taproot (P2TR). '''Pay-to-Merkle-Root (P2MR)''' A script tree output type, similar to to Pay-to-Taproot (P2TR), but with the quantum-vulnerable key path spend removed. ==Footnotes== ==Changelog== To help implementers understand updates to this BIP, we keep a list of substantial changes. * __0.11.0__ (2026-02-10) - Rename BIP from Pay-to-Tapscript-Hash (P2TSH) to Pay-to-Merkle-Root (P2MR) * __0.10.3__ (2026-02-06) - Rename tapscript-native output type to script tree output type. * __0.10.2__ (2026-01-23) - Fix bug in verification, minor review comments and adopt [[bip-0003.mediawiki|BIP 003]] conventions. * __0.10.1__ (2026-01-21) - Terminology and clarity improvements, addressed feedback from reviews. * __0.10.0__ (2025-09-17) - Rewrote BIP for clarity and renamed from P2QRH to P2TSH * __0.9.0__ (2025-07-20) - Changed the Witness Version from 3 to 2. * __0.8.0__ (2025-07-07) - P2QRH is now a P2TR with the vulnerable key path spend removed. Number of PQ signature algorithms supported reduced from three to two. PQ signature algorithm support is now added via opcodes or leaf version. * __0.7.0__ (2025-03-18) - Correct inconsistencies in commitment and attestation structure. Switch from Merkle tree commitment to sorted vector hash commitment. Update descriptor format. * __0.6.2__ (2025-03-12) - Add verification times for each algorithm. 256 to 128 (NIST V to NIST I). Add key type bitmask. Clarify multisig semantics. * __0.6.1__ (2025-02-23) - More points of clarification from review. Update dead link. * __0.6.0__ (2025-01-20) - Remove SQIsign from consideration due to significant performance concerns. Refactor language from long range attack to long exposure so as to not be confused with the language around block re-org attacks. * __0.5.1__ (2024-12-18) - Assigned BIP number. * __0.5.0__ (2024-12-13) - Update to use Merkle tree for attestation commitment. Update LR & SR quantum attack scenarios. * __0.4.0__ (2024-12-01) - Add details on attestation structure and parsing. * __0.3.0__ (2024-10-21) - Replace XMSS with CRYSTALS-Dilithium due to NIST approval and size constraints. * __0.2.2__ (2024-09-30) - Refactor the ECC vs PoW section. Swap quitness for attestation. * __0.2.1__ (2024-09-29) - Update section on PoW to include partial-preimage. * __0.2.0__ (2024-09-28) - Add Winternitz, XMSS signatures, and security assumption types to PQC table. Omit NIST Level I table. Add spend script specification. Add revealed public key scenario table. * __0.1.0__ (2024-09-27) - Initial draft proposal ==Acknowledgements== This document is inspired by [[bip-0341.mediawiki|BIP 341]], which introduced the design of the P2TR (Taproot) output type using Schnorr signatures. I'm incredibly grateful to Ethan Heilman for joining as co-author and transforming this BIP into something far more congruent with existing Bitcoin design. Additionally, much gratitude to our most recent co-author, Isabel Foxen Duke, for her thoughtful editing and crafting much of the language in this proposal. I am likewise indebted to those on the Anduro Quantum Working Group who took the time to contribute including Jeff Bride, Michael Casey, and notmike. Thank you as well to those who took the time to review and contribute, including Jon Atack, Adam Borcany, Ava Chow, Kyle Crews, Pierre-Luc Dallaire-Demers, D++, Mark Erhardt, Jameson Lopp, Antoine Riard, Armin Sabouri, Vojtěch Strnad, Guy Swann, and Joey Yandle. Whatever inaccuracies may remain are attributable solely to the authors. ================================================ FILE: bip-0370.mediawiki ================================================
  BIP: 370
  Layer: Applications
  Title: PSBT Version 2
  Authors: Ava Chow 
  Status: Deployed
  Type: Specification
  Assigned: 2021-01-14
  License: BSD-2-Clause
==Introduction== ===Abstract=== This document proposes a second version of the Partially Signed Bitcoin Transaction format described in BIP 174 which allows for inputs and outputs to be added to the PSBT after creation. ===Copyright=== This BIP is licensed under the 2-clause BSD license. ===Motivation=== Partially Signed Bitcoin Transaction Version 0 as described in BIP 174 is unable to have new inputs and outputs be added to the transaction. The fixed global unsigned transaction cannot be changed which prevents any additional inputs or outputs to be added. PSBT Version 2 is intended to rectify this problem. An additional beneficial side effect is that all information for a given input or output will be provided by its or . With Version 0, to retrieve all of the information for an input or output, data would need to be found in two locations: the / and the global unsigned transaction. PSBT Version 2 now moves all related information to one place. ==Specification== PSBT Version 2 (PSBTv2) only specifies new fields and field inclusion/exclusion requirements. PSBT_GLOBAL_UNSIGNED_TX must be excluded in PSBTv2. PSBT_GLOBAL_VERSION must be included in PSBTv2 and set to version number 2'''What happened to version number 1?''' Version number 1 is skipped because PSBT Version 0 has been colloquially referred to as version 1. Originally this BIP was to be version 1, but because it has been colloquially referred to as version 2 during its design phase, it was decided to change the version number to 2 so that there would not be any confusion. The new global types for PSBT Version 2 are as follows: {| ! Name ! ! ! Description ! ! Description ! Versions Requiring Inclusion ! Versions Requiring Exclusion ! Versions Allowing Inclusion |- | Transaction Version | PSBT_GLOBAL_TX_VERSION = 0x02 | None | No key data | <32-bit little endian int version> | The 32-bit little endian signed integer representing the version number of the transaction being created. Note that this is not the same as the PSBT version number specified by the PSBT_GLOBAL_VERSION field. | 2 | 0 | 2 |- | Fallback Locktime | PSBT_GLOBAL_FALLBACK_LOCKTIME = 0x03 | None | No key data | <32-bit little endian uint locktime> | The 32-bit little endian unsigned integer representing the transaction locktime to use if no inputs specify a required locktime. | | 0 | 2 |- | Input Count | PSBT_GLOBAL_INPUT_COUNT = 0x04 | None | No key data | | Compact size unsigned integer representing the number of inputs in this PSBT. | 2 | 0 | 2 |- | Output Count | PSBT_GLOBAL_OUTPUT_COUNT = 0x05 | None | No key data | | Compact size unsigned integer representing the number of outputs in this PSBT. | 2 | 0 | 2 |- | Transaction Modifiable Flags | PSBT_GLOBAL_TX_MODIFIABLE = 0x06 | None | No key data | <8-bit uint flags> | An 8 bit unsigned integer as a bitfield for various transaction modification flags. Bit 0 is the Inputs Modifiable Flag, set to 1 to indicate whether inputs can be added or removed. Bit 1 is the Outputs Modifiable Flag, set to 1 to indicate whether outputs can be added or removed. Bit 2 is the Has SIGHASH_SINGLE flag, set to 1 to indicate whether the transaction has a SIGHASH_SINGLE signature who's input and output pairing must be preserved. Bit 2 essentially indicates that the Constructor must iterate the inputs to determine whether and how to add or remove an input. | | 0 | 2 |} The new per-input types for PSBT Version 2 are defined as follows: {| ! Name ! ! ! Description ! ! Description ! Versions Requiring Inclusion ! Versions Requiring Exclusion ! Versions Allowing Inclusion |- | Previous TXID | PSBT_IN_PREVIOUS_TXID = 0x0e | None | No key data | <32 byte txid> | 32 byte txid in standard byte order, not display byte order, of the previous transaction whose output at PSBT_IN_OUTPUT_INDEX is being spent. | 2 | 0 | 2 |- | Spent Output Index | PSBT_IN_OUTPUT_INDEX = 0x0f | None | No key data | <32-bit little endian uint index> | 32 bit little endian integer representing the index of the output being spent in the transaction with the txid of PSBT_IN_PREVIOUS_TXID. | 2 | 0 | 2 |- | Sequence Number | PSBT_IN_SEQUENCE = 0x10 | None | No key data | <32-bit little endian uint sequence> | The 32 bit unsigned little endian integer for the sequence number of this input. If omitted, the sequence number is assumed to be the final sequence number (0xffffffff). | | 0 | 2 |- | Required Time-based Locktime | PSBT_IN_REQUIRED_TIME_LOCKTIME = 0x11 | None | No key data | <32-bit little endian uint locktime> | 32 bit unsigned little endian integer greater than or equal to 500000000 representing the minimum Unix timestamp that this input requires to be set as the transaction's lock time. | | 0 | 2 |- | Required Height-based Locktime | PSBT_IN_REQUIRED_HEIGHT_LOCKTIME = 0x12 | None | No key data | <32-bit uint locktime> | 32 bit unsigned little endian integer greater than 0 and less than 500000000 representing the minimum block height that this input requires to be set as the transaction's lock time. | | 0 | 2 |} The new per-output types for PSBT Version 2 are defined as follows: {| ! Name ! ! ! Description ! ! Description ! Versions Requiring Inclusion ! Versions Requiring Exclusion ! Versions Allowing Inclusion |- | Output Amount | PSBT_OUT_AMOUNT = 0x03 | None | No key data | <64-bit little endian int amount> | 64 bit signed little endian integer representing the output's amount in satoshis. | 2 | 0 | 2 |- | Output Script | PSBT_OUT_SCRIPT = 0x04 | None | No key data | | The script for this output, also known as the scriptPubKey. Must be omitted in PSBTv0. Must be provided in PSBTv2. | 2 | 0 | 2 |} ===Determining Lock Time=== The nLockTime field of a transaction is determined by inspecting the PSBT_GLOBAL_FALLBACK_LOCKTIME and each input's PSBT_IN_REQUIRED_TIME_LOCKTIME and PSBT_IN_REQUIRED_HEIGHT_LOCKTIME fields. If none of the inputs have a PSBT_IN_REQUIRED_TIME_LOCKTIME and PSBT_IN_REQUIRED_HEIGHT_LOCKTIME, then PSBT_GLOBAL_FALLBACK_LOCKTIME must be used. If PSBT_GLOBAL_FALLBACK_LOCKTIME is not provided, then it is assumed to be 0. If one or more inputs have a PSBT_IN_REQUIRED_TIME_LOCKTIME or PSBT_IN_REQUIRED_HEIGHT_LOCKTIME, then the field chosen is the one which is supported by all of the inputs. This can be determined by looking at all of the inputs which specify a locktime in either of those fields, and choosing the field which is present in all of those inputs. Inputs not specifying a lock time field can take both types of lock times, as can those that specify both. The lock time chosen is then the maximum value of the chosen type of lock time. If a PSBT has both types of locktimes possible because one or more inputs specify both PSBT_IN_REQUIRED_TIME_LOCKTIME and PSBT_IN_REQUIRED_HEIGHT_LOCKTIME, then locktime determined by looking at the PSBT_IN_REQUIRED_HEIGHT_LOCKTIME fields of the inputs must be chosen.'''Why choose the height based locktime?''' In the event of a tie for the locktime type, signers need to be able to know which locktime to use as their signatures will commit to the locktime in the transaction, so choosing the wrong one will result in an invalid transaction. Height based locktime is preferred over time based as Bitcoin's unit of time is the block height, so a height makes more sense in the context of Bitcoin. ===Unique Identification=== PSBTv2s can be uniquely identified by constructing an unsigned transaction given the information provided in the PSBT, and computing the transaction ID of that transaction. Since PSBT_IN_SEQUENCE can be changed by Updaters and Combiners, the sequence number in this unsigned transaction must be set to 0 (not final, nor the sequence in PSBT_IN_SEQUENCE). The lock time in this unsigned transaction must be computed as described previously. ==Roles== PSBTv2 introduces new roles and modifies some existing roles. ===Creator=== In PSBTv2, the Creator initializes the PSBT with 0 inputs and 0 outputs. The PSBT version number is set to 2. The Creator should also set PSBT_GLOBAL_FALLBACK_LOCKTIME. If the Creator is not also a Constructor and will be giving the PSBT to others to add inputs and outputs, the PSBT_GLOBAL_TX_MODIFIABLE field must be present and the Inputs Modifiable and Outputs Modifiable flags set appropriately; moreover, the transaction version number must be set to at least 2. '''Why does the transaction version number need to be at least 2?''' The transaction version number is part of the validation rules for some features such as OP_CHECKSEQUENCEVERIFY. Since it is backwards compatible, and there are other ways to disable those features (e.g. through sequence numbers), it is easier to require transactions be able to support these features than to try to negotiate the transaction version number. If the Creator is a Constructor and no inputs and outputs will be added by other entities, PSBT_GLOBAL_TX_MODIFIABLE may be omitted. ===Constructor=== This Constructor is only present for PSBTv2. Once a Creator initializes the PSBT, a constructor will add inputs and outputs. Before any input or output may be added, the constructor must check the PSBT_GLOBAL_TX_MODIFIABLE field. Inputs may only be added if the Inputs Modifiable flag is True. Outputs may only be added if the Outputs Modifiable flag is True. When an input or output is added, the corresponding PSBT_GLOBAL_INPUT_COUNT or PSBT_GLOBAL_OUTPUT_COUNT must be incremented to reflect the number of inputs and outputs in the PSBT. When an input is added, it must have PSBT_IN_PREVIOUS_TXID and PSBT_IN_OUTPUT_INDEX set. When an output is added, it must have PSBT_OUT_VALUE and PSBT_OUT_OUTPUT_SCRIPT set. If the input has a required timelock, Constructors must set the requisite timelock field. If the input has a required time based timelock, then PSBT_IN_REQUIRED_TIME_TIMELOCK must be set. If the input has a required height based timelock, then PSBT_IN_REQUIRED_HEIGHT_TIMELOCK must be set. If an input has both types of timelocks, then both may be set. In some cases, an input that can allow both types, but a particular branch supporting only one type of timelock will be taken, then the type of timelock that will be used can be the only one set. If an input being added specifies a required time lock, then the Constructor must iterate through all of the existing inputs and ensure that the time lock types are compatible. Additionally, if during this iteration, it finds that any inputs have signatures, it must ensure that the newly added input does not change the transaction's locktime. If the newly added input has an incompatible time lock, then it must not be added. If it changes the transaction's locktime when there are existing signatures, it must not be added. If the Has SIGHASH_SINGLE flag is True, then the Constructor must iterate through the inputs and find the inputs which have signatures that use SIGHASH_SINGLE. The same number of inputs and outputs must be added before those inputs and their corresponding outputs. A Constructor may choose to declare that no further inputs and outputs can be added to the transaction by setting the appropriate bits in PSBT_GLOBAL_TX_MODIFIABLE to 0 or by removing the field entirely. A single entity is likely to be both a Creator and Constructor. ===Updater=== For PSBTv2, an Updater can set the sequence number. ===Signer=== For PSBTv2s, a signer must update the PSBT_GLOBAL_TX_MODIFIABLE field after signing inputs so that it accurately reflects the state of the PSBT. If the Signer added a signature that does not use SIGHASH_ANYONECANPAY, the Input Modifiable flag must be set to False. If the Signer added a signature that does not use SIGHASH_NONE, the Outputs Modifiable flag must be set to False. If the Signer added a signature that uses SIGHASH_SINGLE, the Has SIGHASH_SINGLE flag must be set to True. ===Transaction Extractor=== For PSBTv2s, the transaction is constructed using the PSBTv2 fields. The lock time for this transaction is determined as described in the Determining Lock Time section. The Extractor should produce a fully valid, network serialized transaction if all inputs are complete. ==Backwards Compatibility== PSBTv2 shares the same generic format as PSBTv0 as defined in BIP 174. Parsers for PSBTv0 should be able to deserialize PSBTv2 with only changes to support the new fields. However PSBTv2 is incompatible with PSBTv0, and vice versa due to the use of the PSBT_GLOBAL_VERSION. This incompatibility is intentional so that PSBT_GLOBAL_UNSIGNED_TX could be removed in PSBTv2. However it is possible to convert a PSBTv2 to a PSBTv0 by creating an unsigned transaction from the PSBTv2 fields. ==Test Vectors== The following are invalid PSBTs: * Case: PSBTv0 but with PSBT_GLOBAL_VERSION set to 2. ** Bytes in Hex:
70736274ff01007102000000010b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc80000000000feffffff020008af2f00000000160014c430f64c4756da310dbd1a085572ef299926272c8bbdeb0b00000000160014a07dac8ab6ca942d379ed795f835ba71c9cc68850000000001fb0402000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e01086b02473044022005275a485734e0ae1f3b971237586f0e72dc85833d278c0e474cd23112c0fa5e02206b048c83cebc3c41d0b93cc7da76185cedbd030d005b08018be2b98bbacbdf7b012103760dcca05f3997dc65b293060f7f29f1514c8c527048e12802b041d4fc340a2700220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a000000002202036efe2c255621986553ba9d65c3ddc64165ca1436e05aa35a4c6eb02451cf796d18f69d873e540000800100008000000080010000006200000000
** Base64 String:
cHNidP8BAHECAAAAAQsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAAAAAAD+////AgAIry8AAAAAFgAUxDD2TEdW2jENvRoIVXLvKZkmJyyLvesLAAAAABYAFKB9rIq2ypQtN57Xlfg1unHJzGiFAAAAAAH7BAIAAAAAAQBSAgAAAAHBqiVuIUuWoYIvk95Cv/O18/+NBRkwbjUV11FaXoBbEgAAAAAA/////wEYxpo7AAAAABYAFLCjrxRCCEEmk8p9FmhStS2wrvBuAAAAAAEBHxjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4BCGsCRzBEAiAFJ1pIVzTgrh87lxI3WG8OctyFgz0njA5HTNIxEsD6XgIgawSMg868PEHQuTzH2nYYXO29Aw0AWwgBi+K5i7rL33sBIQN2DcygXzmX3GWykwYPfynxUUyMUnBI4SgCsEHU/DQKJwAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAAAIgIDbv4sJVYhmGVTup1lw93GQWXKFDbgWqNaTG6wJFHPeW0Y9p2HPlQAAIABAACAAAAAgAEAAABiAAAAAA==
* Case: PSBTv0 but with PSBT_GLOBAL_TX_VERSION. ** Bytes in Hex:
70736274ff01007102000000010b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc80000000000feffffff020008af2f00000000160014c430f64c4756da310dbd1a085572ef299926272c8bbdeb0b00000000160014a07dac8ab6ca942d379ed795f835ba71c9cc68850000000001020402000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e01086b02473044022005275a485734e0ae1f3b971237586f0e72dc85833d278c0e474cd23112c0fa5e02206b048c83cebc3c41d0b93cc7da76185cedbd030d005b08018be2b98bbacbdf7b012103760dcca05f3997dc65b293060f7f29f1514c8c527048e12802b041d4fc340a2700220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a000000002202036efe2c255621986553ba9d65c3ddc64165ca1436e05aa35a4c6eb02451cf796d18f69d873e540000800100008000000080010000006200000000
** Base64 String:
cHNidP8BAHECAAAAAQsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAAAAAAD+////AgAIry8AAAAAFgAUxDD2TEdW2jENvRoIVXLvKZkmJyyLvesLAAAAABYAFKB9rIq2ypQtN57Xlfg1unHJzGiFAAAAAAECBAIAAAAAAQBSAgAAAAHBqiVuIUuWoYIvk95Cv/O18/+NBRkwbjUV11FaXoBbEgAAAAAA/////wEYxpo7AAAAABYAFLCjrxRCCEEmk8p9FmhStS2wrvBuAAAAAAEBHxjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4BCGsCRzBEAiAFJ1pIVzTgrh87lxI3WG8OctyFgz0njA5HTNIxEsD6XgIgawSMg868PEHQuTzH2nYYXO29Aw0AWwgBi+K5i7rL33sBIQN2DcygXzmX3GWykwYPfynxUUyMUnBI4SgCsEHU/DQKJwAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAAAIgIDbv4sJVYhmGVTup1lw93GQWXKFDbgWqNaTG6wJFHPeW0Y9p2HPlQAAIABAACAAAAAgAEAAABiAAAAAA==
* Case: PSBTv0 but with PSBT_GLOBAL_FALLBACK_LOCKTIME. ** Bytes in Hex:
70736274ff01007102000000010b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc80000000000feffffff020008af2f00000000160014c430f64c4756da310dbd1a085572ef299926272c8bbdeb0b00000000160014a07dac8ab6ca942d379ed795f835ba71c9cc68850000000001030402000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e01086b02473044022005275a485734e0ae1f3b971237586f0e72dc85833d278c0e474cd23112c0fa5e02206b048c83cebc3c41d0b93cc7da76185cedbd030d005b08018be2b98bbacbdf7b012103760dcca05f3997dc65b293060f7f29f1514c8c527048e12802b041d4fc340a2700220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a000000002202036efe2c255621986553ba9d65c3ddc64165ca1436e05aa35a4c6eb02451cf796d18f69d873e540000800100008000000080010000006200000000
** Base64 String:
cHNidP8BAHECAAAAAQsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAAAAAAD+////AgAIry8AAAAAFgAUxDD2TEdW2jENvRoIVXLvKZkmJyyLvesLAAAAABYAFKB9rIq2ypQtN57Xlfg1unHJzGiFAAAAAAEDBAIAAAAAAQBSAgAAAAHBqiVuIUuWoYIvk95Cv/O18/+NBRkwbjUV11FaXoBbEgAAAAAA/////wEYxpo7AAAAABYAFLCjrxRCCEEmk8p9FmhStS2wrvBuAAAAAAEBHxjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4BCGsCRzBEAiAFJ1pIVzTgrh87lxI3WG8OctyFgz0njA5HTNIxEsD6XgIgawSMg868PEHQuTzH2nYYXO29Aw0AWwgBi+K5i7rL33sBIQN2DcygXzmX3GWykwYPfynxUUyMUnBI4SgCsEHU/DQKJwAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAAAIgIDbv4sJVYhmGVTup1lw93GQWXKFDbgWqNaTG6wJFHPeW0Y9p2HPlQAAIABAACAAAAAgAEAAABiAAAAAA==
* Case: PSBTv0 but with PSBT_GLOBAL_INPUT_COUNT. ** Bytes in Hex:
70736274ff01007102000000010b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc80000000000feffffff020008af2f00000000160014c430f64c4756da310dbd1a085572ef299926272c8bbdeb0b00000000160014a07dac8ab6ca942d379ed795f835ba71c9cc68850000000001040102000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e01086b02473044022005275a485734e0ae1f3b971237586f0e72dc85833d278c0e474cd23112c0fa5e02206b048c83cebc3c41d0b93cc7da76185cedbd030d005b08018be2b98bbacbdf7b012103760dcca05f3997dc65b293060f7f29f1514c8c527048e12802b041d4fc340a2700220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a000000002202036efe2c255621986553ba9d65c3ddc64165ca1436e05aa35a4c6eb02451cf796d18f69d873e540000800100008000000080010000006200000000
** Base64 String:
cHNidP8BAHECAAAAAQsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAAAAAAD+////AgAIry8AAAAAFgAUxDD2TEdW2jENvRoIVXLvKZkmJyyLvesLAAAAABYAFKB9rIq2ypQtN57Xlfg1unHJzGiFAAAAAAEEAQIAAQBSAgAAAAHBqiVuIUuWoYIvk95Cv/O18/+NBRkwbjUV11FaXoBbEgAAAAAA/////wEYxpo7AAAAABYAFLCjrxRCCEEmk8p9FmhStS2wrvBuAAAAAAEBHxjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4BCGsCRzBEAiAFJ1pIVzTgrh87lxI3WG8OctyFgz0njA5HTNIxEsD6XgIgawSMg868PEHQuTzH2nYYXO29Aw0AWwgBi+K5i7rL33sBIQN2DcygXzmX3GWykwYPfynxUUyMUnBI4SgCsEHU/DQKJwAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAAAIgIDbv4sJVYhmGVTup1lw93GQWXKFDbgWqNaTG6wJFHPeW0Y9p2HPlQAAIABAACAAAAAgAEAAABiAAAAAA==
* Case: PSBTv0 but with PSBT_GLOBAL_OUTPUT_COUNT. ** Bytes in Hex:
70736274ff01007102000000010b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc80000000000feffffff020008af2f00000000160014c430f64c4756da310dbd1a085572ef299926272c8bbdeb0b00000000160014a07dac8ab6ca942d379ed795f835ba71c9cc68850000000001050102000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e01086b02473044022005275a485734e0ae1f3b971237586f0e72dc85833d278c0e474cd23112c0fa5e02206b048c83cebc3c41d0b93cc7da76185cedbd030d005b08018be2b98bbacbdf7b012103760dcca05f3997dc65b293060f7f29f1514c8c527048e12802b041d4fc340a2700220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a000000002202036efe2c255621986553ba9d65c3ddc64165ca1436e05aa35a4c6eb02451cf796d18f69d873e540000800100008000000080010000006200000000
** Base64 String:
cHNidP8BAHECAAAAAQsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAAAAAAD+////AgAIry8AAAAAFgAUxDD2TEdW2jENvRoIVXLvKZkmJyyLvesLAAAAABYAFKB9rIq2ypQtN57Xlfg1unHJzGiFAAAAAAEFAQIAAQBSAgAAAAHBqiVuIUuWoYIvk95Cv/O18/+NBRkwbjUV11FaXoBbEgAAAAAA/////wEYxpo7AAAAABYAFLCjrxRCCEEmk8p9FmhStS2wrvBuAAAAAAEBHxjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4BCGsCRzBEAiAFJ1pIVzTgrh87lxI3WG8OctyFgz0njA5HTNIxEsD6XgIgawSMg868PEHQuTzH2nYYXO29Aw0AWwgBi+K5i7rL33sBIQN2DcygXzmX3GWykwYPfynxUUyMUnBI4SgCsEHU/DQKJwAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAAAIgIDbv4sJVYhmGVTup1lw93GQWXKFDbgWqNaTG6wJFHPeW0Y9p2HPlQAAIABAACAAAAAgAEAAABiAAAAAA==
* Case: PSBTv0 but with PSBT_GLOBAL_TX_MODIFIABLE. ** Bytes in Hex:
70736274ff01007102000000010b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc80000000000feffffff020008af2f00000000160014c430f64c4756da310dbd1a085572ef299926272c8bbdeb0b00000000160014a07dac8ab6ca942d379ed795f835ba71c9cc68850000000001060100000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e01086b02473044022005275a485734e0ae1f3b971237586f0e72dc85833d278c0e474cd23112c0fa5e02206b048c83cebc3c41d0b93cc7da76185cedbd030d005b08018be2b98bbacbdf7b012103760dcca05f3997dc65b293060f7f29f1514c8c527048e12802b041d4fc340a2700220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a000000002202036efe2c255621986553ba9d65c3ddc64165ca1436e05aa35a4c6eb02451cf796d18f69d873e540000800100008000000080010000006200000000
** Base64 String:
cHNidP8BAHECAAAAAQsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAAAAAAD+////AgAIry8AAAAAFgAUxDD2TEdW2jENvRoIVXLvKZkmJyyLvesLAAAAABYAFKB9rIq2ypQtN57Xlfg1unHJzGiFAAAAAAEGAQAAAQBSAgAAAAHBqiVuIUuWoYIvk95Cv/O18/+NBRkwbjUV11FaXoBbEgAAAAAA/////wEYxpo7AAAAABYAFLCjrxRCCEEmk8p9FmhStS2wrvBuAAAAAAEBHxjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4BCGsCRzBEAiAFJ1pIVzTgrh87lxI3WG8OctyFgz0njA5HTNIxEsD6XgIgawSMg868PEHQuTzH2nYYXO29Aw0AWwgBi+K5i7rL33sBIQN2DcygXzmX3GWykwYPfynxUUyMUnBI4SgCsEHU/DQKJwAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAAAIgIDbv4sJVYhmGVTup1lw93GQWXKFDbgWqNaTG6wJFHPeW0Y9p2HPlQAAIABAACAAAAAgAEAAABiAAAAAA==
* Case: PSBTv0 but with PSBT_IN_PREVIOUS_TXID. ** Bytes in Hex:
70736274ff01007102000000010b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc80000000000feffffff020008af2f00000000160014c430f64c4756da310dbd1a085572ef299926272c8bbdeb0b00000000160014a07dac8ab6ca942d379ed795f835ba71c9cc688500000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e01086b02473044022005275a485734e0ae1f3b971237586f0e72dc85833d278c0e474cd23112c0fa5e02206b048c83cebc3c41d0b93cc7da76185cedbd030d005b08018be2b98bbacbdf7b012103760dcca05f3997dc65b293060f7f29f1514c8c527048e12802b041d4fc340a27010e200b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc800220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a000000002202036efe2c255621986553ba9d65c3ddc64165ca1436e05aa35a4c6eb02451cf796d18f69d873e540000800100008000000080010000006200000000
** Base64 String:
cHNidP8BAHECAAAAAQsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAAAAAAD+////AgAIry8AAAAAFgAUxDD2TEdW2jENvRoIVXLvKZkmJyyLvesLAAAAABYAFKB9rIq2ypQtN57Xlfg1unHJzGiFAAAAAAABAFICAAAAAcGqJW4hS5ahgi+T3kK/87Xz/40FGTBuNRXXUVpegFsSAAAAAAD/////ARjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4AAAAAAQEfGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgEIawJHMEQCIAUnWkhXNOCuHzuXEjdYbw5y3IWDPSeMDkdM0jESwPpeAiBrBIyDzrw8QdC5PMfadhhc7b0DDQBbCAGL4rmLusvfewEhA3YNzKBfOZfcZbKTBg9/KfFRTIxScEjhKAKwQdT8NAonAQ4gCwrZIUGcHIcZc11y3HOfnqngY40f5MHu8PmUQISBX8gAIgIC1gH4SEamdV93a+AOPZ3o+xCsyTX7g8RfsBYtTK1at5IY9p2HPlQAAIABAACAAAAAgAAAAAAqAAAAACICA27+LCVWIZhlU7qdZcPdxkFlyhQ24FqjWkxusCRRz3ltGPadhz5UAACAAQAAgAAAAIABAAAAYgAAAAA=
* Case: PSBTv0 but with PSBT_IN_OUTPUT_INDEX. ** Bytes in Hex:
70736274ff01007102000000010b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc80000000000feffffff020008af2f00000000160014c430f64c4756da310dbd1a085572ef299926272c8bbdeb0b00000000160014a07dac8ab6ca942d379ed795f835ba71c9cc688500000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e01086b02473044022005275a485734e0ae1f3b971237586f0e72dc85833d278c0e474cd23112c0fa5e02206b048c83cebc3c41d0b93cc7da76185cedbd030d005b08018be2b98bbacbdf7b012103760dcca05f3997dc65b293060f7f29f1514c8c527048e12802b041d4fc340a27010f040000000000220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a000000002202036efe2c255621986553ba9d65c3ddc64165ca1436e05aa35a4c6eb02451cf796d18f69d873e540000800100008000000080010000006200000000
** Base64 String:
cHNidP8BAHECAAAAAQsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAAAAAAD+////AgAIry8AAAAAFgAUxDD2TEdW2jENvRoIVXLvKZkmJyyLvesLAAAAABYAFKB9rIq2ypQtN57Xlfg1unHJzGiFAAAAAAABAFICAAAAAcGqJW4hS5ahgi+T3kK/87Xz/40FGTBuNRXXUVpegFsSAAAAAAD/////ARjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4AAAAAAQEfGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgEIawJHMEQCIAUnWkhXNOCuHzuXEjdYbw5y3IWDPSeMDkdM0jESwPpeAiBrBIyDzrw8QdC5PMfadhhc7b0DDQBbCAGL4rmLusvfewEhA3YNzKBfOZfcZbKTBg9/KfFRTIxScEjhKAKwQdT8NAonAQ8EAAAAAAAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAAAIgIDbv4sJVYhmGVTup1lw93GQWXKFDbgWqNaTG6wJFHPeW0Y9p2HPlQAAIABAACAAAAAgAEAAABiAAAAAA==
* Case: PSBTv0 but with PSBT_IN_SEQUENCE. ** Bytes in Hex:
70736274ff01007102000000010b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc80000000000feffffff020008af2f00000000160014c430f64c4756da310dbd1a085572ef299926272c8bbdeb0b00000000160014a07dac8ab6ca942d379ed795f835ba71c9cc688500000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e01086b02473044022005275a485734e0ae1f3b971237586f0e72dc85833d278c0e474cd23112c0fa5e02206b048c83cebc3c41d0b93cc7da76185cedbd030d005b08018be2b98bbacbdf7b012103760dcca05f3997dc65b293060f7f29f1514c8c527048e12802b041d4fc340a27011004ffffffff00220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a000000002202036efe2c255621986553ba9d65c3ddc64165ca1436e05aa35a4c6eb02451cf796d18f69d873e540000800100008000000080010000006200000000
** Base64 String:
cHNidP8BAHECAAAAAQsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAAAAAAD+////AgAIry8AAAAAFgAUxDD2TEdW2jENvRoIVXLvKZkmJyyLvesLAAAAABYAFKB9rIq2ypQtN57Xlfg1unHJzGiFAAAAAAABAFICAAAAAcGqJW4hS5ahgi+T3kK/87Xz/40FGTBuNRXXUVpegFsSAAAAAAD/////ARjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4AAAAAAQEfGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgEIawJHMEQCIAUnWkhXNOCuHzuXEjdYbw5y3IWDPSeMDkdM0jESwPpeAiBrBIyDzrw8QdC5PMfadhhc7b0DDQBbCAGL4rmLusvfewEhA3YNzKBfOZfcZbKTBg9/KfFRTIxScEjhKAKwQdT8NAonARAE/////wAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAAAIgIDbv4sJVYhmGVTup1lw93GQWXKFDbgWqNaTG6wJFHPeW0Y9p2HPlQAAIABAACAAAAAgAEAAABiAAAAAA==
* Case: PSBTv0 but with PSBT_IN_REQUIRED_TIME_LOCKTIME. ** Bytes in Hex:
70736274ff01007102000000010b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc80000000000feffffff020008af2f00000000160014c430f64c4756da310dbd1a085572ef299926272c8bbdeb0b00000000160014a07dac8ab6ca942d379ed795f835ba71c9cc688500000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e01086b02473044022005275a485734e0ae1f3b971237586f0e72dc85833d278c0e474cd23112c0fa5e02206b048c83cebc3c41d0b93cc7da76185cedbd030d005b08018be2b98bbacbdf7b012103760dcca05f3997dc65b293060f7f29f1514c8c527048e12802b041d4fc340a270111048c8dc46200220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a000000002202036efe2c255621986553ba9d65c3ddc64165ca1436e05aa35a4c6eb02451cf796d18f69d873e540000800100008000000080010000006200000000
** Base64 String:
cHNidP8BAHECAAAAAQsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAAAAAAD+////AgAIry8AAAAAFgAUxDD2TEdW2jENvRoIVXLvKZkmJyyLvesLAAAAABYAFKB9rIq2ypQtN57Xlfg1unHJzGiFAAAAAAABAFICAAAAAcGqJW4hS5ahgi+T3kK/87Xz/40FGTBuNRXXUVpegFsSAAAAAAD/////ARjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4AAAAAAQEfGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgEIawJHMEQCIAUnWkhXNOCuHzuXEjdYbw5y3IWDPSeMDkdM0jESwPpeAiBrBIyDzrw8QdC5PMfadhhc7b0DDQBbCAGL4rmLusvfewEhA3YNzKBfOZfcZbKTBg9/KfFRTIxScEjhKAKwQdT8NAonAREEjI3EYgAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAAAIgIDbv4sJVYhmGVTup1lw93GQWXKFDbgWqNaTG6wJFHPeW0Y9p2HPlQAAIABAACAAAAAgAEAAABiAAAAAA==
* Case: PSBTv0 but with PSBT_IN_REQUIRED_HEIGHT_LOCKTIME. ** Bytes in Hex:
70736274ff01007102000000010b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc80000000000feffffff020008af2f00000000160014c430f64c4756da310dbd1a085572ef299926272c8bbdeb0b00000000160014a07dac8ab6ca942d379ed795f835ba71c9cc688500000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e01086b02473044022005275a485734e0ae1f3b971237586f0e72dc85833d278c0e474cd23112c0fa5e02206b048c83cebc3c41d0b93cc7da76185cedbd030d005b08018be2b98bbacbdf7b012103760dcca05f3997dc65b293060f7f29f1514c8c527048e12802b041d4fc340a270112041027000000220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a000000002202036efe2c255621986553ba9d65c3ddc64165ca1436e05aa35a4c6eb02451cf796d18f69d873e540000800100008000000080010000006200000000
** Base64 String:
cHNidP8BAHECAAAAAQsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAAAAAAD+////AgAIry8AAAAAFgAUxDD2TEdW2jENvRoIVXLvKZkmJyyLvesLAAAAABYAFKB9rIq2ypQtN57Xlfg1unHJzGiFAAAAAAABAFICAAAAAcGqJW4hS5ahgi+T3kK/87Xz/40FGTBuNRXXUVpegFsSAAAAAAD/////ARjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4AAAAAAQEfGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgEIawJHMEQCIAUnWkhXNOCuHzuXEjdYbw5y3IWDPSeMDkdM0jESwPpeAiBrBIyDzrw8QdC5PMfadhhc7b0DDQBbCAGL4rmLusvfewEhA3YNzKBfOZfcZbKTBg9/KfFRTIxScEjhKAKwQdT8NAonARIEECcAAAAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAAAIgIDbv4sJVYhmGVTup1lw93GQWXKFDbgWqNaTG6wJFHPeW0Y9p2HPlQAAIABAACAAAAAgAEAAABiAAAAAA==
* Case: PSBTv0 but with PSBT_OUT_AMOUNT. ** Bytes in Hex:
70736274ff01007102000000010b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc80000000000feffffff020008af2f00000000160014c430f64c4756da310dbd1a085572ef299926272c8bbdeb0b00000000160014a07dac8ab6ca942d379ed795f835ba71c9cc688500000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e01086b02473044022005275a485734e0ae1f3b971237586f0e72dc85833d278c0e474cd23112c0fa5e02206b048c83cebc3c41d0b93cc7da76185cedbd030d005b08018be2b98bbacbdf7b012103760dcca05f3997dc65b293060f7f29f1514c8c527048e12802b041d4fc340a2700220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a0000000103080008af2f00000000002202036efe2c255621986553ba9d65c3ddc64165ca1436e05aa35a4c6eb02451cf796d18f69d873e540000800100008000000080010000006200000000
** Base64 String:
cHNidP8BAHECAAAAAQsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAAAAAAD+////AgAIry8AAAAAFgAUxDD2TEdW2jENvRoIVXLvKZkmJyyLvesLAAAAABYAFKB9rIq2ypQtN57Xlfg1unHJzGiFAAAAAAABAFICAAAAAcGqJW4hS5ahgi+T3kK/87Xz/40FGTBuNRXXUVpegFsSAAAAAAD/////ARjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4AAAAAAQEfGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgEIawJHMEQCIAUnWkhXNOCuHzuXEjdYbw5y3IWDPSeMDkdM0jESwPpeAiBrBIyDzrw8QdC5PMfadhhc7b0DDQBbCAGL4rmLusvfewEhA3YNzKBfOZfcZbKTBg9/KfFRTIxScEjhKAKwQdT8NAonACICAtYB+EhGpnVfd2vgDj2d6PsQrMk1+4PEX7AWLUytWreSGPadhz5UAACAAQAAgAAAAIAAAAAAKgAAAAEDCAAIry8AAAAAACICA27+LCVWIZhlU7qdZcPdxkFlyhQ24FqjWkxusCRRz3ltGPadhz5UAACAAQAAgAAAAIABAAAAYgAAAAA=
* Case: PSBTv0 but with PSBT_OUT_SCRIPT. ** Bytes in Hex:
70736274ff01007102000000010b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc80000000000feffffff020008af2f00000000160014c430f64c4756da310dbd1a085572ef299926272c8bbdeb0b00000000160014a07dac8ab6ca942d379ed795f835ba71c9cc688500000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e01086b02473044022005275a485734e0ae1f3b971237586f0e72dc85833d278c0e474cd23112c0fa5e02206b048c83cebc3c41d0b93cc7da76185cedbd030d005b08018be2b98bbacbdf7b012103760dcca05f3997dc65b293060f7f29f1514c8c527048e12802b041d4fc340a2700220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a0000000104160014a07dac8ab6ca942d379ed795f835ba71c9cc6885002202036efe2c255621986553ba9d65c3ddc64165ca1436e05aa35a4c6eb02451cf796d18f69d873e540000800100008000000080010000006200000000
** Base64 String:
cHNidP8BAHECAAAAAQsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAAAAAAD+////AgAIry8AAAAAFgAUxDD2TEdW2jENvRoIVXLvKZkmJyyLvesLAAAAABYAFKB9rIq2ypQtN57Xlfg1unHJzGiFAAAAAAABAFICAAAAAcGqJW4hS5ahgi+T3kK/87Xz/40FGTBuNRXXUVpegFsSAAAAAAD/////ARjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4AAAAAAQEfGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgEIawJHMEQCIAUnWkhXNOCuHzuXEjdYbw5y3IWDPSeMDkdM0jESwPpeAiBrBIyDzrw8QdC5PMfadhhc7b0DDQBbCAGL4rmLusvfewEhA3YNzKBfOZfcZbKTBg9/KfFRTIxScEjhKAKwQdT8NAonACICAtYB+EhGpnVfd2vgDj2d6PsQrMk1+4PEX7AWLUytWreSGPadhz5UAACAAQAAgAAAAIAAAAAAKgAAAAEEFgAUoH2sirbKlC03nteV+DW6ccnMaIUAIgIDbv4sJVYhmGVTup1lw93GQWXKFDbgWqNaTG6wJFHPeW0Y9p2HPlQAAIABAACAAAAAgAEAAABiAAAAAA==
* Case: PSBTv2 missing PSBT_GLOBAL_INPUT_COUNT. ** Bytes in Hex:
70736274ff01020402000000010304000000000105010201fb0402000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e010e200b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc8010f0400000000011004feffffff00220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a0000000103080008af2f000000000104160014c430f64c4756da310dbd1a085572ef299926272c00220202e36fbff53dd534070cf8fd396614680f357a9b85db7340bf1cfa745d2ad7b34018f69d873e54000080010000800000008001000000640000000103088bbdeb0b0000000001041600144dd193ac964a56ac1b9e1cca8454fe2f474f851300
** Base64 String:
cHNidP8BAgQCAAAAAQMEAAAAAAEFAQIB+wQCAAAAAAEAUgIAAAABwaolbiFLlqGCL5PeQr/ztfP/jQUZMG41FddRWl6AWxIAAAAAAP////8BGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgAAAAABAR8Yxpo7AAAAABYAFLCjrxRCCEEmk8p9FmhStS2wrvBuAQ4gCwrZIUGcHIcZc11y3HOfnqngY40f5MHu8PmUQISBX8gBDwQAAAAAARAE/v///wAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAABAwgACK8vAAAAAAEEFgAUxDD2TEdW2jENvRoIVXLvKZkmJywAIgIC42+/9T3VNAcM+P05ZhRoDzV6m4Xbc0C/HPp0XSrXs0AY9p2HPlQAAIABAACAAAAAgAEAAABkAAAAAQMIi73rCwAAAAABBBYAFE3Rk6yWSlasG54cyoRU/i9HT4UTAA==
* Case: PSBTv2 missing PSBT_GLOBAL_OUTPUT_COUNT. ** Bytes in Hex:
70736274ff01020402000000010304000000000104010101fb0402000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e010e200b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc8010f0400000000011004feffffff00220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a0000000103080008af2f000000000104160014c430f64c4756da310dbd1a085572ef299926272c00220202e36fbff53dd534070cf8fd396614680f357a9b85db7340bf1cfa745d2ad7b34018f69d873e54000080010000800000008001000000640000000103088bbdeb0b0000000001041600144dd193ac964a56ac1b9e1cca8454fe2f474f851300
** Base64 String:
cHNidP8BAgQCAAAAAQMEAAAAAAEEAQEB+wQCAAAAAAEAUgIAAAABwaolbiFLlqGCL5PeQr/ztfP/jQUZMG41FddRWl6AWxIAAAAAAP////8BGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgAAAAABAR8Yxpo7AAAAABYAFLCjrxRCCEEmk8p9FmhStS2wrvBuAQ4gCwrZIUGcHIcZc11y3HOfnqngY40f5MHu8PmUQISBX8gBDwQAAAAAARAE/v///wAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAABAwgACK8vAAAAAAEEFgAUxDD2TEdW2jENvRoIVXLvKZkmJywAIgIC42+/9T3VNAcM+P05ZhRoDzV6m4Xbc0C/HPp0XSrXs0AY9p2HPlQAAIABAACAAAAAgAEAAABkAAAAAQMIi73rCwAAAAABBBYAFE3Rk6yWSlasG54cyoRU/i9HT4UTAA==
* Case: PSBTv2 missing PSBT_IN_PREVIOUS_TXID. ** Bytes in Hex:
70736274ff0102040200000001030400000000010401010105010201fb0402000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e010f0400000000011004feffffff00220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a0000000103080008af2f000000000104160014c430f64c4756da310dbd1a085572ef299926272c00220202e36fbff53dd534070cf8fd396614680f357a9b85db7340bf1cfa745d2ad7b34018f69d873e54000080010000800000008001000000640000000103088bbdeb0b0000000001041600144dd193ac964a56ac1b9e1cca8454fe2f474f851300
** Base64 String:
cHNidP8BAgQCAAAAAQMEAAAAAAEEAQEBBQECAfsEAgAAAAABAFICAAAAAcGqJW4hS5ahgi+T3kK/87Xz/40FGTBuNRXXUVpegFsSAAAAAAD/////ARjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4AAAAAAQEfGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgEPBAAAAAABEAT+////ACICAtYB+EhGpnVfd2vgDj2d6PsQrMk1+4PEX7AWLUytWreSGPadhz5UAACAAQAAgAAAAIAAAAAAKgAAAAEDCAAIry8AAAAAAQQWABTEMPZMR1baMQ29GghVcu8pmSYnLAAiAgLjb7/1PdU0Bwz4/TlmFGgPNXqbhdtzQL8c+nRdKtezQBj2nYc+VAAAgAEAAIAAAACAAQAAAGQAAAABAwiLvesLAAAAAAEEFgAUTdGTrJZKVqwbnhzKhFT+L0dPhRMA
* Case: PSBTv2 missing PSBT_IN_OUTPUT_INDEX. ** Bytes in Hex:
70736274ff0102040200000001030400000000010401010105010201fb0402000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e010e200b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc8011004feffffff00220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a0000000103080008af2f000000000104160014c430f64c4756da310dbd1a085572ef299926272c00220202e36fbff53dd534070cf8fd396614680f357a9b85db7340bf1cfa745d2ad7b34018f69d873e54000080010000800000008001000000640000000103088bbdeb0b0000000001041600144dd193ac964a56ac1b9e1cca8454fe2f474f851300
** Base64 String:
cHNidP8BAgQCAAAAAQMEAAAAAAEEAQEBBQECAfsEAgAAAAABAFICAAAAAcGqJW4hS5ahgi+T3kK/87Xz/40FGTBuNRXXUVpegFsSAAAAAAD/////ARjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4AAAAAAQEfGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgEOIAsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IARAE/v///wAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAABAwgACK8vAAAAAAEEFgAUxDD2TEdW2jENvRoIVXLvKZkmJywAIgIC42+/9T3VNAcM+P05ZhRoDzV6m4Xbc0C/HPp0XSrXs0AY9p2HPlQAAIABAACAAAAAgAEAAABkAAAAAQMIi73rCwAAAAABBBYAFE3Rk6yWSlasG54cyoRU/i9HT4UTAA==
* Case: PSBTv2 missing PSBT_OUT_AMOUNT. ** Bytes in Hex:
70736274ff0102040200000001030400000000010401010105010201fb0402000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e010e200b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc8010f0400000000011004feffffff00220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a0000000104160014c430f64c4756da310dbd1a085572ef299926272c00220202e36fbff53dd534070cf8fd396614680f357a9b85db7340bf1cfa745d2ad7b34018f69d873e54000080010000800000008001000000640000000103088bbdeb0b0000000001041600144dd193ac964a56ac1b9e1cca8454fe2f474f851300
** Base64 String:
cHNidP8BAgQCAAAAAQMEAAAAAAEEAQEBBQECAfsEAgAAAAABAFICAAAAAcGqJW4hS5ahgi+T3kK/87Xz/40FGTBuNRXXUVpegFsSAAAAAAD/////ARjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4AAAAAAQEfGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgEOIAsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAQ8EAAAAAAEQBP7///8AIgIC1gH4SEamdV93a+AOPZ3o+xCsyTX7g8RfsBYtTK1at5IY9p2HPlQAAIABAACAAAAAgAAAAAAqAAAAAQQWABTEMPZMR1baMQ29GghVcu8pmSYnLAAiAgLjb7/1PdU0Bwz4/TlmFGgPNXqbhdtzQL8c+nRdKtezQBj2nYc+VAAAgAEAAIAAAACAAQAAAGQAAAABAwiLvesLAAAAAAEEFgAUTdGTrJZKVqwbnhzKhFT+L0dPhRMA
* Case: PSBTv2 missing PSBT_OUT_SCRIPT. ** Bytes in Hex:
70736274ff0102040200000001030400000000010401010105010201fb0402000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e010e200b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc8010f0400000000011004feffffff00220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a0000000103080008af2f0000000000220202e36fbff53dd534070cf8fd396614680f357a9b85db7340bf1cfa745d2ad7b34018f69d873e54000080010000800000008001000000640000000103088bbdeb0b0000000001041600144dd193ac964a56ac1b9e1cca8454fe2f474f851300
** Base64 String:
cHNidP8BAgQCAAAAAQMEAAAAAAEEAQEBBQECAfsEAgAAAAABAFICAAAAAcGqJW4hS5ahgi+T3kK/87Xz/40FGTBuNRXXUVpegFsSAAAAAAD/////ARjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4AAAAAAQEfGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgEOIAsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAQ8EAAAAAAEQBP7///8AIgIC1gH4SEamdV93a+AOPZ3o+xCsyTX7g8RfsBYtTK1at5IY9p2HPlQAAIABAACAAAAAgAAAAAAqAAAAAQMIAAivLwAAAAAAIgIC42+/9T3VNAcM+P05ZhRoDzV6m4Xbc0C/HPp0XSrXs0AY9p2HPlQAAIABAACAAAAAgAEAAABkAAAAAQMIi73rCwAAAAABBBYAFE3Rk6yWSlasG54cyoRU/i9HT4UTAA==
* Case: PSBTv2 with PSBT_IN_REQUIRED_TIME_LOCKTIME less than 500000000. ** Bytes in Hex:
70736274ff01020402000000010401010105010201fb0402000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e010e200b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc8010f0400000000011104ff64cd1d00220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a0000000103080008af2f000000000104160014c430f64c4756da310dbd1a085572ef299926272c00220202e36fbff53dd534070cf8fd396614680f357a9b85db7340bf1cfa745d2ad7b34018f69d873e54000080010000800000008001000000640000000103088bbdeb0b0000000001041600144dd193ac964a56ac1b9e1cca8454fe2f474f851300
** Base64 String:
cHNidP8BAgQCAAAAAQQBAQEFAQIB+wQCAAAAAAEAUgIAAAABwaolbiFLlqGCL5PeQr/ztfP/jQUZMG41FddRWl6AWxIAAAAAAP////8BGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgAAAAABAR8Yxpo7AAAAABYAFLCjrxRCCEEmk8p9FmhStS2wrvBuAQ4gCwrZIUGcHIcZc11y3HOfnqngY40f5MHu8PmUQISBX8gBDwQAAAAAAREE/2TNHQAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAABAwgACK8vAAAAAAEEFgAUxDD2TEdW2jENvRoIVXLvKZkmJywAIgIC42+/9T3VNAcM+P05ZhRoDzV6m4Xbc0C/HPp0XSrXs0AY9p2HPlQAAIABAACAAAAAgAEAAABkAAAAAQMIi73rCwAAAAABBBYAFE3Rk6yWSlasG54cyoRU/i9HT4UTAA==
* Case: PSBTv2 with PSBT_IN_REQUIRED_HEIGHT_LOCKTIME greater than or equal to 500000000. ** Bytes in Hex:
70736274ff01020402000000010401010105010201fb0402000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e010e200b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc8010f04000000000112040065cd1d00220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a0000000103080008af2f000000000104160014c430f64c4756da310dbd1a085572ef299926272c00220202e36fbff53dd534070cf8fd396614680f357a9b85db7340bf1cfa745d2ad7b34018f69d873e54000080010000800000008001000000640000000103088bbdeb0b0000000001041600144dd193ac964a56ac1b9e1cca8454fe2f474f851300
** Base64 String:
cHNidP8BAgQCAAAAAQQBAQEFAQIB+wQCAAAAAAEAUgIAAAABwaolbiFLlqGCL5PeQr/ztfP/jQUZMG41FddRWl6AWxIAAAAAAP////8BGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgAAAAABAR8Yxpo7AAAAABYAFLCjrxRCCEEmk8p9FmhStS2wrvBuAQ4gCwrZIUGcHIcZc11y3HOfnqngY40f5MHu8PmUQISBX8gBDwQAAAAAARIEAGXNHQAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAABAwgACK8vAAAAAAEEFgAUxDD2TEdW2jENvRoIVXLvKZkmJywAIgIC42+/9T3VNAcM+P05ZhRoDzV6m4Xbc0C/HPp0XSrXs0AY9p2HPlQAAIABAACAAAAAgAEAAABkAAAAAQMIi73rCwAAAAABBBYAFE3Rk6yWSlasG54cyoRU/i9HT4UTAA==
The following are valid PSBTs * Case: 1 input, 2 output PSBTv2, required fields only. ** Bytes in Hex:
70736274ff01020402000000010401010105010201fb040200000000010e200b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc8010f0400000000000103080008af2f000000000104160014c430f64c4756da310dbd1a085572ef299926272c000103088bbdeb0b0000000001041600144dd193ac964a56ac1b9e1cca8454fe2f474f851300
** Base64 String:
cHNidP8BAgQCAAAAAQQBAQEFAQIB+wQCAAAAAAEOIAsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAQ8EAAAAAAABAwgACK8vAAAAAAEEFgAUxDD2TEdW2jENvRoIVXLvKZkmJywAAQMIi73rCwAAAAABBBYAFE3Rk6yWSlasG54cyoRU/i9HT4UTAA==
* Case: 1 input, 2 output updated PSBTv2. ** Bytes in HEx:
70736274ff01020402000000010401010105010201fb0402000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e010e200b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc8010f040000000000220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a0000000103080008af2f000000000104160014c430f64c4756da310dbd1a085572ef299926272c00220202e36fbff53dd534070cf8fd396614680f357a9b85db7340bf1cfa745d2ad7b34018f69d873e54000080010000800000008001000000640000000103088bbdeb0b0000000001041600144dd193ac964a56ac1b9e1cca8454fe2f474f851300
** Base64 String:
cHNidP8BAgQCAAAAAQQBAQEFAQIB+wQCAAAAAAEAUgIAAAABwaolbiFLlqGCL5PeQr/ztfP/jQUZMG41FddRWl6AWxIAAAAAAP////8BGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgAAAAABAR8Yxpo7AAAAABYAFLCjrxRCCEEmk8p9FmhStS2wrvBuAQ4gCwrZIUGcHIcZc11y3HOfnqngY40f5MHu8PmUQISBX8gBDwQAAAAAACICAtYB+EhGpnVfd2vgDj2d6PsQrMk1+4PEX7AWLUytWreSGPadhz5UAACAAQAAgAAAAIAAAAAAKgAAAAEDCAAIry8AAAAAAQQWABTEMPZMR1baMQ29GghVcu8pmSYnLAAiAgLjb7/1PdU0Bwz4/TlmFGgPNXqbhdtzQL8c+nRdKtezQBj2nYc+VAAAgAEAAIAAAACAAQAAAGQAAAABAwiLvesLAAAAAAEEFgAUTdGTrJZKVqwbnhzKhFT+L0dPhRMA
* Case: 1 input, 2 output updated PSBTv2, with PSBT_IN_SEQUENCE. ** Bytes in Hex:
70736274ff01020402000000010401010105010201fb0402000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e010e200b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc8010f0400000000011004feffffff00220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a0000000103080008af2f000000000104160014c430f64c4756da310dbd1a085572ef299926272c00220202e36fbff53dd534070cf8fd396614680f357a9b85db7340bf1cfa745d2ad7b34018f69d873e54000080010000800000008001000000640000000103088bbdeb0b0000000001041600144dd193ac964a56ac1b9e1cca8454fe2f474f851300
** Base64 String:
cHNidP8BAgQCAAAAAQQBAQEFAQIB+wQCAAAAAAEAUgIAAAABwaolbiFLlqGCL5PeQr/ztfP/jQUZMG41FddRWl6AWxIAAAAAAP////8BGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgAAAAABAR8Yxpo7AAAAABYAFLCjrxRCCEEmk8p9FmhStS2wrvBuAQ4gCwrZIUGcHIcZc11y3HOfnqngY40f5MHu8PmUQISBX8gBDwQAAAAAARAE/v///wAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAABAwgACK8vAAAAAAEEFgAUxDD2TEdW2jENvRoIVXLvKZkmJywAIgIC42+/9T3VNAcM+P05ZhRoDzV6m4Xbc0C/HPp0XSrXs0AY9p2HPlQAAIABAACAAAAAgAEAAABkAAAAAQMIi73rCwAAAAABBBYAFE3Rk6yWSlasG54cyoRU/i9HT4UTAA==
* Case: 1 input, 2 output updated PSBTv2, with PSBT_IN_SEQUENCE, and all locktime fields ** Bytes in Hex:
70736274ff0102040200000001030400000000010401010105010201fb0402000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e010e200b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc8010f0400000000011004feffffff0111048c8dc4620112041027000000220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a0000000103080008af2f000000000104160014c430f64c4756da310dbd1a085572ef299926272c00220202e36fbff53dd534070cf8fd396614680f357a9b85db7340bf1cfa745d2ad7b34018f69d873e54000080010000800000008001000000640000000103088bbdeb0b0000000001041600144dd193ac964a56ac1b9e1cca8454fe2f474f851300
** Base64 String:
cHNidP8BAgQCAAAAAQMEAAAAAAEEAQEBBQECAfsEAgAAAAABAFICAAAAAcGqJW4hS5ahgi+T3kK/87Xz/40FGTBuNRXXUVpegFsSAAAAAAD/////ARjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4AAAAAAQEfGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgEOIAsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAQ8EAAAAAAEQBP7///8BEQSMjcRiARIEECcAAAAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAABAwgACK8vAAAAAAEEFgAUxDD2TEdW2jENvRoIVXLvKZkmJywAIgIC42+/9T3VNAcM+P05ZhRoDzV6m4Xbc0C/HPp0XSrXs0AY9p2HPlQAAIABAACAAAAAgAEAAABkAAAAAQMIi73rCwAAAAABBBYAFE3Rk6yWSlasG54cyoRU/i9HT4UTAA==
* Case: 1 input, 2 output updated PSBTv2, with Inputs Modifiable Flag (bit 0) of PSBT_GLOBAL_TX_MODIFIABLE set ** Bytes in Hex:
70736274ff0102040200000001040101010501020106010101fb0402000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e010e200b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc8010f040000000000220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a0000000103080008af2f000000000104160014c430f64c4756da310dbd1a085572ef299926272c00220202e36fbff53dd534070cf8fd396614680f357a9b85db7340bf1cfa745d2ad7b34018f69d873e54000080010000800000008001000000640000000103088bbdeb0b0000000001041600144dd193ac964a56ac1b9e1cca8454fe2f474f851300
** Base64 String:
cHNidP8BAgQCAAAAAQQBAQEFAQIBBgEBAfsEAgAAAAABAFICAAAAAcGqJW4hS5ahgi+T3kK/87Xz/40FGTBuNRXXUVpegFsSAAAAAAD/////ARjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4AAAAAAQEfGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgEOIAsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAQ8EAAAAAAAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAABAwgACK8vAAAAAAEEFgAUxDD2TEdW2jENvRoIVXLvKZkmJywAIgIC42+/9T3VNAcM+P05ZhRoDzV6m4Xbc0C/HPp0XSrXs0AY9p2HPlQAAIABAACAAAAAgAEAAABkAAAAAQMIi73rCwAAAAABBBYAFE3Rk6yWSlasG54cyoRU/i9HT4UTAA==
* Case: 1 input, 2 output updated PSBTv2, with Outputs Modifiable Flag (bit 1) of PSBT_GLOBAL_TX_MODIFIABLE set ** Bytes in Hex:
70736274ff0102040200000001040101010501020106010201fb0402000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e010e200b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc8010f040000000000220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a0000000103080008af2f000000000104160014c430f64c4756da310dbd1a085572ef299926272c00220202e36fbff53dd534070cf8fd396614680f357a9b85db7340bf1cfa745d2ad7b34018f69d873e54000080010000800000008001000000640000000103088bbdeb0b0000000001041600144dd193ac964a56ac1b9e1cca8454fe2f474f851300
** Base64 String:
cHNidP8BAgQCAAAAAQQBAQEFAQIBBgECAfsEAgAAAAABAFICAAAAAcGqJW4hS5ahgi+T3kK/87Xz/40FGTBuNRXXUVpegFsSAAAAAAD/////ARjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4AAAAAAQEfGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgEOIAsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAQ8EAAAAAAAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAABAwgACK8vAAAAAAEEFgAUxDD2TEdW2jENvRoIVXLvKZkmJywAIgIC42+/9T3VNAcM+P05ZhRoDzV6m4Xbc0C/HPp0XSrXs0AY9p2HPlQAAIABAACAAAAAgAEAAABkAAAAAQMIi73rCwAAAAABBBYAFE3Rk6yWSlasG54cyoRU/i9HT4UTAA==
* Case: 1 input, 2 output updated PSBTv2, with Has SIGHASH_SINGLE Flag (bit 2) of PSBT_GLOBAL_TX_MODIFIABLE set ** Bytes in Hex:
70736274ff0102040200000001040101010501020106010401fb0402000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e010e200b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc8010f040000000000220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a0000000103080008af2f000000000104160014c430f64c4756da310dbd1a085572ef299926272c00220202e36fbff53dd534070cf8fd396614680f357a9b85db7340bf1cfa745d2ad7b34018f69d873e54000080010000800000008001000000640000000103088bbdeb0b0000000001041600144dd193ac964a56ac1b9e1cca8454fe2f474f851300
** Base64 String:
cHNidP8BAgQCAAAAAQQBAQEFAQIBBgEEAfsEAgAAAAABAFICAAAAAcGqJW4hS5ahgi+T3kK/87Xz/40FGTBuNRXXUVpegFsSAAAAAAD/////ARjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4AAAAAAQEfGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgEOIAsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAQ8EAAAAAAAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAABAwgACK8vAAAAAAEEFgAUxDD2TEdW2jENvRoIVXLvKZkmJywAIgIC42+/9T3VNAcM+P05ZhRoDzV6m4Xbc0C/HPp0XSrXs0AY9p2HPlQAAIABAACAAAAAgAEAAABkAAAAAQMIi73rCwAAAAABBBYAFE3Rk6yWSlasG54cyoRU/i9HT4UTAA==
* Case: 1 input, 2 output updated PSBTv2, with an undefined flag (bit 3) of PSBT_GLOBAL_TX_MODIFIABLE set ** Bytes in Hex:
70736274ff0102040200000001040101010501020106010801fb0402000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e010e200b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc8010f040000000000220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a0000000103080008af2f000000000104160014c430f64c4756da310dbd1a085572ef299926272c00220202e36fbff53dd534070cf8fd396614680f357a9b85db7340bf1cfa745d2ad7b34018f69d873e54000080010000800000008001000000640000000103088bbdeb0b0000000001041600144dd193ac964a56ac1b9e1cca8454fe2f474f851300
** Base64 String:
cHNidP8BAgQCAAAAAQQBAQEFAQIBBgEIAfsEAgAAAAABAFICAAAAAcGqJW4hS5ahgi+T3kK/87Xz/40FGTBuNRXXUVpegFsSAAAAAAD/////ARjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4AAAAAAQEfGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgEOIAsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAQ8EAAAAAAAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAABAwgACK8vAAAAAAEEFgAUxDD2TEdW2jENvRoIVXLvKZkmJywAIgIC42+/9T3VNAcM+P05ZhRoDzV6m4Xbc0C/HPp0XSrXs0AY9p2HPlQAAIABAACAAAAAgAEAAABkAAAAAQMIi73rCwAAAAABBBYAFE3Rk6yWSlasG54cyoRU/i9HT4UTAA==
* Case: 1 input, 2 output updated PSBTv2, with both Inputs Modifiable Flag (bit 0) and Outputs Modifiable Flag (bit 1) of PSBT_GLOBAL_TX_MODIFIABLE set ** Bytes in Hex:
70736274ff0102040200000001040101010501020106010301fb0402000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e010e200b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc8010f040000000000220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a0000000103080008af2f000000000104160014c430f64c4756da310dbd1a085572ef299926272c00220202e36fbff53dd534070cf8fd396614680f357a9b85db7340bf1cfa745d2ad7b34018f69d873e54000080010000800000008001000000640000000103088bbdeb0b0000000001041600144dd193ac964a56ac1b9e1cca8454fe2f474f851300
** Base64 String:
cHNidP8BAgQCAAAAAQQBAQEFAQIBBgEDAfsEAgAAAAABAFICAAAAAcGqJW4hS5ahgi+T3kK/87Xz/40FGTBuNRXXUVpegFsSAAAAAAD/////ARjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4AAAAAAQEfGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgEOIAsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAQ8EAAAAAAAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAABAwgACK8vAAAAAAEEFgAUxDD2TEdW2jENvRoIVXLvKZkmJywAIgIC42+/9T3VNAcM+P05ZhRoDzV6m4Xbc0C/HPp0XSrXs0AY9p2HPlQAAIABAACAAAAAgAEAAABkAAAAAQMIi73rCwAAAAABBBYAFE3Rk6yWSlasG54cyoRU/i9HT4UTAA==
* Case: 1 input, 2 output updated PSBTv2, with both Inputs Modifiable Flag (bit 0) and Has SIGHASH_SINGLE Flag (bit 2) of PSBT_GLOBAL_TX_MODIFIABLE set ** Bytes in Hex:
70736274ff0102040200000001040101010501020106010501fb0402000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e010e200b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc8010f040000000000220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a0000000103080008af2f000000000104160014c430f64c4756da310dbd1a085572ef299926272c00220202e36fbff53dd534070cf8fd396614680f357a9b85db7340bf1cfa745d2ad7b34018f69d873e54000080010000800000008001000000640000000103088bbdeb0b0000000001041600144dd193ac964a56ac1b9e1cca8454fe2f474f851300
** Base64 String:
cHNidP8BAgQCAAAAAQQBAQEFAQIBBgEFAfsEAgAAAAABAFICAAAAAcGqJW4hS5ahgi+T3kK/87Xz/40FGTBuNRXXUVpegFsSAAAAAAD/////ARjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4AAAAAAQEfGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgEOIAsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAQ8EAAAAAAAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAABAwgACK8vAAAAAAEEFgAUxDD2TEdW2jENvRoIVXLvKZkmJywAIgIC42+/9T3VNAcM+P05ZhRoDzV6m4Xbc0C/HPp0XSrXs0AY9p2HPlQAAIABAACAAAAAgAEAAABkAAAAAQMIi73rCwAAAAABBBYAFE3Rk6yWSlasG54cyoRU/i9HT4UTAA==
* Case: 1 input, 2 output updated PSBTv2, with both Outputs Modifiable Flag (bit 1) and Has SIGHASH_SINGLE FLag (bit 2) of PSBT_GLOBAL_TX_MODIFIABLE set ** Bytes in Hex:
70736274ff0102040200000001040101010501020106010601fb0402000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e010e200b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc8010f040000000000220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a0000000103080008af2f000000000104160014c430f64c4756da310dbd1a085572ef299926272c00220202e36fbff53dd534070cf8fd396614680f357a9b85db7340bf1cfa745d2ad7b34018f69d873e54000080010000800000008001000000640000000103088bbdeb0b0000000001041600144dd193ac964a56ac1b9e1cca8454fe2f474f851300
** Base64 String:
cHNidP8BAgQCAAAAAQQBAQEFAQIBBgEGAfsEAgAAAAABAFICAAAAAcGqJW4hS5ahgi+T3kK/87Xz/40FGTBuNRXXUVpegFsSAAAAAAD/////ARjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4AAAAAAQEfGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgEOIAsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAQ8EAAAAAAAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAABAwgACK8vAAAAAAEEFgAUxDD2TEdW2jENvRoIVXLvKZkmJywAIgIC42+/9T3VNAcM+P05ZhRoDzV6m4Xbc0C/HPp0XSrXs0AY9p2HPlQAAIABAACAAAAAgAEAAABkAAAAAQMIi73rCwAAAAABBBYAFE3Rk6yWSlasG54cyoRU/i9HT4UTAA==
* Case: 1 input, 2 output updated PSBTv2, with all defined PSBT_GLOBAL_TX_MODIFIABLE flags set ** Bytes in Hex:
70736274ff0102040200000001040101010501020106010701fb0402000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e010e200b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc8010f040000000000220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a0000000103080008af2f000000000104160014c430f64c4756da310dbd1a085572ef299926272c00220202e36fbff53dd534070cf8fd396614680f357a9b85db7340bf1cfa745d2ad7b34018f69d873e54000080010000800000008001000000640000000103088bbdeb0b0000000001041600144dd193ac964a56ac1b9e1cca8454fe2f474f851300
** Base64 String:
cHNidP8BAgQCAAAAAQQBAQEFAQIBBgEHAfsEAgAAAAABAFICAAAAAcGqJW4hS5ahgi+T3kK/87Xz/40FGTBuNRXXUVpegFsSAAAAAAD/////ARjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4AAAAAAQEfGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgEOIAsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAQ8EAAAAAAAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAABAwgACK8vAAAAAAEEFgAUxDD2TEdW2jENvRoIVXLvKZkmJywAIgIC42+/9T3VNAcM+P05ZhRoDzV6m4Xbc0C/HPp0XSrXs0AY9p2HPlQAAIABAACAAAAAgAEAAABkAAAAAQMIi73rCwAAAAABBBYAFE3Rk6yWSlasG54cyoRU/i9HT4UTAA==
* Case: 1 input, 2 output updated PSBTv2, with all possible PSBT_GLOBAL_TX_MODIFIABLE flags set ** Bytes in Hex:
70736274ff010204020000000104010101050102010601ff01fb0402000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e010e200b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc8010f040000000000220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a0000000103080008af2f000000000104160014c430f64c4756da310dbd1a085572ef299926272c00220202e36fbff53dd534070cf8fd396614680f357a9b85db7340bf1cfa745d2ad7b34018f69d873e54000080010000800000008001000000640000000103088bbdeb0b0000000001041600144dd193ac964a56ac1b9e1cca8454fe2f474f851300
** Base64 String:
cHNidP8BAgQCAAAAAQQBAQEFAQIBBgH/AfsEAgAAAAABAFICAAAAAcGqJW4hS5ahgi+T3kK/87Xz/40FGTBuNRXXUVpegFsSAAAAAAD/////ARjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4AAAAAAQEfGMaaOwAAAAAWABSwo68UQghBJpPKfRZoUrUtsK7wbgEOIAsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAQ8EAAAAAAAiAgLWAfhIRqZ1X3dr4A49nej7EKzJNfuDxF+wFi1MrVq3khj2nYc+VAAAgAEAAIAAAACAAAAAACoAAAABAwgACK8vAAAAAAEEFgAUxDD2TEdW2jENvRoIVXLvKZkmJywAIgIC42+/9T3VNAcM+P05ZhRoDzV6m4Xbc0C/HPp0XSrXs0AY9p2HPlQAAIABAACAAAAAgAEAAABkAAAAAQMIi73rCwAAAAABBBYAFE3Rk6yWSlasG54cyoRU/i9HT4UTAA==
* Case: 1 input, 2 output updated PSBTv2, with all PSBTv2 fields ** Bytes in Hex:
70736274ff010204020000000103040000000001040101010501020106010701fb0402000000000100520200000001c1aa256e214b96a1822f93de42bff3b5f3ff8d0519306e3515d7515a5e805b120000000000ffffffff0118c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e0000000001011f18c69a3b00000000160014b0a3af144208412693ca7d166852b52db0aef06e010e200b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc8010f0400000000011004feffffff0111048c8dc4620112041027000000220202d601f84846a6755f776be00e3d9de8fb10acc935fb83c45fb0162d4cad5ab79218f69d873e540000800100008000000080000000002a0000000103080008af2f000000000104160014c430f64c4756da310dbd1a085572ef299926272c00220202e36fbff53dd534070cf8fd396614680f357a9b85db7340bf1cfa745d2ad7b34018f69d873e54000080010000800000008001000000640000000103088bbdeb0b0000000001041600144dd193ac964a56ac1b9e1cca8454fe2f474f851300
** Base64 String:
cHNidP8BAgQCAAAAAQMEAAAAAAEEAQEBBQECAQYBBwH7BAIAAAAAAQBSAgAAAAHBqiVuIUuWoYIvk95Cv/O18/+NBRkwbjUV11FaXoBbEgAAAAAA/////wEYxpo7AAAAABYAFLCjrxRCCEEmk8p9FmhStS2wrvBuAAAAAAEBHxjGmjsAAAAAFgAUsKOvFEIIQSaTyn0WaFK1LbCu8G4BDiALCtkhQZwchxlzXXLcc5+eqeBjjR/kwe7w+ZRAhIFfyAEPBAAAAAABEAT+////AREEjI3EYgESBBAnAAAAIgIC1gH4SEamdV93a+AOPZ3o+xCsyTX7g8RfsBYtTK1at5IY9p2HPlQAAIABAACAAAAAgAAAAAAqAAAAAQMIAAivLwAAAAABBBYAFMQw9kxHVtoxDb0aCFVy7ymZJicsACICAuNvv/U91TQHDPj9OWYUaA81epuF23NAvxz6dF0q17NAGPadhz5UAACAAQAAgAAAAIABAAAAZAAAAAEDCIu96wsAAAAAAQQWABRN0ZOslkpWrBueHMqEVP4vR0+FEwA=
The following tests are the timelock determination algorithm. The timelock for the following PSBTs should be computed to be 0: * Case: No locktimes specified ** Bytes in Hex:
70736274ff01020402000000010401010105010201fb040200000000010e200b0ad921419c1c8719735d72dc739f9ea9e0638d1fe4c1eef0f9944084815fc8010f0400000000000103080008af2f000000000104160014c430f64c4756da310dbd1a085572ef299926272c000103088bbdeb0b0000000001041600144dd193ac964a56ac1b9e1cca8454fe2f474f851300
** Base64 String:
cHNidP8BAgQCAAAAAQQBAQEFAQIB+wQCAAAAAAEOIAsK2SFBnByHGXNdctxzn56p4GONH+TB7vD5lECEgV/IAQ8EAAAAAAABAwgACK8vAAAAAAEEFgAUxDD2TEdW2jENvRoIVXLvKZkmJywAAQMIi73rCwAAAAABBBYAFE3Rk6yWSlasG54cyoRU/i9HT4UTAA==
* Case: Fallback locktime of 0 ** Bytes in Hex:
70736274ff0102040200000001030400000000010401020105010101fb040200000000010e200f758dbfbd4da7c16c8a3309c3c81e1100f561ea646db5b01752c485e1bdde9f010f040100000000010e203a1b3b3c837d6489ea7a31d8e6c7dd503c001bef3e06958e7574808d68ca78a5010f0400000000000103084f9335770000000001041600140b1352cacd03cf6aa1b7f3c8d6388671b34a5e1100
** Base64 String:
cHNidP8BAgQCAAAAAQMEAAAAAAEEAQIBBQEBAfsEAgAAAAABDiAPdY2/vU2nwWyKMwnDyB4RAPVh6mRttbAXUsSF4b3enwEPBAEAAAAAAQ4gOhs7PIN9ZInqejHY5sfdUDwAG+8+BpWOdXSAjWjKeKUBDwQAAAAAAAEDCE+TNXcAAAAAAQQWABQLE1LKzQPPaqG388jWOIZxs0peEQA=
The timelock for the following PSBTs should be computed to be 10000: * Case: Input 1 has PSBT_IN_REQUIRED_HEIGHT_LOCKTIME of 10000, Input 2 has no locktime fields ** Bytes in Hex:
70736274ff0102040200000001030400000000010401020105010101fb040200000000010e200f758dbfbd4da7c16c8a3309c3c81e1100f561ea646db5b01752c485e1bdde9f010f04010000000112041027000000010e203a1b3b3c837d6489ea7a31d8e6c7dd503c001bef3e06958e7574808d68ca78a5010f0400000000000103084f9335770000000001041600140b1352cacd03cf6aa1b7f3c8d6388671b34a5e1100
** Base64 String:
cHNidP8BAgQCAAAAAQMEAAAAAAEEAQIBBQEBAfsEAgAAAAABDiAPdY2/vU2nwWyKMwnDyB4RAPVh6mRttbAXUsSF4b3enwEPBAEAAAABEgQQJwAAAAEOIDobOzyDfWSJ6nox2ObH3VA8ABvvPgaVjnV0gI1oynilAQ8EAAAAAAABAwhPkzV3AAAAAAEEFgAUCxNSys0Dz2qht/PI1jiGcbNKXhEA
* Case: Input 1 has PSBT_IN_REQUIRED_HEIGHT_LOCKTIME of 10000, Input 2 has PSBT_IN_REQUIRED_HEIGHT_LOCKTIME of 9000 ** Bytes in Hex:
70736274ff0102040200000001030400000000010401020105010101fb040200000000010e200f758dbfbd4da7c16c8a3309c3c81e1100f561ea646db5b01752c485e1bdde9f010f04010000000112041027000000010e203a1b3b3c837d6489ea7a31d8e6c7dd503c001bef3e06958e7574808d68ca78a5010f040000000001120428230000000103084f9335770000000001041600140b1352cacd03cf6aa1b7f3c8d6388671b34a5e1100
** Base64 String:
cHNidP8BAgQCAAAAAQMEAAAAAAEEAQIBBQEBAfsEAgAAAAABDiAPdY2/vU2nwWyKMwnDyB4RAPVh6mRttbAXUsSF4b3enwEPBAEAAAABEgQQJwAAAAEOIDobOzyDfWSJ6nox2ObH3VA8ABvvPgaVjnV0gI1oynilAQ8EAAAAAAESBCgjAAAAAQMIT5M1dwAAAAABBBYAFAsTUsrNA89qobfzyNY4hnGzSl4RAA==
* Case: Input 1 has PSBT_IN_REQUIRED_HEIGHT_LOCKTIME of 10000, Input 2 has PSBT_IN_REQUIRED_HEIGHT_LOCKTIME of 9000 and PSBT_IN_REQUIRED_TIME_LOCKTIME of 1657048460 ** Bytes in Hex:
70736274ff0102040200000001030400000000010401020105010101fb040200000000010e200f758dbfbd4da7c16c8a3309c3c81e1100f561ea646db5b01752c485e1bdde9f010f04010000000112041027000000010e203a1b3b3c837d6489ea7a31d8e6c7dd503c001bef3e06958e7574808d68ca78a5010f04000000000111048c8dc46201120428230000000103084f9335770000000001041600140b1352cacd03cf6aa1b7f3c8d6388671b34a5e1100
** Base64 String:
cHNidP8BAgQCAAAAAQMEAAAAAAEEAQIBBQEBAfsEAgAAAAABDiAPdY2/vU2nwWyKMwnDyB4RAPVh6mRttbAXUsSF4b3enwEPBAEAAAABEgQQJwAAAAEOIDobOzyDfWSJ6nox2ObH3VA8ABvvPgaVjnV0gI1oynilAQ8EAAAAAAERBIyNxGIBEgQoIwAAAAEDCE+TNXcAAAAAAQQWABQLE1LKzQPPaqG388jWOIZxs0peEQA=
* Case: Input 1 has PSBT_IN_REQUIRED_HEIGHT_LOCKTIME of 10000 and PSBT_IN_REQUIRED_TIME_LOCKTIME of 1657048459, Input 2 has PSBT_IN_REQUIRED_HEIGHT_LOCKTIME of 9000 and PSBT_IN_REQUIRED_TIME_LOCKTIME of 1657048460 ** Bytes in Hex:
70736274ff0102040200000001030400000000010401020105010101fb040200000000010e200f758dbfbd4da7c16c8a3309c3c81e1100f561ea646db5b01752c485e1bdde9f010f04010000000111048b8dc4620112041027000000010e203a1b3b3c837d6489ea7a31d8e6c7dd503c001bef3e06958e7574808d68ca78a5010f04000000000111048c8dc46201120428230000000103084f9335770000000001041600140b1352cacd03cf6aa1b7f3c8d6388671b34a5e1100
** Base64 String:
cHNidP8BAgQCAAAAAQMEAAAAAAEEAQIBBQEBAfsEAgAAAAABDiAPdY2/vU2nwWyKMwnDyB4RAPVh6mRttbAXUsSF4b3enwEPBAEAAAABEQSLjcRiARIEECcAAAABDiA6Gzs8g31kiep6Mdjmx91QPAAb7z4GlY51dICNaMp4pQEPBAAAAAABEQSMjcRiARIEKCMAAAABAwhPkzV3AAAAAAEEFgAUCxNSys0Dz2qht/PI1jiGcbNKXhEA
The timelock for the following PSBTs should be computed to be 1657048460: * Case: Input 1 has PSBT_IN_REQUIRED_TIME_LOCKTIME of 1657048459, Input 2 has PSBT_IN_REQUIRED_HEIGHT_LOCKTIME of 9000 and PSBT_IN_REQUIRED_TIME_LOCKTIME of 1657048460 ** Bytes in Hex:
70736274ff0102040200000001030400000000010401020105010101fb040200000000010e200f758dbfbd4da7c16c8a3309c3c81e1100f561ea646db5b01752c485e1bdde9f010f04010000000111048b8dc46200010e203a1b3b3c837d6489ea7a31d8e6c7dd503c001bef3e06958e7574808d68ca78a5010f04000000000111048c8dc46201120428230000000103084f9335770000000001041600140b1352cacd03cf6aa1b7f3c8d6388671b34a5e1100
** Base64 String:
cHNidP8BAgQCAAAAAQMEAAAAAAEEAQIBBQEBAfsEAgAAAAABDiAPdY2/vU2nwWyKMwnDyB4RAPVh6mRttbAXUsSF4b3enwEPBAEAAAABEQSLjcRiAAEOIDobOzyDfWSJ6nox2ObH3VA8ABvvPgaVjnV0gI1oynilAQ8EAAAAAAERBIyNxGIBEgQoIwAAAAEDCE+TNXcAAAAAAQQWABQLE1LKzQPPaqG388jWOIZxs0peEQA=
* Case: Input 1 has PSBT_IN_REQUIRED_HEIGHT_LOCKTIME of 10000 and PSBT_IN_REQUIRED_TIME_LOCKTIME of 1657048459, Input 2 has PSBT_IN_REQUIRED_TIME_LOCKTIME of 1657048460 ** Bytes in Hex:
70736274ff0102040200000001030400000000010401020105010101fb040200000000010e200f758dbfbd4da7c16c8a3309c3c81e1100f561ea646db5b01752c485e1bdde9f010f04010000000111048b8dc4620112041027000000010e203a1b3b3c837d6489ea7a31d8e6c7dd503c001bef3e06958e7574808d68ca78a5010f04000000000111048c8dc462000103084f9335770000000001041600140b1352cacd03cf6aa1b7f3c8d6388671b34a5e1100
** Base64 String:
cHNidP8BAgQCAAAAAQMEAAAAAAEEAQIBBQEBAfsEAgAAAAABDiAPdY2/vU2nwWyKMwnDyB4RAPVh6mRttbAXUsSF4b3enwEPBAEAAAABEQSLjcRiARIEECcAAAABDiA6Gzs8g31kiep6Mdjmx91QPAAb7z4GlY51dICNaMp4pQEPBAAAAAABEQSMjcRiAAEDCE+TNXcAAAAAAQQWABQLE1LKzQPPaqG388jWOIZxs0peEQA=
** Bytes in Hex:
70736274ff0102040200000001030400000000010401020105010101fb040200000000010e200f758dbfbd4da7c16c8a3309c3c81e1100f561ea646db5b01752c485e1bdde9f010f040100000000010e203a1b3b3c837d6489ea7a31d8e6c7dd503c001bef3e06958e7574808d68ca78a5010f04000000000111048c8dc462000103084f9335770000000001041600140b1352cacd03cf6aa1b7f3c8d6388671b34a5e1100
** Base64 String:
cHNidP8BAgQCAAAAAQMEAAAAAAEEAQIBBQEBAfsEAgAAAAABDiAPdY2/vU2nwWyKMwnDyB4RAPVh6mRttbAXUsSF4b3enwEPBAEAAAAAAQ4gOhs7PIN9ZInqejHY5sfdUDwAG+8+BpWOdXSAjWjKeKUBDwQAAAAAAREEjI3EYgABAwhPkzV3AAAAAAEEFgAUCxNSys0Dz2qht/PI1jiGcbNKXhEA
The timelock for the following PSBTs cannot be computed: * Case: Input 1 has PSBT_IN_REQUIRED_HEIGHT_LOCKTIME of 10000, Input 2 has PSBT_IN_REQUIRED_TIME_LOCKTIME of 1657048460 ** Bytes in Hex:
70736274ff0102040200000001030400000000010401020105010101fb040200000000010e200f758dbfbd4da7c16c8a3309c3c81e1100f561ea646db5b01752c485e1bdde9f010f04010000000112041027000000010e203a1b3b3c837d6489ea7a31d8e6c7dd503c001bef3e06958e7574808d68ca78a5010f04000000000111048c8dc462000103084f9335770000000001041600140b1352cacd03cf6aa1b7f3c8d6388671b34a5e1100
** Base64 String:
cHNidP8BAgQCAAAAAQMEAAAAAAEEAQIBBQEBAfsEAgAAAAABDiAPdY2/vU2nwWyKMwnDyB4RAPVh6mRttbAXUsSF4b3enwEPBAEAAAABEgQQJwAAAAEOIDobOzyDfWSJ6nox2ObH3VA8ABvvPgaVjnV0gI1oynilAQ8EAAAAAAERBIyNxGIAAQMIT5M1dwAAAAABBBYAFAsTUsrNA89qobfzyNY4hnGzSl4RAA==
==Rationale== ==Reference implementation== The reference implementation of the PSBT format is available in [https://github.com/bitcoin/bitcoin/pull/21283 Bitcoin Core PR 21283]. ================================================ FILE: bip-0371.mediawiki ================================================
  BIP: 371
  Layer: Applications
  Title: Taproot Fields for PSBT
  Authors: Ava Chow 
  Status: Deployed
  Type: Specification
  Assigned: 2021-06-21
  License: BSD-2-Clause
==Introduction== ===Abstract=== This document proposes additional fields for BIP 174 PSBTv0 and BIP 370 PSBTv2 that allow for BIP 340/341/342 Taproot data to be included in a PSBT of any version. These will be fields for signatures and scripts that are relevant to the creation of Taproot inputs. ===Copyright=== This BIP is licensed under the 2-clause BSD license. ===Motivation=== BIPs 340, 341, and 342 specify Taproot which provides a wholly new way to create and spend Bitcoin outputs. The existing PSBT fields are unable to support Taproot due to the new signature algorithm and the method by which scripts are embedded inside of a Taproot output. Therefore new fields must be defined to allow PSBTs to carry the information necessary for signing Taproot inputs. ==Specification== The new per-input types are defined as follows: {| ! Name ! ! ! Description ! ! Description ! Versions Requiring Inclusion ! Versions Requiring Exclusion ! Versions Allowing Inclusion |- | Taproot Key Spend Signature | PSBT_IN_TAP_KEY_SIG = 0x13 | None | No key data '''Why is there no key data for PSBT_IN_TAP_KEY_SIG'''The signature in a key path spend corresponds directly with the pubkey provided in the output script. Thus it is not necessary to provide any metadata that attaches the key path spend signature to a particular pubkey. | <64 or 65 byte signature> | The 64 or 65 byte Schnorr signature for key path spending a Taproot output. Finalizers should remove this field after PSBT_IN_FINAL_SCRIPTWITNESS is constructed. | | | 0, 2 |- | Taproot Script Spend Signature | PSBT_IN_TAP_SCRIPT_SIG = 0x14 | | A 32 byte X-only public key involved in a leaf script concatenated with the 32 byte hash of the leaf it is part of. | <64 or 65 byte signature> | The 64 or 65 byte Schnorr signature for this pubkey and leaf combination. Finalizers should remove this field after PSBT_IN_FINAL_SCRIPTWITNESS is constructed. | | | 0, 2 |- | Taproot Leaf Script | PSBT_IN_TAP_LEAF_SCRIPT = 0x15 | | The control block for this leaf as specified in BIP 341. The control block contains the merkle tree path to this leaf. | <8-bit uint leaf version> | The script for this leaf as would be provided in the witness stack followed by the single byte leaf version. Note that the leaves included in this field should be those that the signers of this input are expected to be able to sign for. Finalizers should remove this field after PSBT_IN_FINAL_SCRIPTWITNESS is constructed. | | | 0, 2 |- | Taproot Key BIP 32 Derivation Path | PSBT_IN_TAP_BIP32_DERIVATION = 0x16 | <32 byte xonlypubkey> | A 32 byte X-only public key involved in this input. It may be the output key, the internal key, or a key present in a leaf script. | <32 byte leaf hash>* <4 byte fingerprint> <32-bit little endian uint path element>* | A compact size unsigned integer representing the number of leaf hashes, followed by a list of leaf hashes, followed by the 4 byte master key fingerprint concatenated with the derivation path of the public key. The derivation path is represented as 32-bit little endian unsigned integer indexes concatenated with each other. Public keys are those needed to spend this output. The leaf hashes are of the leaves which involve this public key. The internal key does not have leaf hashes, so can be indicated with a hashes len of 0. Finalizers should remove this field after PSBT_IN_FINAL_SCRIPTWITNESS is constructed. | | | 0, 2 |- | Taproot Internal Key | PSBT_IN_TAP_INTERNAL_KEY = 0x17 | None | No key data | <32 byte xonlypubkey> | The X-only pubkey used as the internal key in this output.'''Why is the internal key provided?'''The internal key is not necessarily the same key as in the Taproot output script. BIP 341 recommends tweaking the key with the hash of itself. It may be necessary for signers to know what the internal key actually is so that they are able to determine whether an input can be signed by it. Finalizers should remove this field after PSBT_IN_FINAL_SCRIPTWITNESS is constructed. | | | 0, 2 |- | Taproot Merkle Root | PSBT_IN_TAP_MERKLE_ROOT = 0x18 | None | No key data | <32-byte hash> | The 32 byte Merkle root hash. Finalizers should remove this field after PSBT_IN_FINAL_SCRIPTWITNESS is constructed. | | | 0, 2 |} The new per-output types are defined as follows: {| ! Name ! ! ! Description ! ! Description ! Versions Requiring Inclusion ! Versions Requiring Exclusion ! Versions Allowing Inclusion |- | Taproot Internal Key | PSBT_OUT_TAP_INTERNAL_KEY = 0x05 | None | No key data | <32 byte xonlypubkey> | The X-only pubkey used as the internal key in this output. | | | 0, 2 |- | Taproot Tree | PSBT_OUT_TAP_TREE = 0x06 | None | No key data | {<8-bit uint depth> <8-bit uint leaf version> }* | One or more tuples representing the depth, leaf version, and script for a leaf in the Taproot tree, allowing the entire tree to be reconstructed. The tuples must be in depth first search order so that the tree is correctly reconstructed. Each tuple is an 8-bit unsigned integer representing the depth in the Taproot tree for this script, an 8-bit unsigned integer representing the leaf version, the length of the script as a compact size unsigned integer, and the script itself. | | | 0, 2 |- | Taproot Key BIP 32 Derivation Path | PSBT_OUT_TAP_BIP32_DERIVATION = 0x07 | <32 byte xonlypubkey> | A 32 byte X-only public key involved in this output. It may be the output key, the internal key, or a key present in a leaf script. | <32 byte leaf hash>* <4 byte fingerprint> <32-bit little endian uint path element>* | A compact size unsigned integer representing the number of leaf hashes, followed by a list of leaf hashes, followed by the 4 byte master key fingerprint concatenated with the derivation path of the public key. The derivation path is represented as 32-bit little endian unsigned integer indexes concatenated with each other. Public keys are those needed to spend this output. The leaf hashes are of the leaves which involve this public key. The internal key does not have leaf hashes, so can be indicated with a hashes len of 0. Finalizers should remove this field after PSBT_IN_FINAL_SCRIPTWITNESS is constructed. | | | 0, 2 |} ===UTXO Types=== BIP 174 recommends using PSBT_IN_NON_WITNESS_UTXO for all inputs because of potential attacks involving an updater lying about the amounts in an output. Because a Taproot signature will commit to all of the amounts and output scripts spent by the inputs of the transaction, such attacks are prevented as any such lying would result in an invalid signature. Thus Taproot inputs can use just PSBT_IN_WITNESS_UTXO. ==Compatibility== These are simply new fields added to the existing PSBT format. Because PSBT is designed to be extensible, old software will ignore the new fields. ==Test Vectors== The following are invalid PSBTs: * Case: PSBT With PSBT_IN_TAP_INTERNAL_KEY key that is too long (incorrectly serialized as compressed DER) ** Bytes in Hex:
70736274ff010071020000000127744ababf3027fe0d6cf23a96eee2efb188ef52301954585883e69b6624b2420000000000ffffffff02787c01000000000016001483a7e34bd99ff03a4962ef8a1a101bb295461ece606b042a010000001600147ac369df1b20e033d6116623957b0ac49f3c52e8000000000001012b00f2052a010000002251205a2c2cf5b52cf31f83ad2e8da63ff03183ecd8f609c7510ae8a48e03910a075701172102fe349064c98d6e2a853fa3c9b12bd8b304a19c195c60efa7ee2393046d3fa232000000
** Base64 String:
cHNidP8BAHECAAAAASd0Srq/MCf+DWzyOpbu4u+xiO9SMBlUWFiD5ptmJLJCAAAAAAD/////Anh8AQAAAAAAFgAUg6fjS9mf8DpJYu+KGhAbspVGHs5gawQqAQAAABYAFHrDad8bIOAz1hFmI5V7CsSfPFLoAAAAAAABASsA8gUqAQAAACJRIFosLPW1LPMfg60ujaY/8DGD7Nj2CcdRCuikjgORCgdXARchAv40kGTJjW4qhT+jybEr2LMEoZwZXGDvp+4jkwRtP6IyAAAA
* Case: PSBT With PSBT_IN_TAP_KEY_SIG signature that is too short ** Bytes in Hex:
<70736274ff010071020000000127744ababf3027fe0d6cf23a96eee2efb188ef52301954585883e69b6624b2420000000000ffffffff02787c01000000000016001483a7e34bd99ff03a4962ef8a1a101bb295461ece606b042a010000001600147ac369df1b20e033d6116623957b0ac49f3c52e8000000000001012b00f2052a010000002251205a2c2cf5b52cf31f83ad2e8da63ff03183ecd8f609c7510ae8a48e03910a075701133f173bb3d36c074afb716fec6307a069a2e450b995f3c82785945ab8df0e24260dcd703b0cbf34de399184a9481ac2b3586db6601f026a77f7e4938481bc3475000000
** Base64 String:
cHNidP8BAHECAAAAASd0Srq/MCf+DWzyOpbu4u+xiO9SMBlUWFiD5ptmJLJCAAAAAAD/////Anh8AQAAAAAAFgAUg6fjS9mf8DpJYu+KGhAbspVGHs5gawQqAQAAABYAFHrDad8bIOAz1hFmI5V7CsSfPFLoAAAAAAABASsA8gUqAQAAACJRIFosLPW1LPMfg60ujaY/8DGD7Nj2CcdRCuikjgORCgdXARM/Fzuz02wHSvtxb+xjB6BpouRQuZXzyCeFlFq43w4kJg3NcDsMvzTeOZGEqUgawrNYbbZgHwJqd/fkk4SBvDR1AAAA
* Case: PSBT With PSBT_IN_TAP_KEY_SIG signature that is too long ** Bytes in Hex:
<70736274ff010071020000000127744ababf3027fe0d6cf23a96eee2efb188ef52301954585883e69b6624b2420000000000ffffffff02787c01000000000016001483a7e34bd99ff03a4962ef8a1a101bb295461ece606b042a010000001600147ac369df1b20e033d6116623957b0ac49f3c52e8000000000001012b00f2052a010000002251205a2c2cf5b52cf31f83ad2e8da63ff03183ecd8f609c7510ae8a48e03910a0757011342173bb3d36c074afb716fec6307a069a2e450b995f3c82785945ab8df0e24260dcd703b0cbf34de399184a9481ac2b3586db6601f026a77f7e4938481bc34751701aa000000
** Base64 String:
cHNidP8BAHECAAAAASd0Srq/MCf+DWzyOpbu4u+xiO9SMBlUWFiD5ptmJLJCAAAAAAD/////Anh8AQAAAAAAFgAUg6fjS9mf8DpJYu+KGhAbspVGHs5gawQqAQAAABYAFHrDad8bIOAz1hFmI5V7CsSfPFLoAAAAAAABASsA8gUqAQAAACJRIFosLPW1LPMfg60ujaY/8DGD7Nj2CcdRCuikjgORCgdXARNCFzuz02wHSvtxb+xjB6BpouRQuZXzyCeFlFq43w4kJg3NcDsMvzTeOZGEqUgawrNYbbZgHwJqd/fkk4SBvDR1FwGqAAAA
* Case: PSBT With PSBT_IN_TAP_BIP32_DERIVATION key that is too long (incorrectly serialized as compressed DER) ** Bytes in Hex:
<70736274ff010071020000000127744ababf3027fe0d6cf23a96eee2efb188ef52301954585883e69b6624b2420000000000ffffffff02787c01000000000016001483a7e34bd99ff03a4962ef8a1a101bb295461ece606b042a010000001600147ac369df1b20e033d6116623957b0ac49f3c52e8000000000001012b00f2052a010000002251205a2c2cf5b52cf31f83ad2e8da63ff03183ecd8f609c7510ae8a48e03910a0757221602fe349064c98d6e2a853fa3c9b12bd8b304a19c195c60efa7ee2393046d3fa2321900772b2da75600008001000080000000800100000000000000000000
** Base64 String:
cHNidP8BAHECAAAAASd0Srq/MCf+DWzyOpbu4u+xiO9SMBlUWFiD5ptmJLJCAAAAAAD/////Anh8AQAAAAAAFgAUg6fjS9mf8DpJYu+KGhAbspVGHs5gawQqAQAAABYAFHrDad8bIOAz1hFmI5V7CsSfPFLoAAAAAAABASsA8gUqAQAAACJRIFosLPW1LPMfg60ujaY/8DGD7Nj2CcdRCuikjgORCgdXIhYC/jSQZMmNbiqFP6PJsSvYswShnBlcYO+n7iOTBG0/ojIZAHcrLadWAACAAQAAgAAAAIABAAAAAAAAAAAAAA==
* Case: PSBT With PSBT_OUT_TAP_INTERNAL_KEY key that is too long (incorrectly serialized as compressed DER) ** Bytes in Hex:
70736274ff01007d020000000127744ababf3027fe0d6cf23a96eee2efb188ef52301954585883e69b6624b2420000000000ffffffff02887b0100000000001600142382871c7e8421a00093f754d91281e675874b9f606b042a010000002251205a2c2cf5b52cf31f83ad2e8da63ff03183ecd8f609c7510ae8a48e03910a0757000000000001012b00f2052a010000002251205a2c2cf5b52cf31f83ad2e8da63ff03183ecd8f609c7510ae8a48e03910a0757000001052102fe349064c98d6e2a853fa3c9b12bd8b304a19c195c60efa7ee2393046d3fa23200
** Base64 String:
cHNidP8BAH0CAAAAASd0Srq/MCf+DWzyOpbu4u+xiO9SMBlUWFiD5ptmJLJCAAAAAAD/////Aoh7AQAAAAAAFgAUI4KHHH6EIaAAk/dU2RKB5nWHS59gawQqAQAAACJRIFosLPW1LPMfg60ujaY/8DGD7Nj2CcdRCuikjgORCgdXAAAAAAABASsA8gUqAQAAACJRIFosLPW1LPMfg60ujaY/8DGD7Nj2CcdRCuikjgORCgdXAAABBSEC/jSQZMmNbiqFP6PJsSvYswShnBlcYO+n7iOTBG0/ojIA
* Case: PSBT With PSBT_OUT_TAP_BIP32_DERIVATION key that is too long (incorrectly serialized as compressed DER) ** Bytes in Hex:
70736274ff01007d020000000127744ababf3027fe0d6cf23a96eee2efb188ef52301954585883e69b6624b2420000000000ffffffff02887b0100000000001600142382871c7e8421a00093f754d91281e675874b9f606b042a010000002251205a2c2cf5b52cf31f83ad2e8da63ff03183ecd8f609c7510ae8a48e03910a0757000000000001012b00f2052a010000002251205a2c2cf5b52cf31f83ad2e8da63ff03183ecd8f609c7510ae8a48e03910a07570000220702fe349064c98d6e2a853fa3c9b12bd8b304a19c195c60efa7ee2393046d3fa2321900772b2da7560000800100008000000080010000000000000000
** Base64 String:
cHNidP8BAH0CAAAAASd0Srq/MCf+DWzyOpbu4u+xiO9SMBlUWFiD5ptmJLJCAAAAAAD/////Aoh7AQAAAAAAFgAUI4KHHH6EIaAAk/dU2RKB5nWHS59gawQqAQAAACJRIFosLPW1LPMfg60ujaY/8DGD7Nj2CcdRCuikjgORCgdXAAAAAAABASsA8gUqAQAAACJRIFosLPW1LPMfg60ujaY/8DGD7Nj2CcdRCuikjgORCgdXAAAiBwL+NJBkyY1uKoU/o8mxK9izBKGcGVxg76fuI5MEbT+iMhkAdystp1YAAIABAACAAAAAgAEAAAAAAAAAAA==
* Case: PSBT With PSBT_IN_TAP_SCRIPT_SIG key that is too long (incorrectly serialized as compressed DER) ** Bytes in Hex:
70736274ff01005e02000000019bd48765230bf9a72e662001f972556e54f0c6f97feb56bcb5600d817f6995260100000000ffffffff0148e6052a01000000225120030da4fce4f7db28c2cb2951631e003713856597fe963882cb500e68112cca63000000000001012b00f2052a01000000225120c2247efbfd92ac47f6f40b8d42d169175a19fa9fa10e4a25d7f35eb4dd85b6924214022cb13ac68248de806aa6a3659cf3c03eb6821d09c8114a4e868febde865bb6d2cd970e15f53fc0c82f950fd560ffa919b76172be017368a89913af074f400b094089756aa3739ccc689ec0fcf3a360be32cc0b59b16e93a1e8bb4605726b2ca7a3ff706c4176649632b2cc68e1f912b8a578e3719ce7710885c7a966f49bcd43cb0000
** Base64 String:
cHNidP8BAF4CAAAAAZvUh2UjC/mnLmYgAflyVW5U8Mb5f+tWvLVgDYF/aZUmAQAAAAD/////AUjmBSoBAAAAIlEgAw2k/OT32yjCyylRYx4ANxOFZZf+ljiCy1AOaBEsymMAAAAAAAEBKwDyBSoBAAAAIlEgwiR++/2SrEf29AuNQtFpF1oZ+p+hDkol1/NetN2FtpJCFAIssTrGgkjegGqmo2Wc88A+toIdCcgRSk6Gj+vehlu20s2XDhX1P8DIL5UP1WD/qRm3YXK+AXNoqJkTrwdPQAsJQIl1aqNznMxonsD886NgvjLMC1mxbpOh6LtGBXJrLKej/3BsQXZkljKyzGjh+RK4pXjjcZzncQiFx6lm9JvNQ8sAAA==
* Case: PSBT With PSBT_IN_TAP_SCRIPT_SIG signature that is too long ** Bytes in Hex:
70736274ff01005e02000000019bd48765230bf9a72e662001f972556e54f0c6f97feb56bcb5600d817f6995260100000000ffffffff0148e6052a01000000225120030da4fce4f7db28c2cb2951631e003713856597fe963882cb500e68112cca63000000000001012b00f2052a01000000225120c2247efbfd92ac47f6f40b8d42d169175a19fa9fa10e4a25d7f35eb4dd85b69241142cb13ac68248de806aa6a3659cf3c03eb6821d09c8114a4e868febde865bb6d2cd970e15f53fc0c82f950fd560ffa919b76172be017368a89913af074f400b094289756aa3739ccc689ec0fcf3a360be32cc0b59b16e93a1e8bb4605726b2ca7a3ff706c4176649632b2cc68e1f912b8a578e3719ce7710885c7a966f49bcd43cb01010000
** Base64 String:
cHNidP8BAF4CAAAAAZvUh2UjC/mnLmYgAflyVW5U8Mb5f+tWvLVgDYF/aZUmAQAAAAD/////AUjmBSoBAAAAIlEgAw2k/OT32yjCyylRYx4ANxOFZZf+ljiCy1AOaBEsymMAAAAAAAEBKwDyBSoBAAAAIlEgwiR++/2SrEf29AuNQtFpF1oZ+p+hDkol1/NetN2FtpJBFCyxOsaCSN6AaqajZZzzwD62gh0JyBFKToaP696GW7bSzZcOFfU/wMgvlQ/VYP+pGbdhcr4Bc2iomROvB09ACwlCiXVqo3OczGiewPzzo2C+MswLWbFuk6Hou0YFcmssp6P/cGxBdmSWMrLMaOH5ErileONxnOdxCIXHqWb0m81DywEBAAA=
* Case: PSBT With PSBT_IN_TAP_SCRIPT_SIG signature that is too short ** Bytes in Hex:
70736274ff01005e02000000019bd48765230bf9a72e662001f972556e54f0c6f97feb56bcb5600d817f6995260100000000ffffffff0148e6052a01000000225120030da4fce4f7db28c2cb2951631e003713856597fe963882cb500e68112cca63000000000001012b00f2052a01000000225120c2247efbfd92ac47f6f40b8d42d169175a19fa9fa10e4a25d7f35eb4dd85b69241142cb13ac68248de806aa6a3659cf3c03eb6821d09c8114a4e868febde865bb6d2cd970e15f53fc0c82f950fd560ffa919b76172be017368a89913af074f400b093f89756aa3739ccc689ec0fcf3a360be32cc0b59b16e93a1e8bb4605726b2ca7a3ff706c4176649632b2cc68e1f912b8a578e3719ce7710885c7a966f49bcd430000
** Base64 String:
cHNidP8BAF4CAAAAAZvUh2UjC/mnLmYgAflyVW5U8Mb5f+tWvLVgDYF/aZUmAQAAAAD/////AUjmBSoBAAAAIlEgAw2k/OT32yjCyylRYx4ANxOFZZf+ljiCy1AOaBEsymMAAAAAAAEBKwDyBSoBAAAAIlEgwiR++/2SrEf29AuNQtFpF1oZ+p+hDkol1/NetN2FtpJBFCyxOsaCSN6AaqajZZzzwD62gh0JyBFKToaP696GW7bSzZcOFfU/wMgvlQ/VYP+pGbdhcr4Bc2iomROvB09ACwk/iXVqo3OczGiewPzzo2C+MswLWbFuk6Hou0YFcmssp6P/cGxBdmSWMrLMaOH5ErileONxnOdxCIXHqWb0m81DAAA=
* Case: PSBT With PSBT_IN_TAP_LEAF_SCRIPT Control block that is too long ** Bytes in Hex:
70736274ff01005e02000000019bd48765230bf9a72e662001f972556e54f0c6f97feb56bcb5600d817f6995260100000000ffffffff0148e6052a01000000225120030da4fce4f7db28c2cb2951631e003713856597fe963882cb500e68112cca63000000000001012b00f2052a01000000225120c2247efbfd92ac47f6f40b8d42d169175a19fa9fa10e4a25d7f35eb4dd85b6926315c150929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac06f7d62059e9497a1a4a267569d9876da60101aff38e3529b9b939ce7f91ae970115f2e490af7cc45c4f78511f36057ce5c5a5c56325a29fb44dfc203f356e1f80023202cb13ac68248de806aa6a3659cf3c03eb6821d09c8114a4e868febde865bb6d2acc00000
** Base64 String:
cHNidP8BAF4CAAAAAZvUh2UjC/mnLmYgAflyVW5U8Mb5f+tWvLVgDYF/aZUmAQAAAAD/////AUjmBSoBAAAAIlEgAw2k/OT32yjCyylRYx4ANxOFZZf+ljiCy1AOaBEsymMAAAAAAAEBKwDyBSoBAAAAIlEgwiR++/2SrEf29AuNQtFpF1oZ+p+hDkol1/NetN2FtpJjFcFQkpt0waBJVLeLS2A16XpeB4paDyjsltVHv+6azoA6wG99YgWelJehpKJnVp2YdtpgEBr/OONSm5uTnOf5GulwEV8uSQr3zEXE94UR82BXzlxaXFYyWin7RN/CA/NW4fgAIyAssTrGgkjegGqmo2Wc88A+toIdCcgRSk6Gj+vehlu20qzAAAA=
* Case: PSBT With PSBT_IN_TAP_LEAF_SCRIPT Control block that is too short ** Bytes in Hex:
70736274ff01005e02000000019bd48765230bf9a72e662001f972556e54f0c6f97feb56bcb5600d817f6995260100000000ffffffff0148e6052a01000000225120030da4fce4f7db28c2cb2951631e003713856597fe963882cb500e68112cca63000000000001012b00f2052a01000000225120c2247efbfd92ac47f6f40b8d42d169175a19fa9fa10e4a25d7f35eb4dd85b6926115c150929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac06f7d62059e9497a1a4a267569d9876da60101aff38e3529b9b939ce7f91ae970115f2e490af7cc45c4f78511f36057ce5c5a5c56325a29fb44dfc203f356e123202cb13ac68248de806aa6a3659cf3c03eb6821d09c8114a4e868febde865bb6d2acc00000
** Base64 String:
cHNidP8BAF4CAAAAAZvUh2UjC/mnLmYgAflyVW5U8Mb5f+tWvLVgDYF/aZUmAQAAAAD/////AUjmBSoBAAAAIlEgAw2k/OT32yjCyylRYx4ANxOFZZf+ljiCy1AOaBEsymMAAAAAAAEBKwDyBSoBAAAAIlEgwiR++/2SrEf29AuNQtFpF1oZ+p+hDkol1/NetN2FtpJhFcFQkpt0waBJVLeLS2A16XpeB4paDyjsltVHv+6azoA6wG99YgWelJehpKJnVp2YdtpgEBr/OONSm5uTnOf5GulwEV8uSQr3zEXE94UR82BXzlxaXFYyWin7RN/CA/NW4SMgLLE6xoJI3oBqpqNlnPPAPraCHQnIEUpOho/r3oZbttKswAAA
The following are valid PSBTs: * Case: PSBT with one P2TR key only input with internal key and its derivation path ** Bytes in Hex:
70736274ff010052020000000127744ababf3027fe0d6cf23a96eee2efb188ef52301954585883e69b6624b2420000000000ffffffff0148e6052a01000000160014768e1eeb4cf420866033f80aceff0f9720744969000000000001012b00f2052a010000002251205a2c2cf5b52cf31f83ad2e8da63ff03183ecd8f609c7510ae8a48e03910a07572116fe349064c98d6e2a853fa3c9b12bd8b304a19c195c60efa7ee2393046d3fa2321900772b2da75600008001000080000000800100000000000000011720fe349064c98d6e2a853fa3c9b12bd8b304a19c195c60efa7ee2393046d3fa232002202036b772a6db74d8753c98a827958de6c78ab3312109f37d3e0304484242ece73d818772b2da7540000800100008000000080000000000000000000
** Base64 String:
cHNidP8BAFICAAAAASd0Srq/MCf+DWzyOpbu4u+xiO9SMBlUWFiD5ptmJLJCAAAAAAD/////AUjmBSoBAAAAFgAUdo4e60z0IIZgM/gKzv8PlyB0SWkAAAAAAAEBKwDyBSoBAAAAIlEgWiws9bUs8x+DrS6Npj/wMYPs2PYJx1EK6KSOA5EKB1chFv40kGTJjW4qhT+jybEr2LMEoZwZXGDvp+4jkwRtP6IyGQB3Ky2nVgAAgAEAAIAAAACAAQAAAAAAAAABFyD+NJBkyY1uKoU/o8mxK9izBKGcGVxg76fuI5MEbT+iMgAiAgNrdyptt02HU8mKgnlY3mx4qzMSEJ830+AwRIQkLs5z2Bh3Ky2nVAAAgAEAAIAAAACAAAAAAAAAAAAA
* Case: PSBT with one P2TR key only input with internal key, its derivation path, and signature ** Bytes in Hex:
70736274ff010052020000000127744ababf3027fe0d6cf23a96eee2efb188ef52301954585883e69b6624b2420000000000ffffffff0148e6052a01000000160014768e1eeb4cf420866033f80aceff0f9720744969000000000001012b00f2052a010000002251205a2c2cf5b52cf31f83ad2e8da63ff03183ecd8f609c7510ae8a48e03910a0757011340bb53ec917bad9d906af1ba87181c48b86ace5aae2b53605a725ca74625631476fc6f5baedaf4f2ee0f477f36f58f3970d5b8273b7e497b97af2e3f125c97af342116fe349064c98d6e2a853fa3c9b12bd8b304a19c195c60efa7ee2393046d3fa2321900772b2da75600008001000080000000800100000000000000011720fe349064c98d6e2a853fa3c9b12bd8b304a19c195c60efa7ee2393046d3fa232002202036b772a6db74d8753c98a827958de6c78ab3312109f37d3e0304484242ece73d818772b2da7540000800100008000000080000000000000000000
** Base64 String:
cHNidP8BAFICAAAAASd0Srq/MCf+DWzyOpbu4u+xiO9SMBlUWFiD5ptmJLJCAAAAAAD/////AUjmBSoBAAAAFgAUdo4e60z0IIZgM/gKzv8PlyB0SWkAAAAAAAEBKwDyBSoBAAAAIlEgWiws9bUs8x+DrS6Npj/wMYPs2PYJx1EK6KSOA5EKB1cBE0C7U+yRe62dkGrxuocYHEi4as5aritTYFpyXKdGJWMUdvxvW67a9PLuD0d/NvWPOXDVuCc7fkl7l68uPxJcl680IRb+NJBkyY1uKoU/o8mxK9izBKGcGVxg76fuI5MEbT+iMhkAdystp1YAAIABAACAAAAAgAEAAAAAAAAAARcg/jSQZMmNbiqFP6PJsSvYswShnBlcYO+n7iOTBG0/ojIAIgIDa3cqbbdNh1PJioJ5WN5seKszEhCfN9PgMESEJC7Oc9gYdystp1QAAIABAACAAAAAgAAAAAAAAAAAAA==
* Case: PSBT with one P2TR key only output with internal key and its derivation path ** Bytes in Hex:
70736274ff01005e020000000127744ababf3027fe0d6cf23a96eee2efb188ef52301954585883e69b6624b2420000000000ffffffff0148e6052a0100000022512083698e458c6664e1595d75da2597de1e22ee97d798e706c4c0a4b5a9823cd743000000000001012b00f2052a010000002251205a2c2cf5b52cf31f83ad2e8da63ff03183ecd8f609c7510ae8a48e03910a07572116fe349064c98d6e2a853fa3c9b12bd8b304a19c195c60efa7ee2393046d3fa2321900772b2da75600008001000080000000800100000000000000011720fe349064c98d6e2a853fa3c9b12bd8b304a19c195c60efa7ee2393046d3fa232000105201124da7aec92ccd06c954562647f437b138b95721a84be2bf2276bbddab3e67121071124da7aec92ccd06c954562647f437b138b95721a84be2bf2276bbddab3e6711900772b2da7560000800100008000000080000000000500000000
** Base64 String:
cHNidP8BAF4CAAAAASd0Srq/MCf+DWzyOpbu4u+xiO9SMBlUWFiD5ptmJLJCAAAAAAD/////AUjmBSoBAAAAIlEgg2mORYxmZOFZXXXaJZfeHiLul9eY5wbEwKS1qYI810MAAAAAAAEBKwDyBSoBAAAAIlEgWiws9bUs8x+DrS6Npj/wMYPs2PYJx1EK6KSOA5EKB1chFv40kGTJjW4qhT+jybEr2LMEoZwZXGDvp+4jkwRtP6IyGQB3Ky2nVgAAgAEAAIAAAACAAQAAAAAAAAABFyD+NJBkyY1uKoU/o8mxK9izBKGcGVxg76fuI5MEbT+iMgABBSARJNp67JLM0GyVRWJkf0N7E4uVchqEvivyJ2u92rPmcSEHESTaeuySzNBslUViZH9DexOLlXIahL4r8idrvdqz5nEZAHcrLadWAACAAQAAgAAAAIAAAAAABQAAAAA=
* Case: PSBT with one P2TR script path only input with dummy internal key, scripts, derivation paths for keys in the scripts, and merkle root ** Bytes in Hex:
70736274ff01005e02000000019bd48765230bf9a72e662001f972556e54f0c6f97feb56bcb5600d817f6995260100000000ffffffff0148e6052a0100000022512083698e458c6664e1595d75da2597de1e22ee97d798e706c4c0a4b5a9823cd743000000000001012b00f2052a01000000225120c2247efbfd92ac47f6f40b8d42d169175a19fa9fa10e4a25d7f35eb4dd85b6926215c150929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac06f7d62059e9497a1a4a267569d9876da60101aff38e3529b9b939ce7f91ae970115f2e490af7cc45c4f78511f36057ce5c5a5c56325a29fb44dfc203f356e1f823202cb13ac68248de806aa6a3659cf3c03eb6821d09c8114a4e868febde865bb6d2acc04215c150929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac097c6e6fea5ff714ff5724499990810e406e98aa10f5bf7e5f6784bc1d0a9a6ce23204320b0bf16f011b53ea7be615924aa7f27e5d29ad20ea1155d848676c3bad1b2acc06215c150929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac0cd970e15f53fc0c82f950fd560ffa919b76172be017368a89913af074f400b09115f2e490af7cc45c4f78511f36057ce5c5a5c56325a29fb44dfc203f356e1f82320fa0f7a3cef3b1d0c0a6ce7d26e17ada0b2e5c92d19efad48b41859cb8a451ca9acc021162cb13ac68248de806aa6a3659cf3c03eb6821d09c8114a4e868febde865bb6d23901cd970e15f53fc0c82f950fd560ffa919b76172be017368a89913af074f400b09772b2da7560000800100008002000080000000000000000021164320b0bf16f011b53ea7be615924aa7f27e5d29ad20ea1155d848676c3bad1b23901115f2e490af7cc45c4f78511f36057ce5c5a5c56325a29fb44dfc203f356e1f8772b2da75600008001000080010000800000000000000000211650929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac005007c461e5d2116fa0f7a3cef3b1d0c0a6ce7d26e17ada0b2e5c92d19efad48b41859cb8a451ca939016f7d62059e9497a1a4a267569d9876da60101aff38e3529b9b939ce7f91ae970772b2da7560000800100008003000080000000000000000001172050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac0011820f0362e2f75a6f420a5bde3eb221d96ae6720cf25f81890c95b1d775acb515e65000105201124da7aec92ccd06c954562647f437b138b95721a84be2bf2276bbddab3e67121071124da7aec92ccd06c954562647f437b138b95721a84be2bf2276bbddab3e6711900772b2da7560000800100008000000080000000000500000000
** Base64 String:
cHNidP8BAF4CAAAAAZvUh2UjC/mnLmYgAflyVW5U8Mb5f+tWvLVgDYF/aZUmAQAAAAD/////AUjmBSoBAAAAIlEgg2mORYxmZOFZXXXaJZfeHiLul9eY5wbEwKS1qYI810MAAAAAAAEBKwDyBSoBAAAAIlEgwiR++/2SrEf29AuNQtFpF1oZ+p+hDkol1/NetN2FtpJiFcFQkpt0waBJVLeLS2A16XpeB4paDyjsltVHv+6azoA6wG99YgWelJehpKJnVp2YdtpgEBr/OONSm5uTnOf5GulwEV8uSQr3zEXE94UR82BXzlxaXFYyWin7RN/CA/NW4fgjICyxOsaCSN6AaqajZZzzwD62gh0JyBFKToaP696GW7bSrMBCFcFQkpt0waBJVLeLS2A16XpeB4paDyjsltVHv+6azoA6wJfG5v6l/3FP9XJEmZkIEOQG6YqhD1v35fZ4S8HQqabOIyBDILC/FvARtT6nvmFZJKp/J+XSmtIOoRVdhIZ2w7rRsqzAYhXBUJKbdMGgSVS3i0tgNel6XgeKWg8o7JbVR7/ums6AOsDNlw4V9T/AyC+VD9Vg/6kZt2FyvgFzaKiZE68HT0ALCRFfLkkK98xFxPeFEfNgV85cWlxWMlop+0TfwgPzVuH4IyD6D3o87zsdDAps59JuF62gsuXJLRnvrUi0GFnLikUcqazAIRYssTrGgkjegGqmo2Wc88A+toIdCcgRSk6Gj+vehlu20jkBzZcOFfU/wMgvlQ/VYP+pGbdhcr4Bc2iomROvB09ACwl3Ky2nVgAAgAEAAIACAACAAAAAAAAAAAAhFkMgsL8W8BG1Pqe+YVkkqn8n5dKa0g6hFV2EhnbDutGyOQERXy5JCvfMRcT3hRHzYFfOXFpcVjJaKftE38ID81bh+HcrLadWAACAAQAAgAEAAIAAAAAAAAAAACEWUJKbdMGgSVS3i0tgNel6XgeKWg8o7JbVR7/ums6AOsAFAHxGHl0hFvoPejzvOx0MCmzn0m4XraCy5cktGe+tSLQYWcuKRRypOQFvfWIFnpSXoaSiZ1admHbaYBAa/zjjUpubk5zn+RrpcHcrLadWAACAAQAAgAMAAIAAAAAAAAAAAAEXIFCSm3TBoElUt4tLYDXpel4HiloPKOyW1Ue/7prOgDrAARgg8DYuL3Wm9CClvePrIh2WrmcgzyX4GJDJWx13WstRXmUAAQUgESTaeuySzNBslUViZH9DexOLlXIahL4r8idrvdqz5nEhBxEk2nrskszQbJVFYmR/Q3sTi5VyGoS+K/Ina73as+ZxGQB3Ky2nVgAAgAEAAIAAAACAAAAAAAUAAAAA
* Case: PSBT with one P2TR script path only output with dummy internal key, taproot tree, and script key derivation paths ** Bytes in Hex:
70736274ff01005e020000000127744ababf3027fe0d6cf23a96eee2efb188ef52301954585883e69b6624b2420000000000ffffffff0148e6052a010000002251200a8cbdc86de1ce1c0f9caeb22d6df7ced3683fe423e05d1e402a879341d6f6f5000000000001012b00f2052a010000002251205a2c2cf5b52cf31f83ad2e8da63ff03183ecd8f609c7510ae8a48e03910a07572116fe349064c98d6e2a853fa3c9b12bd8b304a19c195c60efa7ee2393046d3fa2321900772b2da75600008001000080000000800100000000000000011720fe349064c98d6e2a853fa3c9b12bd8b304a19c195c60efa7ee2393046d3fa2320001052050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac001066f02c02220736e572900fe1252589a2143c8f3c79f71a0412d2353af755e9701c782694a02ac02c02220631c5f3b5832b8fbdebfb19704ceeb323c21f40f7a24f43d68ef0cc26b125969ac01c0222044faa49a0338de488c8dfffecdfb6f329f380bd566ef20c8df6d813eab1c4273ac210744faa49a0338de488c8dfffecdfb6f329f380bd566ef20c8df6d813eab1c42733901f06b798b92a10ed9a9d0bbfd3af173a53b1617da3a4159ca008216cd856b2e0e772b2da75600008001000080010000800000000003000000210750929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac005007c461e5d2107631c5f3b5832b8fbdebfb19704ceeb323c21f40f7a24f43d68ef0cc26b125969390118ace409889785e0ea70ceebb8e1ca892a7a78eaede0f2e296cf435961a8f4ca772b2da756000080010000800200008000000000030000002107736e572900fe1252589a2143c8f3c79f71a0412d2353af755e9701c782694a02390129a5b4915090162d759afd3fe0f93fa3326056d0b4088cb933cae7826cb8d82c772b2da7560000800100008003000080000000000300000000
** Base64 String:
cHNidP8BAF4CAAAAASd0Srq/MCf+DWzyOpbu4u+xiO9SMBlUWFiD5ptmJLJCAAAAAAD/////AUjmBSoBAAAAIlEgCoy9yG3hzhwPnK6yLW33ztNoP+Qj4F0eQCqHk0HW9vUAAAAAAAEBKwDyBSoBAAAAIlEgWiws9bUs8x+DrS6Npj/wMYPs2PYJx1EK6KSOA5EKB1chFv40kGTJjW4qhT+jybEr2LMEoZwZXGDvp+4jkwRtP6IyGQB3Ky2nVgAAgAEAAIAAAACAAQAAAAAAAAABFyD+NJBkyY1uKoU/o8mxK9izBKGcGVxg76fuI5MEbT+iMgABBSBQkpt0waBJVLeLS2A16XpeB4paDyjsltVHv+6azoA6wAEGbwLAIiBzblcpAP4SUliaIUPI88efcaBBLSNTr3VelwHHgmlKAqwCwCIgYxxfO1gyuPvev7GXBM7rMjwh9A96JPQ9aO8MwmsSWWmsAcAiIET6pJoDON5IjI3//s37bzKfOAvVZu8gyN9tgT6rHEJzrCEHRPqkmgM43kiMjf/+zftvMp84C9Vm7yDI322BPqscQnM5AfBreYuSoQ7ZqdC7/Trxc6U7FhfaOkFZygCCFs2Fay4Odystp1YAAIABAACAAQAAgAAAAAADAAAAIQdQkpt0waBJVLeLS2A16XpeB4paDyjsltVHv+6azoA6wAUAfEYeXSEHYxxfO1gyuPvev7GXBM7rMjwh9A96JPQ9aO8MwmsSWWk5ARis5AmIl4Xg6nDO67jhyokqenjq7eDy4pbPQ1lhqPTKdystp1YAAIABAACAAgAAgAAAAAADAAAAIQdzblcpAP4SUliaIUPI88efcaBBLSNTr3VelwHHgmlKAjkBKaW0kVCQFi11mv0/4Pk/ozJgVtC0CIy5M8rngmy42Cx3Ky2nVgAAgAEAAIADAACAAAAAAAMAAAAA
* Case: PSBT with one P2TR script path only input with dummy internal key, scripts, script key derivation paths, merkle root, and script path signatures ** Bytes in Hex:
70736274ff01005e02000000019bd48765230bf9a72e662001f972556e54f0c6f97feb56bcb5600d817f6995260100000000ffffffff0148e6052a0100000022512083698e458c6664e1595d75da2597de1e22ee97d798e706c4c0a4b5a9823cd743000000000001012b00f2052a01000000225120c2247efbfd92ac47f6f40b8d42d169175a19fa9fa10e4a25d7f35eb4dd85b69241142cb13ac68248de806aa6a3659cf3c03eb6821d09c8114a4e868febde865bb6d2cd970e15f53fc0c82f950fd560ffa919b76172be017368a89913af074f400b0940bf818d9757d6ffeb538ba057fb4c1fc4e0f5ef186e765beb564791e02af5fd3d5e2551d4e34e33d86f276b82c99c79aed3f0395a081efcd2cc2c65dd7e693d7941144320b0bf16f011b53ea7be615924aa7f27e5d29ad20ea1155d848676c3bad1b2115f2e490af7cc45c4f78511f36057ce5c5a5c56325a29fb44dfc203f356e1f840e1f1ab6fabfa26b236f21833719dc1d428ab768d80f91f9988d8abef47bfb863bb1f2a529f768c15f00ce34ec283cdc07e88f8428be28f6ef64043c32911811a4114fa0f7a3cef3b1d0c0a6ce7d26e17ada0b2e5c92d19efad48b41859cb8a451ca96f7d62059e9497a1a4a267569d9876da60101aff38e3529b9b939ce7f91ae97040ec1f0379206461c83342285423326708ab031f0da4a253ee45aafa5b8c92034d8b605490f8cd13e00f989989b97e215faa36f12dee3693d2daccf3781c1757f66215c150929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac06f7d62059e9497a1a4a267569d9876da60101aff38e3529b9b939ce7f91ae970115f2e490af7cc45c4f78511f36057ce5c5a5c56325a29fb44dfc203f356e1f823202cb13ac68248de806aa6a3659cf3c03eb6821d09c8114a4e868febde865bb6d2acc04215c150929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac097c6e6fea5ff714ff5724499990810e406e98aa10f5bf7e5f6784bc1d0a9a6ce23204320b0bf16f011b53ea7be615924aa7f27e5d29ad20ea1155d848676c3bad1b2acc06215c150929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac0cd970e15f53fc0c82f950fd560ffa919b76172be017368a89913af074f400b09115f2e490af7cc45c4f78511f36057ce5c5a5c56325a29fb44dfc203f356e1f82320fa0f7a3cef3b1d0c0a6ce7d26e17ada0b2e5c92d19efad48b41859cb8a451ca9acc021162cb13ac68248de806aa6a3659cf3c03eb6821d09c8114a4e868febde865bb6d23901cd970e15f53fc0c82f950fd560ffa919b76172be017368a89913af074f400b09772b2da7560000800100008002000080000000000000000021164320b0bf16f011b53ea7be615924aa7f27e5d29ad20ea1155d848676c3bad1b23901115f2e490af7cc45c4f78511f36057ce5c5a5c56325a29fb44dfc203f356e1f8772b2da75600008001000080010000800000000000000000211650929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac005007c461e5d2116fa0f7a3cef3b1d0c0a6ce7d26e17ada0b2e5c92d19efad48b41859cb8a451ca939016f7d62059e9497a1a4a267569d9876da60101aff38e3529b9b939ce7f91ae970772b2da7560000800100008003000080000000000000000001172050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac0011820f0362e2f75a6f420a5bde3eb221d96ae6720cf25f81890c95b1d775acb515e65000105201124da7aec92ccd06c954562647f437b138b95721a84be2bf2276bbddab3e67121071124da7aec92ccd06c954562647f437b138b95721a84be2bf2276bbddab3e6711900772b2da7560000800100008000000080000000000500000000
** Base64 String:
cHNidP8BAF4CAAAAAZvUh2UjC/mnLmYgAflyVW5U8Mb5f+tWvLVgDYF/aZUmAQAAAAD/////AUjmBSoBAAAAIlEgg2mORYxmZOFZXXXaJZfeHiLul9eY5wbEwKS1qYI810MAAAAAAAEBKwDyBSoBAAAAIlEgwiR++/2SrEf29AuNQtFpF1oZ+p+hDkol1/NetN2FtpJBFCyxOsaCSN6AaqajZZzzwD62gh0JyBFKToaP696GW7bSzZcOFfU/wMgvlQ/VYP+pGbdhcr4Bc2iomROvB09ACwlAv4GNl1fW/+tTi6BX+0wfxOD17xhudlvrVkeR4Cr1/T1eJVHU404z2G8na4LJnHmu0/A5Wgge/NLMLGXdfmk9eUEUQyCwvxbwEbU+p75hWSSqfyfl0prSDqEVXYSGdsO60bIRXy5JCvfMRcT3hRHzYFfOXFpcVjJaKftE38ID81bh+EDh8atvq/omsjbyGDNxncHUKKt2jYD5H5mI2KvvR7+4Y7sfKlKfdowV8AzjTsKDzcB+iPhCi+KPbvZAQ8MpEYEaQRT6D3o87zsdDAps59JuF62gsuXJLRnvrUi0GFnLikUcqW99YgWelJehpKJnVp2YdtpgEBr/OONSm5uTnOf5GulwQOwfA3kgZGHIM0IoVCMyZwirAx8NpKJT7kWq+luMkgNNi2BUkPjNE+APmJmJuX4hX6o28S3uNpPS2szzeBwXV/ZiFcFQkpt0waBJVLeLS2A16XpeB4paDyjsltVHv+6azoA6wG99YgWelJehpKJnVp2YdtpgEBr/OONSm5uTnOf5GulwEV8uSQr3zEXE94UR82BXzlxaXFYyWin7RN/CA/NW4fgjICyxOsaCSN6AaqajZZzzwD62gh0JyBFKToaP696GW7bSrMBCFcFQkpt0waBJVLeLS2A16XpeB4paDyjsltVHv+6azoA6wJfG5v6l/3FP9XJEmZkIEOQG6YqhD1v35fZ4S8HQqabOIyBDILC/FvARtT6nvmFZJKp/J+XSmtIOoRVdhIZ2w7rRsqzAYhXBUJKbdMGgSVS3i0tgNel6XgeKWg8o7JbVR7/ums6AOsDNlw4V9T/AyC+VD9Vg/6kZt2FyvgFzaKiZE68HT0ALCRFfLkkK98xFxPeFEfNgV85cWlxWMlop+0TfwgPzVuH4IyD6D3o87zsdDAps59JuF62gsuXJLRnvrUi0GFnLikUcqazAIRYssTrGgkjegGqmo2Wc88A+toIdCcgRSk6Gj+vehlu20jkBzZcOFfU/wMgvlQ/VYP+pGbdhcr4Bc2iomROvB09ACwl3Ky2nVgAAgAEAAIACAACAAAAAAAAAAAAhFkMgsL8W8BG1Pqe+YVkkqn8n5dKa0g6hFV2EhnbDutGyOQERXy5JCvfMRcT3hRHzYFfOXFpcVjJaKftE38ID81bh+HcrLadWAACAAQAAgAEAAIAAAAAAAAAAACEWUJKbdMGgSVS3i0tgNel6XgeKWg8o7JbVR7/ums6AOsAFAHxGHl0hFvoPejzvOx0MCmzn0m4XraCy5cktGe+tSLQYWcuKRRypOQFvfWIFnpSXoaSiZ1admHbaYBAa/zjjUpubk5zn+RrpcHcrLadWAACAAQAAgAMAAIAAAAAAAAAAAAEXIFCSm3TBoElUt4tLYDXpel4HiloPKOyW1Ue/7prOgDrAARgg8DYuL3Wm9CClvePrIh2WrmcgzyX4GJDJWx13WstRXmUAAQUgESTaeuySzNBslUViZH9DexOLlXIahL4r8idrvdqz5nEhBxEk2nrskszQbJVFYmR/Q3sTi5VyGoS+K/Ina73as+ZxGQB3Ky2nVgAAgAEAAIAAAACAAAAAAAUAAAAA
==Rationale== ==Reference implementation== The reference implementation of the PSBT format is available at https://github.com/achow101/bitcoin/tree/taproot-psbt. ==Acknowledgements== TBD ================================================ FILE: bip-0372.mediawiki ================================================
  BIP: 372
  Layer: Applications
  Title: Pay-to-contract tweak fields for PSBT
  Authors: Maxim Orlovsky 
  Status: Draft
  Type: Specification
  Assigned: 2022-01-16
  License: BSD-2-Clause
  Requires: BIP-174
==Introduction== ===Abstract=== This document proposes additional fields for BIP 174 PSBTv0 and BIP 370 PSBTv2 that allow for pay-to-contract (P2C) key tweaking data to be included in a PSBT of any version. These will represent extra-transaction information required for the signer to produce valid signatures spending previous outputs. ===Copyright=== This BIP is licensed under the 2-clause BSD license. ===Background=== Key tweaking is a procedure for creating a cryptographic commitment to a message using elliptic curve properties. The procedure uses the discrete log problem (DLP) to commit to an extra-transaction message. This is done by adding to a public key (for which the output owner knows the corresponding private key) a hash of the message multiplied by the generator point G of the elliptic curve. This produces a tweaked public key containing the commitment. Later, in order to spend an output containing the P2C commitment, the same commitment should be added to the corresponding private key. This type of commitment was originally proposed as a part of the pay to contract concept by Ilja Gerhardt and Timo Hanke in [1] and later used by Eternity Wall [2] for the same purpose. Since that time, multiple different protocols for P2C have been developed, including OpenTimeStamps [3], Elements sidechain P2C tweaks [4] and LNPBP-1 [5], used for constructing Peter Todd's single-use-seals [6] in client-side-validation protocols like RGB. ===Motivation=== P2C outputs can be detected onchain and spent only if the output owner not only knows the corresponding original private key, but also is aware of a P2C tweak applied to the public key. In order to produce a valid signature, the same tweak value must be added (modulo group order) to the original private key by a signer device. This represents a challenge for external signers, which may not have any information about such commitment. This proposal addresses this issue by adding relevant fields to the PSBT input information. The proposal abstracts details of specific P2C protocols and provides a universal method for spending previous outputs containing P2C tweaks, applied to the public key contained within any standard form of the scriptPubkey, including bare scripts and P2PK, P2PKH, P2SH, witness v0 P2WPKH, P2WSH, nested witness v0 P2WPKH-P2SH, P2WSH-P2SH and witness v1 P2TR outputs. ==Design== P2C-tweaked public keys are already exposed in the PSBT_IN_REDEEM_SCRIPT, PSBT_IN_WITNESS_SCRIPT, PSBT_IN_TAP_INTERNAL_KEY and PSBT_IN_TAP_LEAF_SCRIPT fields; the only information signer is needed to recognize which keys it should sign with is from which of the original keys they were generated. This is achieved by introducing a new `PSBT_IN_P2C_TWEAK` field, which has the original key as a field key and the tweak as a field value. The signer will recognize the keys which are available to it, apply the tweak to them and see in which scripts it was used -- and use this information to apply tweaks for the corresponding private keys and produce valid signatures. ==Specification== The new per-input type is defined as follows: {| ! Name ! ! ! Description ! ! Description ! Versions Requiring Inclusion ! Versions Requiring Exclusion ! Versions Allowing Inclusion |- | P2C Key Tweak | PSBT_IN_P2C_TWEAK = 0x19 | | 33 bytes of compact public key serialization specifying to which keys the P2C tweak may be applied (i.e. this MUST be a value of a public key before the tweak is applied). BIP-340 keys are serialized by appending `0x02` byte.'''Why compressed public keys are not distinguished from BIP-340 public keys''' We follow the logic of BIP32 key derivation, which does not distinguish them. The type of the key is defined by the input type, and adding additional PSBT field types will just create the need for handling errors when the input type does not match the provided key type. | | The 32 byte value which MUST be added to a private key to produce a correct ECDSA and/or Schnorr signature ("key tweak"). Signers SHOULD remove this field after PSBT_IN_PARTIAL_SIG is constructed. | | | 0, 2 | BIP-P2C |} ==Security considerations== The scope of this proposal is deliberately kept narrow; it addresses only spending of transaction outputs containing P2C tweaks - and does not address construction of new P2C commitments or transactions containing them in their outputs.'''Why only spending of P2C tweaked outputs is covered''' P2C tweaks commit to external data, some of which may represent certain values (like in some sidechains, single-use-seal applications like RGB, etc). Creation of such outputs may allow hardware devices to understand the structure of such extra-transaction data, which may be in different formats and constantly evolve. Thus, this should be addressed with separate standards (or be vendor-based). The current proposal only touches the question of spending an output that contained a previously created P2C commitment, which does not create a new commitment and does not provide that kind of risk of extra-blockchain value losses. ==Rationale== ==Compatibility== The proposal is compatible with the existing consensus rules and does not require any modification to them. The proposed P2C PSBT fields provide sufficient information for creating valid signatures for spending the following output types containing tweaked public keys: - bare scripts, - P2PK, - P2PKH, - P2SH, - witness v0 P2WPKH and P2WSH, - nested witness v0 P2WPKH-P2SH and P2WSH-P2SH Post-0 witness versions, including taproot outputs and future witness versions, may not be supported or covered by this BIP and may require the addition of new fields to the PSBT inputs. ==Reference implementation== WIP ==Acknowledgements== The author is grateful to Andrew Poelstra, who provided an initial set of ideas and information with his previous work on the topic, on which this standard was designed. ==Test vectors== TBD ==References== [1] Ilja Gerhardt, Timo Hanke. ''Homomorphic Payment Addresses and the Pay-to-Contract Protocol.'' arXiv:1212.3257 [cs.CR]. [https://arxiv.org/pdf/1212.3257.pdf arxiv.org/pdf/1212.3257.pdf] [2] Eternity Wall. ''Sign-to-contract.'' [https://blog.eternitywall.com/2018/04/13/sign-to-contract/ blog.eternitywall.com] [3] Peter Todd. ''OpenTimestamps: Scalable, Trust-Minimized, Distributed Timestamping with Bitcoin.'' [https://petertodd.org/2016/opentimestamps-announcement petertodd.org] [4] Adam Back, Matt Corallo, Luke Dashjr, et al. ''Enabling Blockchain Innovations with Pegged Sidechains (commit5620e43). Appendix A.'' [https://blockstream.com/sidechains.pdf blockstream.com/sidechains.pdf] [5] Maxim Orlovsky, Rene Pickhardt, Federico Tenga, et al. ''Key tweaking: collision-resistant elliptic curve-based commitments. LNPBP-1 Standard.'' [https://github.com/LNP-BP/LNPBPs/blob/master/lnpbp-0001.md LNPBP-1 on GitHub] [6] Peter Todd. ''Single-use-seals. LNPBP-8 Standard.'' [https://github.com/LNP-BP/LNPBPs/blob/master/lnpbp-0008.md LNPBP-8 on GitHub] ================================================ FILE: bip-0373.mediawiki ================================================
  BIP: 373
  Layer: Applications
  Title: MuSig2 PSBT Fields
  Authors: Ava Chow 
  Status: Complete
  Type: Specification
  Assigned: 2024-06-04
  License: CC0-1.0
  Requires: 32, 174, 327, 328, 370
==Introduction== ===Abstract=== This document proposes additional fields for [[bip-0174.mediawiki|BIP 174]] PSBTv0 and [[bip-0370.mediawiki|BIP 370]] PSBTv2 that allow for [[bip-0327.mediawiki|BIP 327]] MuSig2 Multi-Signature data to be included in a PSBT of any version. These will be fields for the participants' keys, the public nonces, and the partial signatures produced with MuSig2. ===Copyright=== This BIP is licensed under the Creative Commons CC0 1.0 Universal license. ===Motivation=== [[bip-0327.mediawiki|BIP 327]] specifies a way to create [[bip-0340.mediawiki|BIP 340]] compatible public keys and signatures using the MuSig2 Multi-Signature scheme. The existing PSBT fields are unable to support MuSig2 as it introduces new concepts and additional rounds of communication. Therefore new fields must be defined to allow PSBTs to carry the information necessary to produce a valid signature with MuSig2. ==Specification== The new per-input types are defined as follows: {| ! Name ! ! ! ! Versions Requiring Inclusion ! Versions Requiring Exclusion ! Versions Allowing Inclusion |- | rowspan="2"|MuSig2 Participant Public Keys | rowspan="2"|PSBT_IN_MUSIG2_PARTICIPANT_PUBKEYS = 0x1a | <33 byte aggregate pubkey (compressed)> | <33 byte participant pubkey (compressed)>* | rowspan="2"| | rowspan="2"| | rowspan="2"| 0, 2 |- | The MuSig2 aggregate public key (compressed) '''Why the compressed aggregate public key instead of x-only?''' [[bip-0032.mediawiki|BIP 32]] public keys can be derived from a [[bip-0327.mediawiki|BIP 327]] MuSig2 aggregate public key (see: [[bip-0328.mediawiki|BIP 328]]). But since BIP 32 requires public keys to include their evenness byte, BIP 327 MuSig2 aggregate public keys must include their evenness byte as well. Furthermore, PSBT_IN_TAP_BIP32_DERIVATION fields include fingerprints to identify master keys, and these fingerprints require the y-coordinate of the public key, so x-only serialization can't be used. By including the aggregate key as a full public key, signers that are unaware of the MuSig2 outside of the PSBT will still be able to identify which keys are derived from the aggregate key by computing and then comparing the fingerprints. This is necessary for the signer to apply the correct tweaks to their partial signature. from the KeyAgg algorithm. This key may or may not appear (as x-only) in the Taproot output key, the internal key, or in a script. It may instead be a parent public key from which the Taproot output key, internal key, or keys in a script were derived. | A list of the compressed public keys of the participants in the MuSig2 aggregate key in the order required for aggregation. If sorting was done, then the keys must be in the sorted order. |- | rowspan="2"|MuSig2 Public Nonce | rowspan="2"|PSBT_IN_MUSIG2_PUB_NONCE = 0x1b | <33 byte participant pubkey (compressed)> <33 byte aggregate pubkey (compressed)> <32 byte hash or omitted> | <66 byte public nonce> | rowspan="2"| | rowspan="2"| | rowspan="2"| 0, 2 |- | The compressed public key of the participant providing this nonce, followed by the compressed aggregate public key the participant is providing the nonce for, followed by the [[bip-0341.mediawiki|BIP 341]] tapleaf hash of the Taproot leaf script that will be signed. If the aggregate key is the Taproot internal key or the Taproot output key, then the tapleaf hash must be omitted. The compressed participant public key must be the Taproot output key or found in a script. It is not the internal key nor the aggregate public key that it was derived from, if it was derived from an aggregate key. | The public nonce produced by the NonceGen algorithm. |- | rowspan="2"|MuSig2 Participant Partial Signature | rowspan="2"|PSBT_IN_MUSIG2_PARTIAL_SIG = 0x1c | <33 byte participant pubkey (compressed)> <33 byte aggregate pubkey (compressed)> <32 byte hash or omitted> | <32 byte partial signature> | rowspan="2"| | rowspan="2"| | rowspan="2"| 0, 2 |- | The compressed public key of the participant providing this partial signature, followed by the compressed aggregate public key the participant is providing the signature for, followed by the [[bip-0341.mediawiki|BIP 341]] tapleaf hash of the Taproot leaf script that will be signed. If the aggregate key is the Taproot internal key or the Taproot output key, then the tapleaf hash must be omitted. Note that the compressed participant public key must be the Taproot output key or found in a script. It is not the internal key nor the aggregate public key that it was derived from, if it was derived from an aggregate key. | The partial signature produced by the Sign algorithm. |} The new per-output types are defined as follows: {| ! Name ! ! ! ! Versions Requiring Inclusion ! Versions Requiring Exclusion ! Versions Allowing Inclusion |- | rowspan="2"|MuSig2 Participant Public Keys | rowspan="2"|PSBT_OUT_MUSIG2_PARTICIPANT_PUBKEYS = 0x08 | <33 byte aggregate pubkey (compressed)> | <33 byte participant pubkey (compressed)>* | rowspan="2"| | rowspan="2"| | rowspan="2"|0, 2 |- | The MuSig2 compressed aggregate public key from the KeyAgg algorithm. This key may or may not appear (as x-only) in the Taproot output key, the internal key, or in a script. It may instead be a parent public key from which the Taproot output key, internal key, or keys in a script were derived. | A list of the compressed public keys of the participants in the MuSig2 aggregate key in the order required for aggregation. If sorting was done, then the keys must be in the sorted order. |} ==Roles== ===Updater=== When an updater observes a Taproot output which involves a MuSig2 aggregate public key that it is aware of, it can add a PSBT_IN_MUSIG2_PARTICIPANT_PUBKEYS field containing the public keys of the participants. This aggregate public key may be directly in the script, the Taproot internal key, the Taproot output key, or a public key from which the key in the script was derived from. An aggregate public key that appears directly in the script or internal key may be from the result of deriving child pubkeys from participant xpubs. If the updater has this derivation information, it should also add PSBT_IN_TAP_BIP32_DERIVATION for each participant public key. If the public key found was derived from an aggregate public key, then all MuSig2 PSBT fields for that public key should contain the aggregate public key rather than the found pubkey itself. The updater should also add PSBT_IN_TAP_BIP32_DERIVATION that contains the derivation path used to derive the found pubkey from the aggregate pubkey. Derivation from the aggregate pubkey can be assumed to follow [[bip-0328.mediawiki|BIP 328]] if there is no PSBT_GLOBAL_XPUB that specifies the synthetic xpub for the aggregate public key. Updaters should add PSBT_OUT_MUSIG2_PARTICIPANT_PUBKEYS and PSBT_OUT_TAP_BIP32_DERIVATION similarly to inputs to aid in change detection. ===Signer=== To determine whether a signer is a participant in the MuSig2 aggregate key, the signer should first look at all PSBT_IN_MUSIG2_PARTICIPANT_PUBKEYS and see if any key which it knows the private key for appears as a participant in any aggregate pubkey. Signers should also check whether any of the keys in PSBT_IN_TAP_BIP32_DERIVATION belong to it, and if any of those keys appear in as a participant in PSBT_IN_MUSIG2_PARTICIPANT_PUBKEYS. For each aggregate public key that the signer is a participant of that it wants to produce a signature for, if the signer does not find an existing PSBT_IN_MUSIG2_PUB_NONCE field for its key, then it should add one using the NonceGen algorithm (or one of its variations) to produce a public nonce that is added in a PSBT_IN_MUSIG2_PUB_NONCE field. However signers must keep in mind that '''improper nonce usage can compromise private keys.''' Please see [[bip-0327.mediawiki|BIP 327]] for best practices on nonce generation and usage. Once all signers have added their PSBT_IN_MUSIG2_PUB_NONCE fields, each signer will perform the NonceAgg algorithm followed by the Sign algorithm in order to produce the partial signature for their key. The result will be added to the PSBT in a PSBT_IN_MUSIG2_PARTIAL_SIG field. Signers must remember to apply any relevant tweaks such as a tweak that is the result of performing BIP 32 unhardened derivation with the aggregate public key as the parent key. If all other signers have provided a PSBT_IN_MUSIG2_PARTIAL_SIG, then the final signer may perform the PartialSigAgg algorithm and produce a [[bip-0340.mediawiki|BIP 340]] compatible signature that can be placed into a PSBT_IN_TAP_KEY_SIG or a PSBT_IN_TAP_SCRIPT_SIG. ===Finalizer=== A finalizer may perform the same PartialSigAgg step as the final signer if it has not already been done. Otherwise, the resulting signature is a [[bip-0340.mediawiki|BIP 340]] compatible signature and finalizers should treat it as such. ==Backwards Compatibility== These are simply new fields added to the existing PSBT format. Because PSBT is designed to be extensible, old software will ignore the new fields. Reusing PSBT_IN_TAP_BIP32_DERIVATION to provide derivation paths for participant public keys may cause software unaware of MuSig2 to produce a signature for that public key. This is still safe. If that public key does not directly appear in the leaf script that was signed, then the signature produced will not be useful and so cannot be replayed. If the public key does directly appear in the leaf script, then the signer will have validated the script as if it did not involve a MuSig2 and will have found it acceptable in order for it to have produced a signature. In either case, producing a signature does not give rise to the possibility of losing funds. ==Test Vectors== The following are valid PSBTs All of the following test cases use the aggregate pubkey 030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4 which has the following participant keys: # 02346B99593357107C9D3459E9DEBA8D3EAF44E6636C85C7F853EB90BA52E8CD00, L2XJhGmS9rkNwzn1eFJVD5ydKpA5K5p54uk9qqWpURj85VkEPuNE, cStJABmHavSe7SFH2f7caQUgx3TUyXum8wtcxFyKyYP8LEqnMiEh # 024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c, L19kEzCkrce5E3v7CWKn9pTceVzFwwdorjNXfqtUc5nKLXz4qXSX, cRWjhuCcHgLLPVPNav8uX8xgGjHfcPjVvmWznGLz7CSKbGzmfvRQ # 02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9, KwDiBf89QgGbjEhKnhXJuH7LrciVrZi3qYjgd9M7rFU74sHUHy8S, cMahea7zqjxrtgAbB7LSGbcQUr1uX1ojuat9jZodMN87KcLPVfXz * Case: Spend of a Taproot output where the output key is a MuSig2 Aggregate Pubkey ** With participant pubkeys only *** Bytes in Hex:
70736274ff01005202000000015686dff400165f4e040a5855f658093472c9bcf8108b272a5d31f181f7b4ffb10100000000fdffffff0118ddf50500000000160014c9123e06e8d7f0966c5d1cd0f933002d4eb757cd000000000001012b00e1f505000000002251200b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d421160b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d405002680dd6e2116346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd000500580b088721164fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c0500c3249a822116f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f905007dd65592221a030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d46302346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f90000
*** Base64 String:
cHNidP8BAFICAAAAAVaG3/QAFl9OBApYVfZYCTRyybz4EIsnKl0x8YH3tP+xAQAAAAD9////ARjd9QUAAAAAFgAUyRI+BujX8JZsXRzQ+TMALU63V80AAAAAAAEBKwDh9QUAAAAAIlEgC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9QhFgtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUBQAmgN1uIRY0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAUAWAsIhyEWT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwFAMMkmoIhFvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5BQB91lWSIhoDC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9RjAjRrmVkzVxB8nTRZ6d66jT6vROZjbIXH+FPrkLpS6M0AAk+v1l+BaRhvwr/bIjPHfmMNEL4oCiTHFlwJonYRd1wsAvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5AAA=
** With all pubnonces *** Bytes in Hex:
70736274ff01005202000000015686dff400165f4e040a5855f658093472c9bcf8108b272a5d31f181f7b4ffb10100000000fdffffff0118ddf50500000000160014c9123e06e8d7f0966c5d1cd0f933002d4eb757cd000000000001012b00e1f505000000002251200b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d421160b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d405002680dd6e2116346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd000500580b088721164fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c0500c3249a822116f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f905007dd65592221a030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d46302346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9431b02346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d44202529b19d7879ccc04c915487f5f1341bc6858b0bc74e5036c643d37b53a4371b503b7f8afe3263fcb3ef2454fe16f3a6759c5600c78e637b8dfa0d83e8552882056431b024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d44203a81d973499e74f82d2b5ab13f1e69e9e11a5fdb40f5466ef672e6e4ceba0be7903499593767150394eece384d051c45b615c52dbe1c8eb3610d7b344b43b7dad6d431b02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d442033949dbff31b9d50251d8821e66cc5c97b7e3afd7d95bfdc77500fda8947f3ae0023f20e4f0bf0b76f0d40cd3abfe7ce373d6685bbd77b5fa28e7f49fb429d189b00000
*** Base64 String:
cHNidP8BAFICAAAAAVaG3/QAFl9OBApYVfZYCTRyybz4EIsnKl0x8YH3tP+xAQAAAAD9////ARjd9QUAAAAAFgAUyRI+BujX8JZsXRzQ+TMALU63V80AAAAAAAEBKwDh9QUAAAAAIlEgC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9QhFgtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUBQAmgN1uIRY0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAUAWAsIhyEWT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwFAMMkmoIhFvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5BQB91lWSIhoDC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9RjAjRrmVkzVxB8nTRZ6d66jT6vROZjbIXH+FPrkLpS6M0AAk+v1l+BaRhvwr/bIjPHfmMNEL4oCiTHFlwJonYRd1wsAvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5QxsCNGuZWTNXEHydNFnp3rqNPq9E5mNshcf4U+uQulLozQADC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9RCAlKbGdeHnMwEyRVIf18TQbxoWLC8dOUDbGQ9N7U6Q3G1A7f4r+MmP8s+8kVP4W86Z1nFYAx45je436DYPoVSiCBWQxsCT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwDC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9RCA6gdlzSZ50+C0rWrE/Hmnp4Rpf20D1Rm72cubkzroL55A0mVk3ZxUDlO7OOE0FHEW2FcUtvhyOs2ENezRLQ7fa1tQxsC+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvkDC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9RCAzlJ2/8xudUCUdiCHmbMXJe346/X2Vv9x3UA/aiUfzrgAj8g5PC/C3bw1AzTq/5843PWaFu9d7X6KOf0n7Qp0YmwAAA=
** With all partial signatures *** Bytes in Hex:
70736274ff01005202000000015686dff400165f4e040a5855f658093472c9bcf8108b272a5d31f181f7b4ffb10100000000fdffffff0118ddf50500000000160014c9123e06e8d7f0966c5d1cd0f933002d4eb757cd000000000001012b00e1f505000000002251200b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d421160b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d405002680dd6e2116346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd000500580b088721164fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c0500c3249a822116f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f905007dd65592221a030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d46302346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9431b02346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d44202529b19d7879ccc04c915487f5f1341bc6858b0bc74e5036c643d37b53a4371b503b7f8afe3263fcb3ef2454fe16f3a6759c5600c78e637b8dfa0d83e8552882056431b024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d44203a81d973499e74f82d2b5ab13f1e69e9e11a5fdb40f5466ef672e6e4ceba0be7903499593767150394eece384d051c45b615c52dbe1c8eb3610d7b344b43b7dad6d431b02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d442033949dbff31b9d50251d8821e66cc5c97b7e3afd7d95bfdc77500fda8947f3ae0023f20e4f0bf0b76f0d40cd3abfe7ce373d6685bbd77b5fa28e7f49fb429d189b0431c02346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4200e57ca4ca0de1a3116d3fd6baf19d38572e47e8ff024e7efc39512751e54ed31431c024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4207254079cab166b0d50b54283fccb4aea15f776747a5d2a53d7da06239340dbcc431c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d42001245e8861e62ac5bfc0008418fd057ce6b03c17b1d6b5c6980413c5c4e358970000
*** Base64 String:
cHNidP8BAFICAAAAAVaG3/QAFl9OBApYVfZYCTRyybz4EIsnKl0x8YH3tP+xAQAAAAD9////ARjd9QUAAAAAFgAUyRI+BujX8JZsXRzQ+TMALU63V80AAAAAAAEBKwDh9QUAAAAAIlEgC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9QhFgtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUBQAmgN1uIRY0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAUAWAsIhyEWT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwFAMMkmoIhFvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5BQB91lWSIhoDC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9RjAjRrmVkzVxB8nTRZ6d66jT6vROZjbIXH+FPrkLpS6M0AAk+v1l+BaRhvwr/bIjPHfmMNEL4oCiTHFlwJonYRd1wsAvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5QxsCNGuZWTNXEHydNFnp3rqNPq9E5mNshcf4U+uQulLozQADC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9RCAlKbGdeHnMwEyRVIf18TQbxoWLC8dOUDbGQ9N7U6Q3G1A7f4r+MmP8s+8kVP4W86Z1nFYAx45je436DYPoVSiCBWQxsCT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwDC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9RCA6gdlzSZ50+C0rWrE/Hmnp4Rpf20D1Rm72cubkzroL55A0mVk3ZxUDlO7OOE0FHEW2FcUtvhyOs2ENezRLQ7fa1tQxsC+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvkDC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9RCAzlJ2/8xudUCUdiCHmbMXJe346/X2Vv9x3UA/aiUfzrgAj8g5PC/C3bw1AzTq/5843PWaFu9d7X6KOf0n7Qp0YmwQxwCNGuZWTNXEHydNFnp3rqNPq9E5mNshcf4U+uQulLozQADC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9QgDlfKTKDeGjEW0/1rrxnThXLkfo/wJOfvw5USdR5U7TFDHAJPr9ZfgWkYb8K/2yIzx35jDRC+KAokxxZcCaJ2EXdcLAMLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1CByVAecqxZrDVC1QoP8y0rqFfd2dHpdKlPX2gYjk0DbzEMcAvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5AwtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUIAEkXohh5irFv8AAhBj9BXzmsDwXsda1xpgEE8XE41iXAAA=
* Case: Spend of a Taproot output where the internal key is a MuSig2 Aggregate Pubkey ** With participant pubkeys only *** Bytes in Hex:
70736274ff01005202000000015818a9cd644b369c306c7fb191ec014ff625e63c283f00f9d17a959fefa3e8f60000000000fdffffff0118ddf50500000000160014c9123e06e8d7f0966c5d1cd0f933002d4eb757cd000000000001012b00e1f505000000002251202967d2d020a9795da72b51be4f3fca25bb0e57e91c5b3e7a81abfa7232a3494221160b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d405002680dd6e2116346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd000500580b088721164fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c0500c3249a822116f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f905007dd655920117200b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4221a030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d46302346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f90000
*** Base64 String:
cHNidP8BAFICAAAAAVgYqc1kSzacMGx/sZHsAU/2JeY8KD8A+dF6lZ/vo+j2AAAAAAD9////ARjd9QUAAAAAFgAUyRI+BujX8JZsXRzQ+TMALU63V80AAAAAAAEBKwDh9QUAAAAAIlEgKWfS0CCpeV2nK1G+Tz/KJbsOV+kcWz56gav6cjKjSUIhFgtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUBQAmgN1uIRY0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAUAWAsIhyEWT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwFAMMkmoIhFvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5BQB91lWSARcgC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9QiGgMLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1GMCNGuZWTNXEHydNFnp3rqNPq9E5mNshcf4U+uQulLozQACT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwC+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvkAAA==
** With all pubnonces *** Bytes in Hex:
70736274ff01005202000000015818a9cd644b369c306c7fb191ec014ff625e63c283f00f9d17a959fefa3e8f60000000000fdffffff0118ddf50500000000160014c9123e06e8d7f0966c5d1cd0f933002d4eb757cd000000000001012b00e1f505000000002251202967d2d020a9795da72b51be4f3fca25bb0e57e91c5b3e7a81abfa7232a3494221160b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d405002680dd6e2116346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd000500580b088721164fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c0500c3249a822116f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f905007dd655920117200b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4221a030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d46302346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9431b02346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00032967d2d020a9795da72b51be4f3fca25bb0e57e91c5b3e7a81abfa7232a349424203cc17485ca01c2ebb0eba1c80b3eadaf5ee9cc14629fa4f1071d19820e2d07fcc02adfcad45a68cfb67759c9849cdd579639e4d1867272b991a0363d1ca76283efc431b024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c032967d2d020a9795da72b51be4f3fca25bb0e57e91c5b3e7a81abfa7232a349424202343bb8359c434f5f6a9d6b46f7573258fbfbb561bb5212cbf5850a82a9a02f7e0246e83221664427aca6d13c10809a2cb4b54dae9a7b2f5ab764213dd479a6a942431b02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9032967d2d020a9795da72b51be4f3fca25bb0e57e91c5b3e7a81abfa7232a3494242039dee4258b8dfe34460086ff1703209e478437c6ab0f598a2e6e809fd30a9ff3a03e06b4e04ec4de4f757c84d51acdaf6cb1ef4bccbfd8103703bc01a845dcf33650000
*** Base64 String:
cHNidP8BAFICAAAAAVgYqc1kSzacMGx/sZHsAU/2JeY8KD8A+dF6lZ/vo+j2AAAAAAD9////ARjd9QUAAAAAFgAUyRI+BujX8JZsXRzQ+TMALU63V80AAAAAAAEBKwDh9QUAAAAAIlEgKWfS0CCpeV2nK1G+Tz/KJbsOV+kcWz56gav6cjKjSUIhFgtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUBQAmgN1uIRY0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAUAWAsIhyEWT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwFAMMkmoIhFvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5BQB91lWSARcgC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9QiGgMLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1GMCNGuZWTNXEHydNFnp3rqNPq9E5mNshcf4U+uQulLozQACT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwC+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvlDGwI0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAMpZ9LQIKl5XacrUb5PP8oluw5X6RxbPnqBq/pyMqNJQkIDzBdIXKAcLrsOuhyAs+ra9e6cwUYp+k8QcdGYIOLQf8wCrfytRaaM+2d1nJhJzdV5Y55NGGcnK5kaA2PRynYoPvxDGwJPr9ZfgWkYb8K/2yIzx35jDRC+KAokxxZcCaJ2EXdcLAMpZ9LQIKl5XacrUb5PP8oluw5X6RxbPnqBq/pyMqNJQkICNDu4NZxDT19qnWtG91cyWPv7tWG7UhLL9YUKgqmgL34CRugyIWZEJ6ym0TwQgJostLVNrpp7L1q3ZCE91HmmqUJDGwL5MIoBkljDEEk0T4X4nVIptTHIRYNvmbCGAfETvOA2+QMpZ9LQIKl5XacrUb5PP8oluw5X6RxbPnqBq/pyMqNJQkIDne5CWLjf40RgCG/xcDIJ5HhDfGqw9Zii5ugJ/TCp/zoD4GtOBOxN5PdXyE1RrNr2yx70vMv9gQNwO8AahF3PM2UAAA==
** With all partial signatures *** Bytes in Hex:
70736274ff01005202000000015818a9cd644b369c306c7fb191ec014ff625e63c283f00f9d17a959fefa3e8f60000000000fdffffff0118ddf50500000000160014c9123e06e8d7f0966c5d1cd0f933002d4eb757cd000000000001012b00e1f505000000002251202967d2d020a9795da72b51be4f3fca25bb0e57e91c5b3e7a81abfa7232a349420113402e89a7bdf9085c6438d15ddf1a86772a65222244276e9302ffdd9fa93b1c20ae58a6b11a6be98b151d8582daa84c10017c994d9235b13ec518a94782c67c40e221160b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d405002680dd6e2116346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd000500580b088721164fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c0500c3249a822116f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f905007dd655920117200b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4221a030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d46302346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9431b02346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00032967d2d020a9795da72b51be4f3fca25bb0e57e91c5b3e7a81abfa7232a349424203cc17485ca01c2ebb0eba1c80b3eadaf5ee9cc14629fa4f1071d19820e2d07fcc02adfcad45a68cfb67759c9849cdd579639e4d1867272b991a0363d1ca76283efc431b024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c032967d2d020a9795da72b51be4f3fca25bb0e57e91c5b3e7a81abfa7232a349424202343bb8359c434f5f6a9d6b46f7573258fbfbb561bb5212cbf5850a82a9a02f7e0246e83221664427aca6d13c10809a2cb4b54dae9a7b2f5ab764213dd479a6a942431b02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9032967d2d020a9795da72b51be4f3fca25bb0e57e91c5b3e7a81abfa7232a3494242039dee4258b8dfe34460086ff1703209e478437c6ab0f598a2e6e809fd30a9ff3a03e06b4e04ec4de4f757c84d51acdaf6cb1ef4bccbfd8103703bc01a845dcf3365431c02346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00032967d2d020a9795da72b51be4f3fca25bb0e57e91c5b3e7a81abfa7232a3494220109ad32155722014ddca21ae3b8d3c3a93a6d0ab5c7e19d0c693d565c47c1626431c024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c032967d2d020a9795da72b51be4f3fca25bb0e57e91c5b3e7a81abfa7232a349422035d5eecc404fa2a63644f30cf8af43fdbd829e5cd9c74707ca9b33a9134c756e431c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9032967d2d020a9795da72b51be4f3fca25bb0e57e91c5b3e7a81abfa7232a3494220b9c855defd44676ff3fc5342adbc90c2dec15624eab55b1ff29765315603db6e0000
*** Base64 String:
cHNidP8BAFICAAAAAVgYqc1kSzacMGx/sZHsAU/2JeY8KD8A+dF6lZ/vo+j2AAAAAAD9////ARjd9QUAAAAAFgAUyRI+BujX8JZsXRzQ+TMALU63V80AAAAAAAEBKwDh9QUAAAAAIlEgKWfS0CCpeV2nK1G+Tz/KJbsOV+kcWz56gav6cjKjSUIBE0Auiae9+QhcZDjRXd8ahncqZSIiRCdukwL/3Z+pOxwgrlimsRpr6YsVHYWC2qhMEAF8mU2SNbE+xRipR4LGfEDiIRYLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1AUAJoDdbiEWNGuZWTNXEHydNFnp3rqNPq9E5mNshcf4U+uQulLozQAFAFgLCIchFk+v1l+BaRhvwr/bIjPHfmMNEL4oCiTHFlwJonYRd1wsBQDDJJqCIRb5MIoBkljDEEk0T4X4nVIptTHIRYNvmbCGAfETvOA2+QUAfdZVkgEXIAtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUIhoDC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9RjAjRrmVkzVxB8nTRZ6d66jT6vROZjbIXH+FPrkLpS6M0AAk+v1l+BaRhvwr/bIjPHfmMNEL4oCiTHFlwJonYRd1wsAvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5QxsCNGuZWTNXEHydNFnp3rqNPq9E5mNshcf4U+uQulLozQADKWfS0CCpeV2nK1G+Tz/KJbsOV+kcWz56gav6cjKjSUJCA8wXSFygHC67DrocgLPq2vXunMFGKfpPEHHRmCDi0H/MAq38rUWmjPtndZyYSc3VeWOeTRhnJyuZGgNj0cp2KD78QxsCT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwDKWfS0CCpeV2nK1G+Tz/KJbsOV+kcWz56gav6cjKjSUJCAjQ7uDWcQ09fap1rRvdXMlj7+7Vhu1ISy/WFCoKpoC9+AkboMiFmRCesptE8EICaLLS1Ta6aey9at2QhPdR5pqlCQxsC+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvkDKWfS0CCpeV2nK1G+Tz/KJbsOV+kcWz56gav6cjKjSUJCA53uQli43+NEYAhv8XAyCeR4Q3xqsPWYouboCf0wqf86A+BrTgTsTeT3V8hNUaza9sse9LzL/YEDcDvAGoRdzzNlQxwCNGuZWTNXEHydNFnp3rqNPq9E5mNshcf4U+uQulLozQADKWfS0CCpeV2nK1G+Tz/KJbsOV+kcWz56gav6cjKjSUIgEJrTIVVyIBTdyiGuO408OpOm0KtcfhnQxpPVZcR8FiZDHAJPr9ZfgWkYb8K/2yIzx35jDRC+KAokxxZcCaJ2EXdcLAMpZ9LQIKl5XacrUb5PP8oluw5X6RxbPnqBq/pyMqNJQiA11e7MQE+ipjZE8wz4r0P9vYKeXNnHRwfKmzOpE0x1bkMcAvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5Ayln0tAgqXldpytRvk8/yiW7DlfpHFs+eoGr+nIyo0lCILnIVd79RGdv8/xTQq28kMLewVYk6rVbH/KXZTFWA9tuAAA=
* Case: Spend of a Taproot output where a key in a script is a MuSig2 Aggregate Pubkey ** With participant pubkeys only *** Bytes in Hex:
70736274ff01005202000000019a8b4a50796b9600990f7fe11dfa00bc70efd296048afc86719af0fb1fa919370100000000fdffffff0118ddf50500000000160014c9123e06e8d7f0966c5d1cd0f933002d4eb757cd000000000001012b00e1f5050000000022512056bdb481b4d67103f6d5dea8a9aafd3684a6a79b4a2e247799db8d4b1a86e1f82215c050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac023200b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4acc021160b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d42501b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c2680dd6e2116346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd002501b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c580b088721164fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c2501b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2cc3249a82211650929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac005007c461e5d2116f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f92501b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c7dd6559201172050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac0011820b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c221a030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d46302346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f90000
*** Base64 String:
cHNidP8BAFICAAAAAZqLSlB5a5YAmQ9/4R36ALxw79KWBIr8hnGa8PsfqRk3AQAAAAD9////ARjd9QUAAAAAFgAUyRI+BujX8JZsXRzQ+TMALU63V80AAAAAAAEBKwDh9QUAAAAAIlEgVr20gbTWcQP21d6oqar9NoSmp5tKLiR3mduNSxqG4fgiFcBQkpt0waBJVLeLS2A16XpeB4paDyjsltVHv+6azoA6wCMgC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9SswCEWC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9QlAbEf7apjoJVlAacwjJO1Y3Nx52E9m4reF4PUnibAbPosJoDdbiEWNGuZWTNXEHydNFnp3rqNPq9E5mNshcf4U+uQulLozQAlAbEf7apjoJVlAacwjJO1Y3Nx52E9m4reF4PUnibAbPosWAsIhyEWT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwlAbEf7apjoJVlAacwjJO1Y3Nx52E9m4reF4PUnibAbPoswySagiEWUJKbdMGgSVS3i0tgNel6XgeKWg8o7JbVR7/ums6AOsAFAHxGHl0hFvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5JQGxH+2qY6CVZQGnMIyTtWNzcedhPZuK3heD1J4mwGz6LH3WVZIBFyBQkpt0waBJVLeLS2A16XpeB4paDyjsltVHv+6azoA6wAEYILEf7apjoJVlAacwjJO1Y3Nx52E9m4reF4PUnibAbPosIhoDC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9RjAjRrmVkzVxB8nTRZ6d66jT6vROZjbIXH+FPrkLpS6M0AAk+v1l+BaRhvwr/bIjPHfmMNEL4oCiTHFlwJonYRd1wsAvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5AAA=
** With all pubnonces *** Bytes in Hex:
70736274ff01005202000000019a8b4a50796b9600990f7fe11dfa00bc70efd296048afc86719af0fb1fa919370100000000fdffffff0118ddf50500000000160014c9123e06e8d7f0966c5d1cd0f933002d4eb757cd000000000001012b00e1f5050000000022512056bdb481b4d67103f6d5dea8a9aafd3684a6a79b4a2e247799db8d4b1a86e1f82215c050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac023200b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4acc021160b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d42501b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c2680dd6e2116346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd002501b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c580b088721164fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c2501b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2cc3249a82211650929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac005007c461e5d2116f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f92501b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c7dd6559201172050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac0011820b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c221a030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d46302346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9631b02346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c4202d99e7c8719b3ad08566b0cb9c7d5eda3127c9e8119185b7d584d939b173915f50240df22aab78332cf0f25329d103dc0d2060a03742e9448026e736bcf3db98f3c631b024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c4202e702a7075226a0d9313a77e6db10b8e742d4cffdc948a0edc9b856c13b412e5403386a0298f308fb3099155772e45b2aa8e770f435bedfe2041d1cc4d3d37538c6631b02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c4202b1d912d45d753ceed0954417ba982656d2aec53f8638bd6f297dae3b743d71b0032f424537d599d28f14d59fe0a11b82fea2aa226a2980ffdacad5fdab20f806830000
*** Base64 String:
cHNidP8BAFICAAAAAZqLSlB5a5YAmQ9/4R36ALxw79KWBIr8hnGa8PsfqRk3AQAAAAD9////ARjd9QUAAAAAFgAUyRI+BujX8JZsXRzQ+TMALU63V80AAAAAAAEBKwDh9QUAAAAAIlEgVr20gbTWcQP21d6oqar9NoSmp5tKLiR3mduNSxqG4fgiFcBQkpt0waBJVLeLS2A16XpeB4paDyjsltVHv+6azoA6wCMgC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9SswCEWC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9QlAbEf7apjoJVlAacwjJO1Y3Nx52E9m4reF4PUnibAbPosJoDdbiEWNGuZWTNXEHydNFnp3rqNPq9E5mNshcf4U+uQulLozQAlAbEf7apjoJVlAacwjJO1Y3Nx52E9m4reF4PUnibAbPosWAsIhyEWT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwlAbEf7apjoJVlAacwjJO1Y3Nx52E9m4reF4PUnibAbPoswySagiEWUJKbdMGgSVS3i0tgNel6XgeKWg8o7JbVR7/ums6AOsAFAHxGHl0hFvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5JQGxH+2qY6CVZQGnMIyTtWNzcedhPZuK3heD1J4mwGz6LH3WVZIBFyBQkpt0waBJVLeLS2A16XpeB4paDyjsltVHv+6azoA6wAEYILEf7apjoJVlAacwjJO1Y3Nx52E9m4reF4PUnibAbPosIhoDC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9RjAjRrmVkzVxB8nTRZ6d66jT6vROZjbIXH+FPrkLpS6M0AAk+v1l+BaRhvwr/bIjPHfmMNEL4oCiTHFlwJonYRd1wsAvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5YxsCNGuZWTNXEHydNFnp3rqNPq9E5mNshcf4U+uQulLozQADC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9SxH+2qY6CVZQGnMIyTtWNzcedhPZuK3heD1J4mwGz6LEIC2Z58hxmzrQhWawy5x9XtoxJ8noEZGFt9WE2Tmxc5FfUCQN8iqreDMs8PJTKdED3A0gYKA3QulEgCbnNrzz25jzxjGwJPr9ZfgWkYb8K/2yIzx35jDRC+KAokxxZcCaJ2EXdcLAMLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1LEf7apjoJVlAacwjJO1Y3Nx52E9m4reF4PUnibAbPosQgLnAqcHUiag2TE6d+bbELjnQtTP/clIoO3JuFbBO0EuVAM4agKY8wj7MJkVV3LkWyqo53D0Nb7f4gQdHMTT03U4xmMbAvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5AwtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+ixCArHZEtRddTzu0JVEF7qYJlbSrsU/hji9byl9rjt0PXGwAy9CRTfVmdKPFNWf4KEbgv6iqiJqKYD/2srV/asg+AaDAAA=
** With all partial signatures *** Bytes in Hex:
70736274ff01005202000000019a8b4a50796b9600990f7fe11dfa00bc70efd296048afc86719af0fb1fa919370100000000fdffffff0118ddf50500000000160014c9123e06e8d7f0966c5d1cd0f933002d4eb757cd000000000001012b00e1f5050000000022512056bdb481b4d67103f6d5dea8a9aafd3684a6a79b4a2e247799db8d4b1a86e1f841140b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c402667d52f6cc07fe06db31b1a5f7efe81903f9cbeef40fa64dafca01d2cb1d56403bc7504898e55872557d16d2ca79bc55fef10973841a33ec032d884758c9fe62215c050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac023200b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4acc021160b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d42501b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c2680dd6e2116346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd002501b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c580b088721164fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c2501b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2cc3249a82211650929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac005007c461e5d2116f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f92501b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c7dd6559201172050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac0011820b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c221a030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d46302346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9631b02346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c4202d99e7c8719b3ad08566b0cb9c7d5eda3127c9e8119185b7d584d939b173915f50240df22aab78332cf0f25329d103dc0d2060a03742e9448026e736bcf3db98f3c631b024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c4202e702a7075226a0d9313a77e6db10b8e742d4cffdc948a0edc9b856c13b412e5403386a0298f308fb3099155772e45b2aa8e770f435bedfe2041d1cc4d3d37538c6631b02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c4202b1d912d45d753ceed0954417ba982656d2aec53f8638bd6f297dae3b743d71b0032f424537d599d28f14d59fe0a11b82fea2aa226a2980ffdacad5fdab20f80683631c02346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c20ada78b70af8cffa4c50863aef515ac58a327cd58c55bad29a162e67d9c413322631c024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c201fa8b7e6741c21eb8d9b0f65269df9e423369fc390ad2e918420c57feb2a1b61631c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c20366c31ad65e533f6d2b45e5910f3f587543f8061918167bf5a818b13be5792a40000
*** Base64 String:
cHNidP8BAFICAAAAAZqLSlB5a5YAmQ9/4R36ALxw79KWBIr8hnGa8PsfqRk3AQAAAAD9////ARjd9QUAAAAAFgAUyRI+BujX8JZsXRzQ+TMALU63V80AAAAAAAEBKwDh9QUAAAAAIlEgVr20gbTWcQP21d6oqar9NoSmp5tKLiR3mduNSxqG4fhBFAtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+ixAJmfVL2zAf+BtsxsaX37+gZA/nL7vQPpk2vygHSyx1WQDvHUEiY5VhyVX0W0sp5vFX+8QlzhBoz7AMtiEdYyf5iIVwFCSm3TBoElUt4tLYDXpel4HiloPKOyW1Ue/7prOgDrAIyALWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1KzAIRYLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1CUBsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+iwmgN1uIRY0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNACUBsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+ixYCwiHIRZPr9ZfgWkYb8K/2yIzx35jDRC+KAokxxZcCaJ2EXdcLCUBsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+izDJJqCIRZQkpt0waBJVLeLS2A16XpeB4paDyjsltVHv+6azoA6wAUAfEYeXSEW+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvklAbEf7apjoJVlAacwjJO1Y3Nx52E9m4reF4PUnibAbPosfdZVkgEXIFCSm3TBoElUt4tLYDXpel4HiloPKOyW1Ue/7prOgDrAARggsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+iwiGgMLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1GMCNGuZWTNXEHydNFnp3rqNPq9E5mNshcf4U+uQulLozQACT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwC+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvljGwI0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAMLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1LEf7apjoJVlAacwjJO1Y3Nx52E9m4reF4PUnibAbPosQgLZnnyHGbOtCFZrDLnH1e2jEnyegRkYW31YTZObFzkV9QJA3yKqt4Myzw8lMp0QPcDSBgoDdC6USAJuc2vPPbmPPGMbAk+v1l+BaRhvwr/bIjPHfmMNEL4oCiTHFlwJonYRd1wsAwtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+ixCAucCpwdSJqDZMTp35tsQuOdC1M/9yUig7cm4VsE7QS5UAzhqApjzCPswmRVXcuRbKqjncPQ1vt/iBB0cxNPTdTjGYxsC+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvkDC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9SxH+2qY6CVZQGnMIyTtWNzcedhPZuK3heD1J4mwGz6LEICsdkS1F11PO7QlUQXupgmVtKuxT+GOL1vKX2uO3Q9cbADL0JFN9WZ0o8U1Z/goRuC/qKqImopgP/aytX9qyD4BoNjHAI0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAMLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1LEf7apjoJVlAacwjJO1Y3Nx52E9m4reF4PUnibAbPosIK2ni3CvjP+kxQhjrvUVrFijJ81YxVutKaFi5n2cQTMiYxwCT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwDC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9SxH+2qY6CVZQGnMIyTtWNzcedhPZuK3heD1J4mwGz6LCAfqLfmdBwh642bD2UmnfnkIzafw5CtLpGEIMV/6yobYWMcAvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5AwtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+iwgNmwxrWXlM/bStF5ZEPP1h1Q/gGGRgWe/WoGLE75XkqQAAA==
* Case: Spend of a Taproot output where the internal key is derived from a MuSig2 Aggregate Pubkey ** With participant pubkeys only *** Bytes in Hex:
70736274ff01005202000000012589e7767958ba154f9018cccf0dedea6147bb60cd1a194b6e3590a9965690d60100000000fdffffff0118ddf50500000000160014c9123e06e8d7f0966c5d1cd0f933002d4eb757cd000000000001012b00e1f50500000000225120d0b226c6599f273874df8fe684ab6c3028081bee8a2cbed31a136f5865f6cfa42116346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd000500580b088721164fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c0500c3249a8221168dd96ab858b259c518218c014a46eb4e6ac899e51c675ef774fbb68a8799ce2f0d002680dd6e01000000020000002116f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f905007dd655920117208dd96ab858b259c518218c014a46eb4e6ac899e51c675ef774fbb68a8799ce2f221a030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d46302346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f90000
*** Base64 String:
cHNidP8BAFICAAAAASWJ53Z5WLoVT5AYzM8N7ephR7tgzRoZS241kKmWVpDWAQAAAAD9////ARjd9QUAAAAAFgAUyRI+BujX8JZsXRzQ+TMALU63V80AAAAAAAEBKwDh9QUAAAAAIlEg0LImxlmfJzh034/mhKtsMCgIG+6KLL7TGhNvWGX2z6QhFjRrmVkzVxB8nTRZ6d66jT6vROZjbIXH+FPrkLpS6M0ABQBYCwiHIRZPr9ZfgWkYb8K/2yIzx35jDRC+KAokxxZcCaJ2EXdcLAUAwySagiEWjdlquFiyWcUYIYwBSkbrTmrImeUcZ173dPu2ioeZzi8NACaA3W4BAAAAAgAAACEW+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvkFAH3WVZIBFyCN2Wq4WLJZxRghjAFKRutOasiZ5RxnXvd0+7aKh5nOLyIaAwtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUYwI0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAJPr9ZfgWkYb8K/2yIzx35jDRC+KAokxxZcCaJ2EXdcLAL5MIoBkljDEEk0T4X4nVIptTHIRYNvmbCGAfETvOA2+QAA
** With all pubnonces *** Bytes in Hex:
70736274ff01005202000000012589e7767958ba154f9018cccf0dedea6147bb60cd1a194b6e3590a9965690d60100000000fdffffff0118ddf50500000000160014c9123e06e8d7f0966c5d1cd0f933002d4eb757cd000000000001012b00e1f50500000000225120d0b226c6599f273874df8fe684ab6c3028081bee8a2cbed31a136f5865f6cfa42116346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd000500580b088721164fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c0500c3249a8221168dd96ab858b259c518218c014a46eb4e6ac899e51c675ef774fbb68a8799ce2f0d002680dd6e01000000020000002116f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f905007dd655920117208dd96ab858b259c518218c014a46eb4e6ac899e51c675ef774fbb68a8799ce2f221a030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d46302346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9431b02346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd0002d0b226c6599f273874df8fe684ab6c3028081bee8a2cbed31a136f5865f6cfa442024eefc9fdd12be74746485c678b8268949cc9236e9fce82241395523af04262bf038c276e832aad4bfb9e90485162f574c8b2619df5bd19db8ffa2eb0059493bf1b431b024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02d0b226c6599f273874df8fe684ab6c3028081bee8a2cbed31a136f5865f6cfa44203a324a3f4221bfab2b6fa0786a7048f3345ce344f1458e151ba187b59aab498cb02a3638259ba4ccc46fe79d8d79a4d9e704ec0f7701b5e664d4d8733838af49196431b02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f902d0b226c6599f273874df8fe684ab6c3028081bee8a2cbed31a136f5865f6cfa44202c12eb4ef8760321c072a51d8fb65c34ee8b452a14818557f61df061285a5809103a08e41b262942c6e5932fd1fb5d99236897989f6e912dc21476d2771874114930000
*** Base64 String:
cHNidP8BAFICAAAAASWJ53Z5WLoVT5AYzM8N7ephR7tgzRoZS241kKmWVpDWAQAAAAD9////ARjd9QUAAAAAFgAUyRI+BujX8JZsXRzQ+TMALU63V80AAAAAAAEBKwDh9QUAAAAAIlEg0LImxlmfJzh034/mhKtsMCgIG+6KLL7TGhNvWGX2z6QhFjRrmVkzVxB8nTRZ6d66jT6vROZjbIXH+FPrkLpS6M0ABQBYCwiHIRZPr9ZfgWkYb8K/2yIzx35jDRC+KAokxxZcCaJ2EXdcLAUAwySagiEWjdlquFiyWcUYIYwBSkbrTmrImeUcZ173dPu2ioeZzi8NACaA3W4BAAAAAgAAACEW+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvkFAH3WVZIBFyCN2Wq4WLJZxRghjAFKRutOasiZ5RxnXvd0+7aKh5nOLyIaAwtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUYwI0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAJPr9ZfgWkYb8K/2yIzx35jDRC+KAokxxZcCaJ2EXdcLAL5MIoBkljDEEk0T4X4nVIptTHIRYNvmbCGAfETvOA2+UMbAjRrmVkzVxB8nTRZ6d66jT6vROZjbIXH+FPrkLpS6M0AAtCyJsZZnyc4dN+P5oSrbDAoCBvuiiy+0xoTb1hl9s+kQgJO78n90SvnR0ZIXGeLgmiUnMkjbp/OgiQTlVI68EJivwOMJ26DKq1L+56QSFFi9XTIsmGd9b0Z24/6LrAFlJO/G0MbAk+v1l+BaRhvwr/bIjPHfmMNEL4oCiTHFlwJonYRd1wsAtCyJsZZnyc4dN+P5oSrbDAoCBvuiiy+0xoTb1hl9s+kQgOjJKP0Ihv6srb6B4anBI8zRc40TxRY4VG6GHtZqrSYywKjY4JZukzMRv552NeaTZ5wTsD3cBteZk1NhzODivSRlkMbAvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5AtCyJsZZnyc4dN+P5oSrbDAoCBvuiiy+0xoTb1hl9s+kQgLBLrTvh2AyHAcqUdj7ZcNO6LRSoUgYVX9h3wYShaWAkQOgjkGyYpQsblky/R+12ZI2iXmJ9ukS3CFHbSdxh0EUkwAA
** With all partial signatures *** Bytes in Hex:
70736274ff01005202000000012589e7767958ba154f9018cccf0dedea6147bb60cd1a194b6e3590a9965690d60100000000fdffffff0118ddf50500000000160014c9123e06e8d7f0966c5d1cd0f933002d4eb757cd000000000001012b00e1f50500000000225120d0b226c6599f273874df8fe684ab6c3028081bee8a2cbed31a136f5865f6cfa40113409e39897ac2ffe27525dc460f8584fddd11fe9a97ce2e50c1489b8c1a4e92fcc07e48db63a1a4ccb9d297537d0c038838378bbf278de7aa1a128995d1625cc5cd2116346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd000500580b088721164fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c0500c3249a8221168dd96ab858b259c518218c014a46eb4e6ac899e51c675ef774fbb68a8799ce2f0d002680dd6e01000000020000002116f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f905007dd655920117208dd96ab858b259c518218c014a46eb4e6ac899e51c675ef774fbb68a8799ce2f221a030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d46302346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9431b02346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd0002d0b226c6599f273874df8fe684ab6c3028081bee8a2cbed31a136f5865f6cfa442024eefc9fdd12be74746485c678b8268949cc9236e9fce82241395523af04262bf038c276e832aad4bfb9e90485162f574c8b2619df5bd19db8ffa2eb0059493bf1b431b024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02d0b226c6599f273874df8fe684ab6c3028081bee8a2cbed31a136f5865f6cfa44203a324a3f4221bfab2b6fa0786a7048f3345ce344f1458e151ba187b59aab498cb02a3638259ba4ccc46fe79d8d79a4d9e704ec0f7701b5e664d4d8733838af49196431b02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f902d0b226c6599f273874df8fe684ab6c3028081bee8a2cbed31a136f5865f6cfa44202c12eb4ef8760321c072a51d8fb65c34ee8b452a14818557f61df061285a5809103a08e41b262942c6e5932fd1fb5d99236897989f6e912dc21476d277187411493431c02346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd0002d0b226c6599f273874df8fe684ab6c3028081bee8a2cbed31a136f5865f6cfa420657db286be14e80ece0dd84b4d17c4dc414c3e56bc8cef0827b061b4dd2c8f43431c024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02d0b226c6599f273874df8fe684ab6c3028081bee8a2cbed31a136f5865f6cfa420e78552fb4ce9b2d00e1ed0e2cb98e087199127477e8f1a1c681a00b9c4ce7098431c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f902d0b226c6599f273874df8fe684ab6c3028081bee8a2cbed31a136f5865f6cfa420cbcc95786a1c674d48d8ac52e322dd7c6eabac3bfc4be79b750de28df82e2f730000
*** Base64 String:
cHNidP8BAFICAAAAASWJ53Z5WLoVT5AYzM8N7ephR7tgzRoZS241kKmWVpDWAQAAAAD9////ARjd9QUAAAAAFgAUyRI+BujX8JZsXRzQ+TMALU63V80AAAAAAAEBKwDh9QUAAAAAIlEg0LImxlmfJzh034/mhKtsMCgIG+6KLL7TGhNvWGX2z6QBE0CeOYl6wv/idSXcRg+FhP3dEf6al84uUMFIm4waTpL8wH5I22OhpMy50pdTfQwDiDg3i78njeeqGhKJldFiXMXNIRY0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAUAWAsIhyEWT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwFAMMkmoIhFo3ZarhYslnFGCGMAUpG605qyJnlHGde93T7toqHmc4vDQAmgN1uAQAAAAIAAAAhFvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5BQB91lWSARcgjdlquFiyWcUYIYwBSkbrTmrImeUcZ173dPu2ioeZzi8iGgMLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1GMCNGuZWTNXEHydNFnp3rqNPq9E5mNshcf4U+uQulLozQACT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwC+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvlDGwI0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAALQsibGWZ8nOHTfj+aEq2wwKAgb7oosvtMaE29YZfbPpEICTu/J/dEr50dGSFxni4JolJzJI26fzoIkE5VSOvBCYr8DjCdugyqtS/uekEhRYvV0yLJhnfW9GduP+i6wBZSTvxtDGwJPr9ZfgWkYb8K/2yIzx35jDRC+KAokxxZcCaJ2EXdcLALQsibGWZ8nOHTfj+aEq2wwKAgb7oosvtMaE29YZfbPpEIDoySj9CIb+rK2+geGpwSPM0XONE8UWOFRuhh7Waq0mMsCo2OCWbpMzEb+edjXmk2ecE7A93AbXmZNTYczg4r0kZZDGwL5MIoBkljDEEk0T4X4nVIptTHIRYNvmbCGAfETvOA2+QLQsibGWZ8nOHTfj+aEq2wwKAgb7oosvtMaE29YZfbPpEICwS6074dgMhwHKlHY+2XDTui0UqFIGFV/Yd8GEoWlgJEDoI5BsmKULG5ZMv0ftdmSNol5ifbpEtwhR20ncYdBFJNDHAI0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAALQsibGWZ8nOHTfj+aEq2wwKAgb7oosvtMaE29YZfbPpCBlfbKGvhToDs4N2EtNF8TcQUw+VryM7wgnsGG03SyPQ0McAk+v1l+BaRhvwr/bIjPHfmMNEL4oCiTHFlwJonYRd1wsAtCyJsZZnyc4dN+P5oSrbDAoCBvuiiy+0xoTb1hl9s+kIOeFUvtM6bLQDh7Q4suY4IcZkSdHfo8aHGgaALnEznCYQxwC+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvkC0LImxlmfJzh034/mhKtsMCgIG+6KLL7TGhNvWGX2z6Qgy8yVeGocZ01I2KxS4yLdfG6rrDv8S+ebdQ3ijfguL3MAAA==
* Case: Receiving a Taproot output where the internal key is a MuSig2 Aggregate Pubkey ** Bytes in Hex:
70736274ff01007d02000000012589e7767958ba154f9018cccf0dedea6147bb60cd1a194b6e3590a9965690d60000000000fdffffff0280969800000000002251202967d2d020a9795da72b51be4f3fca25bb0e57e91c5b3e7a81abfa7232a349420fc0927c00000000160014349c5d330278c3002a64f597d2b01aa3dc1bd903000000000001007d02000000019a8b4a50796b9600990f7fe11dfa00bc70efd296048afc86719af0fb1fa919370000000000fdffffff02895c2b7d00000000160014cfd98ba1027ea4ed4bd2ae1b348b6156a015037500e1f50500000000225120d0b226c6599f273874df8fe684ab6c3028081bee8a2cbed31a136f5865f6cfa4e100000001011f895c2b7d00000000160014cfd98ba1027ea4ed4bd2ae1b348b6156a0150375220602a66650f08bffa4f089eb22edcdbe7616645ff6cd180a36484d4bc81054595b7b18bfff44a3540000800100008000000080010000008a020000000105200b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d421070b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d405002680dd6e2107346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd000500580b088721074fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c0500c3249a822107f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f905007dd655922208030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d46302346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f900220203be4ae53d37cc075f40b30d6da4729d40adeeb983533af1616192bc76d5b2612a18bfff44a3540000800100008000000080010000008d02000000
** Base64 String:
cHNidP8BAH0CAAAAASWJ53Z5WLoVT5AYzM8N7ephR7tgzRoZS241kKmWVpDWAAAAAAD9////AoCWmAAAAAAAIlEgKWfS0CCpeV2nK1G+Tz/KJbsOV+kcWz56gav6cjKjSUIPwJJ8AAAAABYAFDScXTMCeMMAKmT1l9KwGqPcG9kDAAAAAAABAH0CAAAAAZqLSlB5a5YAmQ9/4R36ALxw79KWBIr8hnGa8PsfqRk3AAAAAAD9////AolcK30AAAAAFgAUz9mLoQJ+pO1L0q4bNIthVqAVA3UA4fUFAAAAACJRINCyJsZZnyc4dN+P5oSrbDAoCBvuiiy+0xoTb1hl9s+k4QAAAAEBH4lcK30AAAAAFgAUz9mLoQJ+pO1L0q4bNIthVqAVA3UiBgKmZlDwi/+k8InrIu3NvnYWZF/2zRgKNkhNS8gQVFlbexi//0SjVAAAgAEAAIAAAACAAQAAAIoCAAAAAQUgC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9QhBwtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUBQAmgN1uIQc0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAUAWAsIhyEHT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwFAMMkmoIhB/kwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5BQB91lWSIggDC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9RjAjRrmVkzVxB8nTRZ6d66jT6vROZjbIXH+FPrkLpS6M0AAk+v1l+BaRhvwr/bIjPHfmMNEL4oCiTHFlwJonYRd1wsAvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5ACICA75K5T03zAdfQLMNbaRynUCt7rmDUzrxYWGSvHbVsmEqGL//RKNUAACAAQAAgAAAAIABAAAAjQIAAAA=
* Case: Receiving a Taproot output where the internal key is derived from a MuSig2 Aggregate Pubkey ** Bytes in Hex:
70736274ff01007d0200000001f835a5ec8e4008f96f17407e13f0c34912c39d27620800fae02baf86b8a78e760000000000fdffffff028096980000000000225120d0b226c6599f273874df8fe684ab6c3028081bee8a2cbed31a136f5865f6cfa49e405d05000000001600149f94ac2db46420b95dc0db1cc8f4bec0bb9234d8000000000001005202000000015686dff400165f4e040a5855f658093472c9bcf8108b272a5d31f181f7b4ffb10100000000fdffffff0118ddf50500000000160014c9123e06e8d7f0966c5d1cd0f933002d4eb757cd0000000001011f18ddf50500000000160014c9123e06e8d7f0966c5d1cd0f933002d4eb757cd220603293c8d8dc47b712d7c13a5d0536b7f2e3193267e60f7e66e563939dbe507479c18bfff44a35400008001000080000000800000000097010000000105208dd96ab858b259c518218c014a46eb4e6ac899e51c675ef774fbb68a8799ce2f2107346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd000500580b088721074fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c0500c3249a8221078dd96ab858b259c518218c014a46eb4e6ac899e51c675ef774fbb68a8799ce2f0d002680dd6e01000000020000002107f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f905007dd655922208030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d46302346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f900220202ce69de967622b1c82eb0a0f80ceb0573a0f768b02fdb047b13c171e79174fcce18bfff44a3540000800100008000000080010000008e02000000
** Base64 String:
cHNidP8BAH0CAAAAAfg1peyOQAj5bxdAfhPww0kSw50nYggA+uArr4a4p452AAAAAAD9////AoCWmAAAAAAAIlEg0LImxlmfJzh034/mhKtsMCgIG+6KLL7TGhNvWGX2z6SeQF0FAAAAABYAFJ+UrC20ZCC5XcDbHMj0vsC7kjTYAAAAAAABAFICAAAAAVaG3/QAFl9OBApYVfZYCTRyybz4EIsnKl0x8YH3tP+xAQAAAAD9////ARjd9QUAAAAAFgAUyRI+BujX8JZsXRzQ+TMALU63V80AAAAAAQEfGN31BQAAAAAWABTJEj4G6NfwlmxdHND5MwAtTrdXzSIGAyk8jY3Ee3EtfBOl0FNrfy4xkyZ+YPfmblY5OdvlB0ecGL//RKNUAACAAQAAgAAAAIAAAAAAlwEAAAABBSCN2Wq4WLJZxRghjAFKRutOasiZ5RxnXvd0+7aKh5nOLyEHNGuZWTNXEHydNFnp3rqNPq9E5mNshcf4U+uQulLozQAFAFgLCIchB0+v1l+BaRhvwr/bIjPHfmMNEL4oCiTHFlwJonYRd1wsBQDDJJqCIQeN2Wq4WLJZxRghjAFKRutOasiZ5RxnXvd0+7aKh5nOLw0AJoDdbgEAAAACAAAAIQf5MIoBkljDEEk0T4X4nVIptTHIRYNvmbCGAfETvOA2+QUAfdZVkiIIAwtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUYwI0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAJPr9ZfgWkYb8K/2yIzx35jDRC+KAokxxZcCaJ2EXdcLAL5MIoBkljDEEk0T4X4nVIptTHIRYNvmbCGAfETvOA2+QAiAgLOad6WdiKxyC6woPgM6wVzoPdosC/bBHsTwXHnkXT8zhi//0SjVAAAgAEAAIAAAACAAQAAAI4CAAAA
The following are invalid PSBTs * Case: PSBT with x-only aggregate pubkey in input participant pubkeys keydata ** Bytes in Hex:
70736274ff01005202000000015686dff400165f4e040a5855f658093472c9bcf8108b272a5d31f181f7b4ffb10100000000fdffffff0118ddf50500000000160014c9123e06e8d7f0966c5d1cd0f933002d4eb757cd000000000001012b00e1f505000000002251200b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d421160b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d405002680dd6e2116346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd000500580b088721164fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c0500c3249a822116f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f905007dd65592211a0b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d46302346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f90000
** Base64 String:
cHNidP8BAFICAAAAAVaG3/QAFl9OBApYVfZYCTRyybz4EIsnKl0x8YH3tP+xAQAAAAD9////ARjd9QUAAAAAFgAUyRI+BujX8JZsXRzQ+TMALU63V80AAAAAAAEBKwDh9QUAAAAAIlEgC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9QhFgtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUBQAmgN1uIRY0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAUAWAsIhyEWT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwFAMMkmoIhFvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5BQB91lWSIRoLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1GMCNGuZWTNXEHydNFnp3rqNPq9E5mNshcf4U+uQulLozQACT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwC+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvkAAA==
* Case: PSBT with an x-only input participant pubkey ** Bytes in Hex:
70736274ff01005202000000015686dff400165f4e040a5855f658093472c9bcf8108b272a5d31f181f7b4ffb10100000000fdffffff0118ddf50500000000160014c9123e06e8d7f0966c5d1cd0f933002d4eb757cd000000000001012b00e1f505000000002251200b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d421160b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d405002680dd6e2116346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd000500580b088721164fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c0500c3249a822116f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f905007dd65592221a030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d462346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f90000
** Base64 String:
cHNidP8BAFICAAAAAVaG3/QAFl9OBApYVfZYCTRyybz4EIsnKl0x8YH3tP+xAQAAAAD9////ARjd9QUAAAAAFgAUyRI+BujX8JZsXRzQ+TMALU63V80AAAAAAAEBKwDh9QUAAAAAIlEgC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9QhFgtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUBQAmgN1uIRY0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAUAWAsIhyEWT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwFAMMkmoIhFvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5BQB91lWSIhoDC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9RiNGuZWTNXEHydNFnp3rqNPq9E5mNshcf4U+uQulLozQACT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwC+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvkAAA==
* Case: PSBT with x-only aggregate pubkey in output participant pubkeys keydata ** Bytes in Hex:
70736274ff01007d02000000012589e7767958ba154f9018cccf0dedea6147bb60cd1a194b6e3590a9965690d60000000000fdffffff0280969800000000002251202967d2d020a9795da72b51be4f3fca25bb0e57e91c5b3e7a81abfa7232a349420fc0927c00000000160014349c5d330278c3002a64f597d2b01aa3dc1bd903000000000001007d02000000019a8b4a50796b9600990f7fe11dfa00bc70efd296048afc86719af0fb1fa919370000000000fdffffff02895c2b7d00000000160014cfd98ba1027ea4ed4bd2ae1b348b6156a015037500e1f50500000000225120d0b226c6599f273874df8fe684ab6c3028081bee8a2cbed31a136f5865f6cfa4e100000001011f895c2b7d00000000160014cfd98ba1027ea4ed4bd2ae1b348b6156a0150375220602a66650f08bffa4f089eb22edcdbe7616645ff6cd180a36484d4bc81054595b7b18bfff44a3540000800100008000000080010000008a020000000105200b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d421070b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d405002680dd6e2107346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd000500580b088721074fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c0500c3249a822107f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f905007dd6559221080b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d46302346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f900220203be4ae53d37cc075f40b30d6da4729d40adeeb983533af1616192bc76d5b2612a18bfff44a3540000800100008000000080010000008d02000000
** Base64 String:
cHNidP8BAH0CAAAAASWJ53Z5WLoVT5AYzM8N7ephR7tgzRoZS241kKmWVpDWAAAAAAD9////AoCWmAAAAAAAIlEgKWfS0CCpeV2nK1G+Tz/KJbsOV+kcWz56gav6cjKjSUIPwJJ8AAAAABYAFDScXTMCeMMAKmT1l9KwGqPcG9kDAAAAAAABAH0CAAAAAZqLSlB5a5YAmQ9/4R36ALxw79KWBIr8hnGa8PsfqRk3AAAAAAD9////AolcK30AAAAAFgAUz9mLoQJ+pO1L0q4bNIthVqAVA3UA4fUFAAAAACJRINCyJsZZnyc4dN+P5oSrbDAoCBvuiiy+0xoTb1hl9s+k4QAAAAEBH4lcK30AAAAAFgAUz9mLoQJ+pO1L0q4bNIthVqAVA3UiBgKmZlDwi/+k8InrIu3NvnYWZF/2zRgKNkhNS8gQVFlbexi//0SjVAAAgAEAAIAAAACAAQAAAIoCAAAAAQUgC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9QhBwtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUBQAmgN1uIQc0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAUAWAsIhyEHT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwFAMMkmoIhB/kwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5BQB91lWSIQgLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1GMCNGuZWTNXEHydNFnp3rqNPq9E5mNshcf4U+uQulLozQACT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwC+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvkAIgIDvkrlPTfMB19Asw1tpHKdQK3uuYNTOvFhYZK8dtWyYSoYv/9Eo1QAAIABAACAAAAAgAEAAACNAgAAAA==
* Case: PSBT with an x-only output participant pubkey ** Bytes in Hex:
70736274ff01007d02000000012589e7767958ba154f9018cccf0dedea6147bb60cd1a194b6e3590a9965690d60000000000fdffffff0280969800000000002251202967d2d020a9795da72b51be4f3fca25bb0e57e91c5b3e7a81abfa7232a349420fc0927c00000000160014349c5d330278c3002a64f597d2b01aa3dc1bd903000000000001007d02000000019a8b4a50796b9600990f7fe11dfa00bc70efd296048afc86719af0fb1fa919370000000000fdffffff02895c2b7d00000000160014cfd98ba1027ea4ed4bd2ae1b348b6156a015037500e1f50500000000225120d0b226c6599f273874df8fe684ab6c3028081bee8a2cbed31a136f5865f6cfa4e100000001011f895c2b7d00000000160014cfd98ba1027ea4ed4bd2ae1b348b6156a0150375220602a66650f08bffa4f089eb22edcdbe7616645ff6cd180a36484d4bc81054595b7b18bfff44a3540000800100008000000080010000008a020000000105200b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d421070b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d405002680dd6e2107346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd000500580b088721074fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c0500c3249a822107f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f905007dd6559221080b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d46302346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f900220203be4ae53d37cc075f40b30d6da4729d40adeeb983533af1616192bc76d5b2612a18bfff44a3540000800100008000000080010000008d02000000
** Base64 String:
cHNidP8BAH0CAAAAASWJ53Z5WLoVT5AYzM8N7ephR7tgzRoZS241kKmWVpDWAAAAAAD9////AoCWmAAAAAAAIlEgKWfS0CCpeV2nK1G+Tz/KJbsOV+kcWz56gav6cjKjSUIPwJJ8AAAAABYAFDScXTMCeMMAKmT1l9KwGqPcG9kDAAAAAAABAH0CAAAAAZqLSlB5a5YAmQ9/4R36ALxw79KWBIr8hnGa8PsfqRk3AAAAAAD9////AolcK30AAAAAFgAUz9mLoQJ+pO1L0q4bNIthVqAVA3UA4fUFAAAAACJRINCyJsZZnyc4dN+P5oSrbDAoCBvuiiy+0xoTb1hl9s+k4QAAAAEBH4lcK30AAAAAFgAUz9mLoQJ+pO1L0q4bNIthVqAVA3UiBgKmZlDwi/+k8InrIu3NvnYWZF/2zRgKNkhNS8gQVFlbexi//0SjVAAAgAEAAIAAAACAAQAAAIoCAAAAAQUgC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9QhBwtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUBQAmgN1uIQc0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAUAWAsIhyEHT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwFAMMkmoIhB/kwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5BQB91lWSIQgLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1GMCNGuZWTNXEHydNFnp3rqNPq9E5mNshcf4U+uQulLozQACT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwC+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvkAIgIDvkrlPTfMB19Asw1tpHKdQK3uuYNTOvFhYZK8dtWyYSoYv/9Eo1QAAIABAACAAAAAgAEAAACNAgAAAA==
* Case: PSBT with x-only aggregate pubkey in public nonce keydata ** Bytes in Hex:
70736274ff01005202000000015686dff400165f4e040a5855f658093472c9bcf8108b272a5d31f181f7b4ffb10100000000fdffffff0118ddf50500000000160014c9123e06e8d7f0966c5d1cd0f933002d4eb757cd000000000001012b00e1f505000000002251200b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d421160b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d405002680dd6e2116346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd000500580b088721164fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c0500c3249a822116f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f905007dd65592221a030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d46302346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9421b02346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd000b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d44202529b19d7879ccc04c915487f5f1341bc6858b0bc74e5036c643d37b53a4371b503b7f8afe3263fcb3ef2454fe16f3a6759c5600c78e637b8dfa0d83e8552882056431b024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d44203a81d973499e74f82d2b5ab13f1e69e9e11a5fdb40f5466ef672e6e4ceba0be7903499593767150394eece384d051c45b615c52dbe1c8eb3610d7b344b43b7dad6d431b02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d442033949dbff31b9d50251d8821e66cc5c97b7e3afd7d95bfdc77500fda8947f3ae0023f20e4f0bf0b76f0d40cd3abfe7ce373d6685bbd77b5fa28e7f49fb429d189b00000
** Base64 String:
cHNidP8BAFICAAAAAVaG3/QAFl9OBApYVfZYCTRyybz4EIsnKl0x8YH3tP+xAQAAAAD9////ARjd9QUAAAAAFgAUyRI+BujX8JZsXRzQ+TMALU63V80AAAAAAAEBKwDh9QUAAAAAIlEgC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9QhFgtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUBQAmgN1uIRY0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAUAWAsIhyEWT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwFAMMkmoIhFvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5BQB91lWSIhoDC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9RjAjRrmVkzVxB8nTRZ6d66jT6vROZjbIXH+FPrkLpS6M0AAk+v1l+BaRhvwr/bIjPHfmMNEL4oCiTHFlwJonYRd1wsAvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5QhsCNGuZWTNXEHydNFnp3rqNPq9E5mNshcf4U+uQulLozQALWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1EICUpsZ14eczATJFUh/XxNBvGhYsLx05QNsZD03tTpDcbUDt/iv4yY/yz7yRU/hbzpnWcVgDHjmN7jfoNg+hVKIIFZDGwJPr9ZfgWkYb8K/2yIzx35jDRC+KAokxxZcCaJ2EXdcLAMLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1EIDqB2XNJnnT4LStasT8eaenhGl/bQPVGbvZy5uTOugvnkDSZWTdnFQOU7s44TQUcRbYVxS2+HI6zYQ17NEtDt9rW1DGwL5MIoBkljDEEk0T4X4nVIptTHIRYNvmbCGAfETvOA2+QMLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1EIDOUnb/zG51QJR2IIeZsxcl7fjr9fZW/3HdQD9qJR/OuACPyDk8L8LdvDUDNOr/nzjc9ZoW713tfoo5/SftCnRibAAAA==
* Case: PSBT with an x-only participant pubkey in public nonce keydata ** Bytes in Hex:
70736274ff01005202000000015686dff400165f4e040a5855f658093472c9bcf8108b272a5d31f181f7b4ffb10100000000fdffffff0118ddf50500000000160014c9123e06e8d7f0966c5d1cd0f933002d4eb757cd000000000001012b00e1f505000000002251200b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d421160b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d405002680dd6e2116346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd000500580b088721164fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c0500c3249a822116f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f905007dd65592221a030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d46302346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9421b346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d44202529b19d7879ccc04c915487f5f1341bc6858b0bc74e5036c643d37b53a4371b503b7f8afe3263fcb3ef2454fe16f3a6759c5600c78e637b8dfa0d83e8552882056431b024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d44203a81d973499e74f82d2b5ab13f1e69e9e11a5fdb40f5466ef672e6e4ceba0be7903499593767150394eece384d051c45b615c52dbe1c8eb3610d7b344b43b7dad6d431b02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d442033949dbff31b9d50251d8821e66cc5c97b7e3afd7d95bfdc77500fda8947f3ae0023f20e4f0bf0b76f0d40cd3abfe7ce373d6685bbd77b5fa28e7f49fb429d189b00000
** Base64 String:
cHNidP8BAFICAAAAAVaG3/QAFl9OBApYVfZYCTRyybz4EIsnKl0x8YH3tP+xAQAAAAD9////ARjd9QUAAAAAFgAUyRI+BujX8JZsXRzQ+TMALU63V80AAAAAAAEBKwDh9QUAAAAAIlEgC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9QhFgtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUBQAmgN1uIRY0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAUAWAsIhyEWT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwFAMMkmoIhFvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5BQB91lWSIhoDC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9RjAjRrmVkzVxB8nTRZ6d66jT6vROZjbIXH+FPrkLpS6M0AAk+v1l+BaRhvwr/bIjPHfmMNEL4oCiTHFlwJonYRd1wsAvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5Qhs0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAMLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1EICUpsZ14eczATJFUh/XxNBvGhYsLx05QNsZD03tTpDcbUDt/iv4yY/yz7yRU/hbzpnWcVgDHjmN7jfoNg+hVKIIFZDGwJPr9ZfgWkYb8K/2yIzx35jDRC+KAokxxZcCaJ2EXdcLAMLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1EIDqB2XNJnnT4LStasT8eaenhGl/bQPVGbvZy5uTOugvnkDSZWTdnFQOU7s44TQUcRbYVxS2+HI6zYQ17NEtDt9rW1DGwL5MIoBkljDEEk0T4X4nVIptTHIRYNvmbCGAfETvOA2+QMLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1EIDOUnb/zG51QJR2IIeZsxcl7fjr9fZW/3HdQD9qJR/OuACPyDk8L8LdvDUDNOr/nzjc9ZoW713tfoo5/SftCnRibAAAA==
* Case: PSBT with invalid public nonce valuedata length ** Bytes in Hex:
70736274ff01005202000000015686dff400165f4e040a5855f658093472c9bcf8108b272a5d31f181f7b4ffb10100000000fdffffff0118ddf50500000000160014c9123e06e8d7f0966c5d1cd0f933002d4eb757cd000000000001012b00e1f505000000002251200b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d421160b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d405002680dd6e2116346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd000500580b088721164fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c0500c3249a822116f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f905007dd65592221a030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d46302346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9431b02346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d44102529b19d7879ccc04c915487f5f1341bc6858b0bc74e5036c643d37b53a4371b503b7f8afe3263fcb3ef2454fe16f3a6759c5600c78e637b8dfa0d83e85528820431b024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d44203a81d973499e74f82d2b5ab13f1e69e9e11a5fdb40f5466ef672e6e4ceba0be7903499593767150394eece384d051c45b615c52dbe1c8eb3610d7b344b43b7dad6d431b02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d442033949dbff31b9d50251d8821e66cc5c97b7e3afd7d95bfdc77500fda8947f3ae0023f20e4f0bf0b76f0d40cd3abfe7ce373d6685bbd77b5fa28e7f49fb429d189b00000
** Base64 String:
cHNidP8BAFICAAAAAVaG3/QAFl9OBApYVfZYCTRyybz4EIsnKl0x8YH3tP+xAQAAAAD9////ARjd9QUAAAAAFgAUyRI+BujX8JZsXRzQ+TMALU63V80AAAAAAAEBKwDh9QUAAAAAIlEgC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9QhFgtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUBQAmgN1uIRY0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAUAWAsIhyEWT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwFAMMkmoIhFvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5BQB91lWSIhoDC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9RjAjRrmVkzVxB8nTRZ6d66jT6vROZjbIXH+FPrkLpS6M0AAk+v1l+BaRhvwr/bIjPHfmMNEL4oCiTHFlwJonYRd1wsAvkwigGSWMMQSTRPhfidUim1MchFg2+ZsIYB8RO84Db5QxsCNGuZWTNXEHydNFnp3rqNPq9E5mNshcf4U+uQulLozQADC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9RBAlKbGdeHnMwEyRVIf18TQbxoWLC8dOUDbGQ9N7U6Q3G1A7f4r+MmP8s+8kVP4W86Z1nFYAx45je436DYPoVSiCBDGwJPr9ZfgWkYb8K/2yIzx35jDRC+KAokxxZcCaJ2EXdcLAMLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1EIDqB2XNJnnT4LStasT8eaenhGl/bQPVGbvZy5uTOugvnkDSZWTdnFQOU7s44TQUcRbYVxS2+HI6zYQ17NEtDt9rW1DGwL5MIoBkljDEEk0T4X4nVIptTHIRYNvmbCGAfETvOA2+QMLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1EIDOUnb/zG51QJR2IIeZsxcl7fjr9fZW/3HdQD9qJR/OuACPyDk8L8LdvDUDNOr/nzjc9ZoW713tfoo5/SftCnRibAAAA==
* Case: PSBT with x-only aggregate pubkey in partial sig keydata ** Bytes in Hex:
70736274ff01005202000000019a8b4a50796b9600990f7fe11dfa00bc70efd296048afc86719af0fb1fa919370100000000fdffffff0118ddf50500000000160014c9123e06e8d7f0966c5d1cd0f933002d4eb757cd000000000001012b00e1f5050000000022512056bdb481b4d67103f6d5dea8a9aafd3684a6a79b4a2e247799db8d4b1a86e1f841140b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c402667d52f6cc07fe06db31b1a5f7efe81903f9cbeef40fa64dafca01d2cb1d56403bc7504898e55872557d16d2ca79bc55fef10973841a33ec032d884758c9fe62215c050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac023200b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4acc021160b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d42501b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c2680dd6e2116346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd002501b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c580b088721164fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c2501b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2cc3249a82211650929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac005007c461e5d2116f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f92501b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c7dd6559201172050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac0011820b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c221a030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d46302346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9631b02346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c4202d99e7c8719b3ad08566b0cb9c7d5eda3127c9e8119185b7d584d939b173915f50240df22aab78332cf0f25329d103dc0d2060a03742e9448026e736bcf3db98f3c631b024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c4202e702a7075226a0d9313a77e6db10b8e742d4cffdc948a0edc9b856c13b412e5403386a0298f308fb3099155772e45b2aa8e770f435bedfe2041d1cc4d3d37538c6631b02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c4202b1d912d45d753ceed0954417ba982656d2aec53f8638bd6f297dae3b743d71b0032f424537d599d28f14d59fe0a11b82fea2aa226a2980ffdacad5fdab20f80683621c02346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd000b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c20ada78b70af8cffa4c50863aef515ac58a327cd58c55bad29a162e67d9c413322631c024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c201fa8b7e6741c21eb8d9b0f65269df9e423369fc390ad2e918420c57feb2a1b61631c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c20366c31ad65e533f6d2b45e5910f3f587543f8061918167bf5a818b13be5792a40000
** Base64 String:
cHNidP8BAFICAAAAAZqLSlB5a5YAmQ9/4R36ALxw79KWBIr8hnGa8PsfqRk3AQAAAAD9////ARjd9QUAAAAAFgAUyRI+BujX8JZsXRzQ+TMALU63V80AAAAAAAEBKwDh9QUAAAAAIlEgVr20gbTWcQP21d6oqar9NoSmp5tKLiR3mduNSxqG4fhBFAtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+ixAJmfVL2zAf+BtsxsaX37+gZA/nL7vQPpk2vygHSyx1WQDvHUEiY5VhyVX0W0sp5vFX+8QlzhBoz7AMtiEdYyf5iIVwFCSm3TBoElUt4tLYDXpel4HiloPKOyW1Ue/7prOgDrAIyALWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1KzAIRYLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1CUBsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+iwmgN1uIRY0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNACUBsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+ixYCwiHIRZPr9ZfgWkYb8K/2yIzx35jDRC+KAokxxZcCaJ2EXdcLCUBsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+izDJJqCIRZQkpt0waBJVLeLS2A16XpeB4paDyjsltVHv+6azoA6wAUAfEYeXSEW+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvklAbEf7apjoJVlAacwjJO1Y3Nx52E9m4reF4PUnibAbPosfdZVkgEXIFCSm3TBoElUt4tLYDXpel4HiloPKOyW1Ue/7prOgDrAARggsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+iwiGgMLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1GMCNGuZWTNXEHydNFnp3rqNPq9E5mNshcf4U+uQulLozQACT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwC+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvljGwI0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAMLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1LEf7apjoJVlAacwjJO1Y3Nx52E9m4reF4PUnibAbPosQgLZnnyHGbOtCFZrDLnH1e2jEnyegRkYW31YTZObFzkV9QJA3yKqt4Myzw8lMp0QPcDSBgoDdC6USAJuc2vPPbmPPGMbAk+v1l+BaRhvwr/bIjPHfmMNEL4oCiTHFlwJonYRd1wsAwtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+ixCAucCpwdSJqDZMTp35tsQuOdC1M/9yUig7cm4VsE7QS5UAzhqApjzCPswmRVXcuRbKqjncPQ1vt/iBB0cxNPTdTjGYxsC+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvkDC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9SxH+2qY6CVZQGnMIyTtWNzcedhPZuK3heD1J4mwGz6LEICsdkS1F11PO7QlUQXupgmVtKuxT+GOL1vKX2uO3Q9cbADL0JFN9WZ0o8U1Z/goRuC/qKqImopgP/aytX9qyD4BoNiHAI0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+iwgraeLcK+M/6TFCGOu9RWsWKMnzVjFW60poWLmfZxBMyJjHAJPr9ZfgWkYb8K/2yIzx35jDRC+KAokxxZcCaJ2EXdcLAMLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1LEf7apjoJVlAacwjJO1Y3Nx52E9m4reF4PUnibAbPosIB+ot+Z0HCHrjZsPZSad+eQjNp/DkK0ukYQgxX/rKhthYxwC+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvkDC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9SxH+2qY6CVZQGnMIyTtWNzcedhPZuK3heD1J4mwGz6LCA2bDGtZeUz9tK0XlkQ8/WHVD+AYZGBZ79agYsTvleSpAAA
* Case: PSBT with an x-only participant pubkey in partial sig keydata ** Bytes in Hex:
70736274ff01005202000000019a8b4a50796b9600990f7fe11dfa00bc70efd296048afc86719af0fb1fa919370100000000fdffffff0118ddf50500000000160014c9123e06e8d7f0966c5d1cd0f933002d4eb757cd000000000001012b00e1f5050000000022512056bdb481b4d67103f6d5dea8a9aafd3684a6a79b4a2e247799db8d4b1a86e1f841140b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c402667d52f6cc07fe06db31b1a5f7efe81903f9cbeef40fa64dafca01d2cb1d56403bc7504898e55872557d16d2ca79bc55fef10973841a33ec032d884758c9fe62215c050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac023200b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4acc021160b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d42501b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c2680dd6e2116346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd002501b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c580b088721164fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c2501b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2cc3249a82211650929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac005007c461e5d2116f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f92501b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c7dd6559201172050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac0011820b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c221a030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d46302346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9631b02346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c4202d99e7c8719b3ad08566b0cb9c7d5eda3127c9e8119185b7d584d939b173915f50240df22aab78332cf0f25329d103dc0d2060a03742e9448026e736bcf3db98f3c631b024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c4202e702a7075226a0d9313a77e6db10b8e742d4cffdc948a0edc9b856c13b412e5403386a0298f308fb3099155772e45b2aa8e770f435bedfe2041d1cc4d3d37538c6631b02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c4202b1d912d45d753ceed0954417ba982656d2aec53f8638bd6f297dae3b743d71b0032f424537d599d28f14d59fe0a11b82fea2aa226a2980ffdacad5fdab20f80683621c346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c20ada78b70af8cffa4c50863aef515ac58a327cd58c55bad29a162e67d9c413322631c024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c201fa8b7e6741c21eb8d9b0f65269df9e423369fc390ad2e918420c57feb2a1b61631c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c20366c31ad65e533f6d2b45e5910f3f587543f8061918167bf5a818b13be5792a40000
** Base64 String:
cHNidP8BAFICAAAAAZqLSlB5a5YAmQ9/4R36ALxw79KWBIr8hnGa8PsfqRk3AQAAAAD9////ARjd9QUAAAAAFgAUyRI+BujX8JZsXRzQ+TMALU63V80AAAAAAAEBKwDh9QUAAAAAIlEgVr20gbTWcQP21d6oqar9NoSmp5tKLiR3mduNSxqG4fhBFAtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+ixAJmfVL2zAf+BtsxsaX37+gZA/nL7vQPpk2vygHSyx1WQDvHUEiY5VhyVX0W0sp5vFX+8QlzhBoz7AMtiEdYyf5iIVwFCSm3TBoElUt4tLYDXpel4HiloPKOyW1Ue/7prOgDrAIyALWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1KzAIRYLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1CUBsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+iwmgN1uIRY0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNACUBsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+ixYCwiHIRZPr9ZfgWkYb8K/2yIzx35jDRC+KAokxxZcCaJ2EXdcLCUBsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+izDJJqCIRZQkpt0waBJVLeLS2A16XpeB4paDyjsltVHv+6azoA6wAUAfEYeXSEW+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvklAbEf7apjoJVlAacwjJO1Y3Nx52E9m4reF4PUnibAbPosfdZVkgEXIFCSm3TBoElUt4tLYDXpel4HiloPKOyW1Ue/7prOgDrAARggsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+iwiGgMLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1GMCNGuZWTNXEHydNFnp3rqNPq9E5mNshcf4U+uQulLozQACT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwC+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvljGwI0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAMLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1LEf7apjoJVlAacwjJO1Y3Nx52E9m4reF4PUnibAbPosQgLZnnyHGbOtCFZrDLnH1e2jEnyegRkYW31YTZObFzkV9QJA3yKqt4Myzw8lMp0QPcDSBgoDdC6USAJuc2vPPbmPPGMbAk+v1l+BaRhvwr/bIjPHfmMNEL4oCiTHFlwJonYRd1wsAwtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+ixCAucCpwdSJqDZMTp35tsQuOdC1M/9yUig7cm4VsE7QS5UAzhqApjzCPswmRVXcuRbKqjncPQ1vt/iBB0cxNPTdTjGYxsC+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvkDC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9SxH+2qY6CVZQGnMIyTtWNzcedhPZuK3heD1J4mwGz6LEICsdkS1F11PO7QlUQXupgmVtKuxT+GOL1vKX2uO3Q9cbADL0JFN9WZ0o8U1Z/goRuC/qKqImopgP/aytX9qyD4BoNiHDRrmVkzVxB8nTRZ6d66jT6vROZjbIXH+FPrkLpS6M0AAwtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+iwgraeLcK+M/6TFCGOu9RWsWKMnzVjFW60poWLmfZxBMyJjHAJPr9ZfgWkYb8K/2yIzx35jDRC+KAokxxZcCaJ2EXdcLAMLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1LEf7apjoJVlAacwjJO1Y3Nx52E9m4reF4PUnibAbPosIB+ot+Z0HCHrjZsPZSad+eQjNp/DkK0ukYQgxX/rKhthYxwC+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvkDC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9SxH+2qY6CVZQGnMIyTtWNzcedhPZuK3heD1J4mwGz6LCA2bDGtZeUz9tK0XlkQ8/WHVD+AYZGBZ79agYsTvleSpAAA
* Case: PSBT with invalid partial sig valuedata length ** Bytes in Hex:
70736274ff01005202000000019a8b4a50796b9600990f7fe11dfa00bc70efd296048afc86719af0fb1fa919370100000000fdffffff0118ddf50500000000160014c9123e06e8d7f0966c5d1cd0f933002d4eb757cd000000000001012b00e1f5050000000022512056bdb481b4d67103f6d5dea8a9aafd3684a6a79b4a2e247799db8d4b1a86e1f841140b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c402667d52f6cc07fe06db31b1a5f7efe81903f9cbeef40fa64dafca01d2cb1d56403bc7504898e55872557d16d2ca79bc55fef10973841a33ec032d884758c9fe62215c050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac023200b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4acc021160b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d42501b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c2680dd6e2116346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd002501b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c580b088721164fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c2501b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2cc3249a82211650929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac005007c461e5d2116f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f92501b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c7dd6559201172050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac0011820b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c221a030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d46302346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9631b02346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c4202d99e7c8719b3ad08566b0cb9c7d5eda3127c9e8119185b7d584d939b173915f50240df22aab78332cf0f25329d103dc0d2060a03742e9448026e736bcf3db98f3c631b024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c4202e702a7075226a0d9313a77e6db10b8e742d4cffdc948a0edc9b856c13b412e5403386a0298f308fb3099155772e45b2aa8e770f435bedfe2041d1cc4d3d37538c6631b02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c4202b1d912d45d753ceed0954417ba982656d2aec53f8638bd6f297dae3b743d71b0032f424537d599d28f14d59fe0a11b82fea2aa226a2980ffdacad5fdab20f80683631c02346b99593357107c9d3459e9deba8d3eaf44e6636c85c7f853eb90ba52e8cd00030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c1fa78b70af8cffa4c50863aef515ac58a327cd58c55bad29a162e67d9c413322631c024fafd65f8169186fc2bfdb2233c77e630d10be280a24c7165c09a27611775c2c030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c201fa8b7e6741c21eb8d9b0f65269df9e423369fc390ad2e918420c57feb2a1b61631c02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9030b58e337aa4d3852a8c29387c42408d8cfbe3a613a5e397e0a9f01a5fb7107d4b11fedaa63a0956501a7308c93b5637371e7613d9b8ade1783d49e26c06cfa2c20366c31ad65e533f6d2b45e5910f3f587543f8061918167bf5a818b13be5792a40000
** Base64 String:
cHNidP8BAFICAAAAAZqLSlB5a5YAmQ9/4R36ALxw79KWBIr8hnGa8PsfqRk3AQAAAAD9////ARjd9QUAAAAAFgAUyRI+BujX8JZsXRzQ+TMALU63V80AAAAAAAEBKwDh9QUAAAAAIlEgVr20gbTWcQP21d6oqar9NoSmp5tKLiR3mduNSxqG4fhBFAtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+ixAJmfVL2zAf+BtsxsaX37+gZA/nL7vQPpk2vygHSyx1WQDvHUEiY5VhyVX0W0sp5vFX+8QlzhBoz7AMtiEdYyf5iIVwFCSm3TBoElUt4tLYDXpel4HiloPKOyW1Ue/7prOgDrAIyALWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1KzAIRYLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1CUBsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+iwmgN1uIRY0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNACUBsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+ixYCwiHIRZPr9ZfgWkYb8K/2yIzx35jDRC+KAokxxZcCaJ2EXdcLCUBsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+izDJJqCIRZQkpt0waBJVLeLS2A16XpeB4paDyjsltVHv+6azoA6wAUAfEYeXSEW+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvklAbEf7apjoJVlAacwjJO1Y3Nx52E9m4reF4PUnibAbPosfdZVkgEXIFCSm3TBoElUt4tLYDXpel4HiloPKOyW1Ue/7prOgDrAARggsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+iwiGgMLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1GMCNGuZWTNXEHydNFnp3rqNPq9E5mNshcf4U+uQulLozQACT6/WX4FpGG/Cv9siM8d+Yw0QvigKJMcWXAmidhF3XCwC+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvljGwI0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAMLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1LEf7apjoJVlAacwjJO1Y3Nx52E9m4reF4PUnibAbPosQgLZnnyHGbOtCFZrDLnH1e2jEnyegRkYW31YTZObFzkV9QJA3yKqt4Myzw8lMp0QPcDSBgoDdC6USAJuc2vPPbmPPGMbAk+v1l+BaRhvwr/bIjPHfmMNEL4oCiTHFlwJonYRd1wsAwtY4zeqTThSqMKTh8QkCNjPvjphOl45fgqfAaX7cQfUsR/tqmOglWUBpzCMk7Vjc3HnYT2bit4Xg9SeJsBs+ixCAucCpwdSJqDZMTp35tsQuOdC1M/9yUig7cm4VsE7QS5UAzhqApjzCPswmRVXcuRbKqjncPQ1vt/iBB0cxNPTdTjGYxsC+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvkDC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9SxH+2qY6CVZQGnMIyTtWNzcedhPZuK3heD1J4mwGz6LEICsdkS1F11PO7QlUQXupgmVtKuxT+GOL1vKX2uO3Q9cbADL0JFN9WZ0o8U1Z/goRuC/qKqImopgP/aytX9qyD4BoNjHAI0a5lZM1cQfJ00Weneuo0+r0TmY2yFx/hT65C6UujNAAMLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1LEf7apjoJVlAacwjJO1Y3Nx52E9m4reF4PUnibAbPosH6eLcK+M/6TFCGOu9RWsWKMnzVjFW60poWLmfZxBMyJjHAJPr9ZfgWkYb8K/2yIzx35jDRC+KAokxxZcCaJ2EXdcLAMLWOM3qk04UqjCk4fEJAjYz746YTpeOX4KnwGl+3EH1LEf7apjoJVlAacwjJO1Y3Nx52E9m4reF4PUnibAbPosIB+ot+Z0HCHrjZsPZSad+eQjNp/DkK0ukYQgxX/rKhthYxwC+TCKAZJYwxBJNE+F+J1SKbUxyEWDb5mwhgHxE7zgNvkDC1jjN6pNOFKowpOHxCQI2M++OmE6Xjl+Cp8BpftxB9SxH+2qY6CVZQGnMIyTtWNzcedhPZuK3heD1J4mwGz6LCA2bDGtZeUz9tK0XlkQ8/WHVD+AYZGBZ79agYsTvleSpAAA
==Rationale== ==Reference implementation== The reference implementation of the PSBT format is available at Bitcoin Core [[https://github.com/bitcoin/bitcoin/pull/31247|PR #31247]]. ==Acknowledgements== Thanks to Sanket Kanjalkar whose notes on this topic formed the initial basis of this BIP. Also thanks to Pieter Wuille, Jonas Nick, Tim Ruffing, Marko Bencun, Salvatore Ingala, and all others who have participated in discussions about these fields. ================================================ FILE: bip-0374/gen_test_vectors.py ================================================ #!/usr/bin/env python3 """Generate the BIP-0374 test vectors.""" import csv from pathlib import Path from reference import ( dleq_generate_proof, dleq_verify_proof, ) from secp256k1lab.secp256k1 import G as GENERATOR, GE from secp256k1lab.util import tagged_hash NUM_SUCCESS_TEST_VECTORS = 8 DLEQ_TAG_TESTVECTORS_RNG = "BIP0374/testvectors_rng" FILENAME_GENERATE_PROOF_TEST = Path(__file__).parent / 'test_vectors_generate_proof.csv' FILENAME_VERIFY_PROOF_TEST = Path(__file__).parent / 'test_vectors_verify_proof.csv' def random_scalar_int(vector_i, purpose): rng_out = tagged_hash(DLEQ_TAG_TESTVECTORS_RNG, purpose.encode() + vector_i.to_bytes(4, 'little')) return int.from_bytes(rng_out, 'big') % GE.ORDER def random_bytes(vector_i, purpose): rng_out = tagged_hash(DLEQ_TAG_TESTVECTORS_RNG, purpose.encode() + vector_i.to_bytes(4, 'little')) return rng_out def create_test_vector_data(vector_i): g = random_scalar_int(vector_i, "scalar_g") if vector_i < 5 else 1 assert 0 < g < GE.ORDER G = g * GENERATOR assert not G.infinity a = random_scalar_int(vector_i, "scalar_a") A = a * G b = random_scalar_int(vector_i, "scalar_b") B = b * G C = a * B # shared secret assert C.to_bytes_compressed() == (b * A).to_bytes_compressed() auxrand = random_bytes(vector_i, "auxrand") msg = random_bytes(vector_i, "message") if vector_i != 5 else None proof = dleq_generate_proof(a, B, auxrand, G=G, m=msg) return (G, a, A, b, B, C, auxrand, msg, proof) TEST_VECTOR_DATA = [create_test_vector_data(i) for i in range(NUM_SUCCESS_TEST_VECTORS)] def gen_all_generate_proof_vectors(f): writer = csv.writer(f) writer.writerow(("index", "point_G", "scalar_a", "point_B", "auxrand_r", "message", "result_proof", "comment")) # success cases with random values idx = 0 for i in range(NUM_SUCCESS_TEST_VECTORS): G, a, A, b, B, C, auxrand, msg, proof = TEST_VECTOR_DATA[i] assert proof is not None and len(proof) == 64 if msg is None: msg = b"" writer.writerow((idx, G.to_bytes_compressed().hex(), f"{a:064x}", B.to_bytes_compressed().hex(), auxrand.hex(), msg.hex(), proof.hex(), f"Success case {i+1}")) idx += 1 # failure cases: a is not within group order (a=0, a=N) a_invalid = 0 assert dleq_generate_proof(a_invalid, B, auxrand, G=G, m=msg) is None writer.writerow((idx, G.to_bytes_compressed().hex(), f"{a_invalid:064x}", B.to_bytes_compressed().hex(), auxrand.hex(), msg.hex(), "INVALID", f"Failure case (a=0)")) idx += 1 a_invalid = GE.ORDER assert dleq_generate_proof(a_invalid, B, auxrand, G=G, m=msg) is None writer.writerow((idx, G.to_bytes_compressed().hex(), f"{a_invalid:064x}", B.to_bytes_compressed().hex(), auxrand.hex(), msg.hex(), "INVALID", f"Failure case (a=N [group order])")) idx += 1 # failure case: B is point at infinity B_infinity = GE() B_infinity_str = "INFINITY" assert dleq_generate_proof(a, B_infinity, auxrand, m=msg) is None writer.writerow((idx, G.to_bytes_compressed().hex(), f"{a:064x}", B_infinity_str, auxrand.hex(), msg.hex(), "INVALID", f"Failure case (B is point at infinity)")) idx += 1 def gen_all_verify_proof_vectors(f): writer = csv.writer(f) writer.writerow(("index", "point_G", "point_A", "point_B", "point_C", "proof", "message", "result_success", "comment")) # success cases (same as above) idx = 0 for i in range(NUM_SUCCESS_TEST_VECTORS): G, _, A, _, B, C, _, msg, proof = TEST_VECTOR_DATA[i] assert dleq_verify_proof(A, B, C, proof, G=G, m=msg) if msg is None: msg = b"" writer.writerow((idx, G.to_bytes_compressed().hex(), A.to_bytes_compressed().hex(), B.to_bytes_compressed().hex(), C.to_bytes_compressed().hex(), proof.hex(), msg.hex(), "TRUE", f"Success case {i+1}")) idx += 1 # other permutations of A, B, C should always fail for i, points in enumerate(([A, C, B], [B, A, C], [B, C, A], [C, A, B], [C, B, A])): assert not dleq_verify_proof(points[0], points[1], points[2], proof, m=msg) writer.writerow((idx, G.to_bytes_compressed().hex(), points[0].to_bytes_compressed().hex(), points[1].to_bytes_compressed().hex(), points[2].to_bytes_compressed().hex(), proof.hex(), msg.hex(), "FALSE", f"Swapped points case {i+1}")) idx += 1 # modifying proof should fail (flip one bit) proof_damage_pos = random_scalar_int(idx, "damage_pos") % 256 proof_damaged = list(proof) proof_damaged[proof_damage_pos // 8] ^= (1 << (proof_damage_pos % 8)) proof_damaged = bytes(proof_damaged) writer.writerow((idx, G.to_bytes_compressed().hex(), A.to_bytes_compressed().hex(), B.to_bytes_compressed().hex(), C.to_bytes_compressed().hex(), proof_damaged.hex(), msg.hex(), "FALSE", f"Tampered proof (random bit-flip)")) idx += 1 # modifying message should fail (flip one bit) msg_damage_pos = random_scalar_int(idx, "damage_pos") % 256 msg_damaged = list(msg) msg_damaged[msg_damage_pos // 8] ^= (1 << (msg_damage_pos % 8)) msg_damaged = bytes(msg_damaged) writer.writerow((idx, G.to_bytes_compressed().hex(), A.to_bytes_compressed().hex(), B.to_bytes_compressed().hex(), C.to_bytes_compressed().hex(), proof.hex(), msg_damaged.hex(), "FALSE", f"Tampered message (random bit-flip)")) idx += 1 if __name__ == "__main__": print(f"Generating {FILENAME_GENERATE_PROOF_TEST}...") with open(FILENAME_GENERATE_PROOF_TEST, "w", encoding="utf-8") as fil_generate_proof: gen_all_generate_proof_vectors(fil_generate_proof) print(f"Generating {FILENAME_VERIFY_PROOF_TEST}...") with open(FILENAME_VERIFY_PROOF_TEST, "w", encoding="utf-8") as fil_verify_proof: gen_all_verify_proof_vectors(fil_verify_proof) ================================================ FILE: bip-0374/reference.py ================================================ #!/usr/bin/env python3 """Reference implementation of DLEQ BIP for secp256k1 with unit tests.""" from pathlib import Path import random import sys import unittest # Prefer the vendored copy of secp256k1lab sys.path.insert(0, str(Path(__file__).parent / "secp256k1lab/src")) from secp256k1lab.secp256k1 import G, GE from secp256k1lab.util import tagged_hash, xor_bytes DLEQ_TAG_AUX = "BIP0374/aux" DLEQ_TAG_NONCE = "BIP0374/nonce" DLEQ_TAG_CHALLENGE = "BIP0374/challenge" def dleq_challenge( A: GE, B: GE, C: GE, R1: GE, R2: GE, m: bytes | None, G: GE, ) -> int: if m is not None: assert len(m) == 32 m = bytes([]) if m is None else m return int.from_bytes( tagged_hash( DLEQ_TAG_CHALLENGE, A.to_bytes_compressed() + B.to_bytes_compressed() + C.to_bytes_compressed() + G.to_bytes_compressed() + R1.to_bytes_compressed() + R2.to_bytes_compressed() + m, ), "big", ) def dleq_generate_proof( a: int, B: GE, r: bytes, G: GE = G, m: bytes | None = None ) -> bytes | None: assert len(r) == 32 if not (0 < a < GE.ORDER): return None if B.infinity: return None if m is not None: assert len(m) == 32 A = a * G C = a * B t = xor_bytes(a.to_bytes(32, "big"), tagged_hash(DLEQ_TAG_AUX, r)) m_prime = bytes([]) if m is None else m rand = tagged_hash( DLEQ_TAG_NONCE, t + A.to_bytes_compressed() + C.to_bytes_compressed() + m_prime ) k = int.from_bytes(rand, "big") % GE.ORDER if k == 0: return None R1 = k * G R2 = k * B e = dleq_challenge(A, B, C, R1, R2, m, G) s = (k + e * a) % GE.ORDER proof = e.to_bytes(32, "big") + s.to_bytes(32, "big") if not dleq_verify_proof(A, B, C, proof, G=G, m=m): return None return proof def dleq_verify_proof( A: GE, B: GE, C: GE, proof: bytes, G: GE = G, m: bytes | None = None ) -> bool: if A.infinity or B.infinity or C.infinity or G.infinity: return False assert len(proof) == 64 e = int.from_bytes(proof[:32], "big") s = int.from_bytes(proof[32:], "big") if s >= GE.ORDER: return False R1 = s * G - e * A if R1.infinity: return False R2 = s * B - e * C if R2.infinity: return False if e != dleq_challenge(A, B, C, R1, R2, m, G): return False return True class DLEQTests(unittest.TestCase): def test_dleq(self): seed = random.randrange(sys.maxsize) random.seed(seed) print(f"PRNG seed is: {seed}") for _ in range(10): # generate random keypairs for both parties a = random.randrange(1, GE.ORDER) A = a * G b = random.randrange(1, GE.ORDER) B = b * G # create shared secret C = a * B # create dleq proof rand_aux = random.randbytes(32) proof = dleq_generate_proof(a, B, rand_aux) self.assertTrue(proof is not None) # verify dleq proof success = dleq_verify_proof(A, B, C, proof) self.assertTrue(success) # flip a random bit in the dleq proof and check that verification fails for _ in range(5): proof_damaged = list(proof) proof_damaged[random.randrange(len(proof))] ^= 1 << ( random.randrange(8) ) success = dleq_verify_proof(A, B, C, bytes(proof_damaged)) self.assertFalse(success) # create the same dleq proof with a message message = random.randbytes(32) proof = dleq_generate_proof(a, B, rand_aux, m=message) self.assertTrue(proof is not None) # verify dleq proof with a message success = dleq_verify_proof(A, B, C, proof, m=message) self.assertTrue(success) # flip a random bit in the dleq proof and check that verification fails for _ in range(5): proof_damaged = list(proof) proof_damaged[random.randrange(len(proof))] ^= 1 << ( random.randrange(8) ) success = dleq_verify_proof(A, B, C, bytes(proof_damaged), m=message) self.assertFalse(success) ================================================ FILE: bip-0374/run_test_vectors.py ================================================ #!/usr/bin/env python3 """Run the BIP-DLEQ test vectors.""" import csv from pathlib import Path import sys from reference import ( dleq_generate_proof, dleq_verify_proof, ) from secp256k1lab.secp256k1 import GE FILENAME_GENERATE_PROOF_TEST = Path(__file__).parent / 'test_vectors_generate_proof.csv' FILENAME_VERIFY_PROOF_TEST = Path(__file__).parent / 'test_vectors_verify_proof.csv' all_passed = True print("-----------------------------------------") print("----- Proof generation test vectors -----") print("-----------------------------------------") with open(FILENAME_GENERATE_PROOF_TEST, newline='') as csvfile: reader = csv.reader(csvfile) next(reader) for row in reader: (index, point_G_hex, seckey_a_hex, point_B_hex, aux_rand_hex, msg_hex, result_str, comment) = row G = GE() if point_G_hex == 'INFINITY' else GE.from_bytes(bytes.fromhex(point_G_hex)) a = int.from_bytes(bytes.fromhex(seckey_a_hex), 'big') B = GE() if point_B_hex == 'INFINITY' else GE.from_bytes(bytes.fromhex(point_B_hex)) aux_rand = bytes.fromhex(aux_rand_hex) msg = bytes.fromhex(msg_hex) if msg == b"": msg = None print('Test vector', ('#' + index).rjust(3, ' ') + ':' + f' ({comment})') expected_result = None if result_str == 'INVALID' else bytes.fromhex(result_str) actual_result = dleq_generate_proof(a, B, aux_rand, G=G, m=msg) if expected_result == actual_result: print(' * Passed proof generation test.') else: print(' * Failed proof generation test.') print(' Expected proof: ', expected_result.hex() if expected_result is not None else 'INVALID') print(' Actual proof: ', actual_result.hex() if actual_result is not None else 'INVALID') all_passed = False print() print("-------------------------------------------") print("----- Proof verification test vectors -----") print("-------------------------------------------") with open(FILENAME_VERIFY_PROOF_TEST, newline='') as csvfile: reader = csv.reader(csvfile) next(reader) for row in reader: (index, point_G_hex, point_A_hex, point_B_hex, point_C_hex, proof_hex, msg_hex, result_success, comment) = row G = GE() if point_G_hex == 'INFINITY' else GE.from_bytes(bytes.fromhex(point_G_hex)) A = GE() if point_A_hex == 'INFINITY' else GE.from_bytes(bytes.fromhex(point_A_hex)) B = GE() if point_B_hex == 'INFINITY' else GE.from_bytes(bytes.fromhex(point_B_hex)) C = GE() if point_C_hex == 'INFINITY' else GE.from_bytes(bytes.fromhex(point_C_hex)) proof = bytes.fromhex(proof_hex) msg = bytes.fromhex(msg_hex) if msg == b"": msg = None print('Test vector', ('#' + index).rjust(3, ' ') + ':' + f' ({comment})') expected_result = result_success == 'TRUE' actual_result = dleq_verify_proof(A, B, C, proof, G=G, m=msg) if expected_result == actual_result: print(' * Passed proof verification test.') else: print(' * Failed proof verification test.') print(' Expected verification result: ', expected_result) print(' Actual verification result: ', actual_result) all_passed = False print() if all_passed: print('All test vectors passed.') sys.exit(0) else: print('Some test vectors failed.') sys.exit(1) ================================================ FILE: bip-0374/secp256k1lab/.github/workflows/main.yml ================================================ name: Tests on: [push, pull_request] jobs: ruff: runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - name: Install the latest version of uv uses: astral-sh/setup-uv@v5 - run: uvx ruff check . mypy: runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - name: Install the latest version of uv uses: astral-sh/setup-uv@v5 - run: uvx mypy . ================================================ FILE: bip-0374/secp256k1lab/.python-version ================================================ 3.9 ================================================ FILE: bip-0374/secp256k1lab/CHANGELOG.md ================================================ # Changelog All notable changes to this project will be documented in this file. The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/), and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html). ## [1.0.0] - 2025-03-31 Initial release. ================================================ FILE: bip-0374/secp256k1lab/COPYING ================================================ The MIT License (MIT) Copyright (c) 2009-2024 The Bitcoin Core developers Copyright (c) 2009-2024 Bitcoin Developers Copyright (c) 2025- The secp256k1lab Developers Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. ================================================ FILE: bip-0374/secp256k1lab/README.md ================================================ secp256k1lab ============ ![Dependencies: None](https://img.shields.io/badge/dependencies-none-success) An INSECURE implementation of the secp256k1 elliptic curve and related cryptographic schemes written in Python, intended for prototyping, experimentation and education. Features: * Low-level secp256k1 field and group arithmetic. * Schnorr signing/verification and key generation according to [BIP-340](https://github.com/bitcoin/bips/blob/master/bip-0340.mediawiki). * ECDH key exchange. WARNING: The code in this library is slow and trivially vulnerable to side channel attacks. ================================================ FILE: bip-0374/secp256k1lab/pyproject.toml ================================================ [project] name = "secp256k1lab" version = "1.0.0" description = "An INSECURE implementation of the secp256k1 elliptic curve and related cryptographic schemes, intended for prototyping, experimentation and education" readme = "README.md" authors = [ { name = "Pieter Wuille", email = "pieter@wuille.net" }, { name = "Tim Ruffing", email = "me@real-or-random.org" }, { name = "Jonas Nick", email = "jonasd.nick@gmail.com" }, { name = "Sebastian Falbesoner", email = "sebastian.falbesoner@gmail.com" } ] maintainers = [ { name = "Tim Ruffing", email = "me@real-or-random.org" }, { name = "Jonas Nick", email = "jonasd.nick@gmail.com" }, { name = "Sebastian Falbesoner", email = "sebastian.falbesoner@gmail.com" } ] requires-python = ">=3.9" license = "MIT" license-files = ["COPYING"] keywords = ["secp256k1", "elliptic curves", "cryptography", "Bitcoin"] classifiers = [ "Development Status :: 5 - Production/Stable", "Intended Audience :: Developers", "Intended Audience :: Education", "Intended Audience :: Science/Research", "License :: OSI Approved :: MIT License", "Programming Language :: Python", "Topic :: Security :: Cryptography", ] dependencies = [] [build-system] requires = ["hatchling"] build-backend = "hatchling.build" ================================================ FILE: bip-0374/secp256k1lab/src/secp256k1lab/__init__.py ================================================ ================================================ FILE: bip-0374/secp256k1lab/src/secp256k1lab/bip340.py ================================================ # The following functions are based on the BIP 340 reference implementation: # https://github.com/bitcoin/bips/blob/master/bip-0340/reference.py from .secp256k1 import FE, GE, G from .util import int_from_bytes, bytes_from_int, xor_bytes, tagged_hash def pubkey_gen(seckey: bytes) -> bytes: d0 = int_from_bytes(seckey) if not (1 <= d0 <= GE.ORDER - 1): raise ValueError("The secret key must be an integer in the range 1..n-1.") P = d0 * G assert not P.infinity return P.to_bytes_xonly() def schnorr_sign( msg: bytes, seckey: bytes, aux_rand: bytes, tag_prefix: str = "BIP0340" ) -> bytes: d0 = int_from_bytes(seckey) if not (1 <= d0 <= GE.ORDER - 1): raise ValueError("The secret key must be an integer in the range 1..n-1.") if len(aux_rand) != 32: raise ValueError("aux_rand must be 32 bytes instead of %i." % len(aux_rand)) P = d0 * G assert not P.infinity d = d0 if P.has_even_y() else GE.ORDER - d0 t = xor_bytes(bytes_from_int(d), tagged_hash(tag_prefix + "/aux", aux_rand)) k0 = ( int_from_bytes(tagged_hash(tag_prefix + "/nonce", t + P.to_bytes_xonly() + msg)) % GE.ORDER ) if k0 == 0: raise RuntimeError("Failure. This happens only with negligible probability.") R = k0 * G assert not R.infinity k = k0 if R.has_even_y() else GE.ORDER - k0 e = ( int_from_bytes( tagged_hash( tag_prefix + "/challenge", R.to_bytes_xonly() + P.to_bytes_xonly() + msg ) ) % GE.ORDER ) sig = R.to_bytes_xonly() + bytes_from_int((k + e * d) % GE.ORDER) assert schnorr_verify(msg, P.to_bytes_xonly(), sig, tag_prefix=tag_prefix) return sig def schnorr_verify( msg: bytes, pubkey: bytes, sig: bytes, tag_prefix: str = "BIP0340" ) -> bool: if len(pubkey) != 32: raise ValueError("The public key must be a 32-byte array.") if len(sig) != 64: raise ValueError("The signature must be a 64-byte array.") try: P = GE.from_bytes_xonly(pubkey) except ValueError: return False r = int_from_bytes(sig[0:32]) s = int_from_bytes(sig[32:64]) if (r >= FE.SIZE) or (s >= GE.ORDER): return False e = ( int_from_bytes(tagged_hash(tag_prefix + "/challenge", sig[0:32] + pubkey + msg)) % GE.ORDER ) R = s * G - e * P if R.infinity or (not R.has_even_y()) or (R.x != r): return False return True ================================================ FILE: bip-0374/secp256k1lab/src/secp256k1lab/ecdh.py ================================================ import hashlib from .secp256k1 import GE, Scalar def ecdh_compressed_in_raw_out(seckey: bytes, pubkey: bytes) -> GE: """TODO""" shared_secret = Scalar.from_bytes_checked(seckey) * GE.from_bytes_compressed(pubkey) assert not shared_secret.infinity # prime-order group return shared_secret def ecdh_libsecp256k1(seckey: bytes, pubkey: bytes) -> bytes: """TODO""" shared_secret = ecdh_compressed_in_raw_out(seckey, pubkey) return hashlib.sha256(shared_secret.to_bytes_compressed()).digest() ================================================ FILE: bip-0374/secp256k1lab/src/secp256k1lab/keys.py ================================================ from .secp256k1 import GE, G from .util import int_from_bytes # The following function is based on the BIP 327 reference implementation # https://github.com/bitcoin/bips/blob/master/bip-0327/reference.py # Return the plain public key corresponding to a given secret key def pubkey_gen_plain(seckey: bytes) -> bytes: d0 = int_from_bytes(seckey) if not (1 <= d0 <= GE.ORDER - 1): raise ValueError("The secret key must be an integer in the range 1..n-1.") P = d0 * G assert not P.infinity return P.to_bytes_compressed() ================================================ FILE: bip-0374/secp256k1lab/src/secp256k1lab/py.typed ================================================ ================================================ FILE: bip-0374/secp256k1lab/src/secp256k1lab/secp256k1.py ================================================ # Copyright (c) 2022-2023 The Bitcoin Core developers # Distributed under the MIT software license, see the accompanying # file COPYING or http://www.opensource.org/licenses/mit-license.php. """Test-only implementation of low-level secp256k1 field and group arithmetic It is designed for ease of understanding, not performance. WARNING: This code is slow and trivially vulnerable to side channel attacks. Do not use for anything but tests. Exports: * FE: class for secp256k1 field elements * GE: class for secp256k1 group elements * G: the secp256k1 generator point """ # TODO Docstrings of methods still say "field element" class APrimeFE: """Objects of this class represent elements of a prime field. They are represented internally in numerator / denominator form, in order to delay inversions. """ # The size of the field (also its modulus and characteristic). SIZE: int def __init__(self, a=0, b=1): """Initialize a field element a/b; both a and b can be ints or field elements.""" if isinstance(a, type(self)): num = a._num den = a._den else: num = a % self.SIZE den = 1 if isinstance(b, type(self)): den = (den * b._num) % self.SIZE num = (num * b._den) % self.SIZE else: den = (den * b) % self.SIZE assert den != 0 if num == 0: den = 1 self._num = num self._den = den def __add__(self, a): """Compute the sum of two field elements (second may be int).""" if isinstance(a, type(self)): return type(self)(self._num * a._den + self._den * a._num, self._den * a._den) if isinstance(a, int): return type(self)(self._num + self._den * a, self._den) return NotImplemented def __radd__(self, a): """Compute the sum of an integer and a field element.""" return type(self)(a) + self @classmethod # REVIEW This should be # def sum(cls, *es: Iterable[Self]) -> Self: # but Self needs the typing_extension package on Python <= 3.12. def sum(cls, *es): """Compute the sum of field elements. sum(a, b, c, ...) is identical to (0 + a + b + c + ...).""" return sum(es, start=cls(0)) def __sub__(self, a): """Compute the difference of two field elements (second may be int).""" if isinstance(a, type(self)): return type(self)(self._num * a._den - self._den * a._num, self._den * a._den) if isinstance(a, int): return type(self)(self._num - self._den * a, self._den) return NotImplemented def __rsub__(self, a): """Compute the difference of an integer and a field element.""" return type(self)(a) - self def __mul__(self, a): """Compute the product of two field elements (second may be int).""" if isinstance(a, type(self)): return type(self)(self._num * a._num, self._den * a._den) if isinstance(a, int): return type(self)(self._num * a, self._den) return NotImplemented def __rmul__(self, a): """Compute the product of an integer with a field element.""" return type(self)(a) * self def __truediv__(self, a): """Compute the ratio of two field elements (second may be int).""" if isinstance(a, type(self)) or isinstance(a, int): return type(self)(self, a) return NotImplemented def __pow__(self, a): """Raise a field element to an integer power.""" return type(self)(pow(self._num, a, self.SIZE), pow(self._den, a, self.SIZE)) def __neg__(self): """Negate a field element.""" return type(self)(-self._num, self._den) def __int__(self): """Convert a field element to an integer in range 0..SIZE-1. The result is cached.""" if self._den != 1: self._num = (self._num * pow(self._den, -1, self.SIZE)) % self.SIZE self._den = 1 return self._num def sqrt(self): """Compute the square root of a field element if it exists (None otherwise).""" raise NotImplementedError def is_square(self): """Determine if this field element has a square root.""" # A more efficient algorithm is possible here (Jacobi symbol). return self.sqrt() is not None def is_even(self): """Determine whether this field element, represented as integer in 0..SIZE-1, is even.""" return int(self) & 1 == 0 def __eq__(self, a): """Check whether two field elements are equal (second may be an int).""" if isinstance(a, type(self)): return (self._num * a._den - self._den * a._num) % self.SIZE == 0 return (self._num - self._den * a) % self.SIZE == 0 def to_bytes(self): """Convert a field element to a 32-byte array (BE byte order).""" return int(self).to_bytes(32, 'big') @classmethod def from_int_checked(cls, v): """Convert an integer to a field element (no overflow allowed).""" if v >= cls.SIZE: raise ValueError return cls(v) @classmethod def from_int_wrapping(cls, v): """Convert an integer to a field element (reduced modulo SIZE).""" return cls(v % cls.SIZE) @classmethod def from_bytes_checked(cls, b): """Convert a 32-byte array to a field element (BE byte order, no overflow allowed).""" v = int.from_bytes(b, 'big') return cls.from_int_checked(v) @classmethod def from_bytes_wrapping(cls, b): """Convert a 32-byte array to a field element (BE byte order, reduced modulo SIZE).""" v = int.from_bytes(b, 'big') return cls.from_int_wrapping(v) def __str__(self): """Convert this field element to a 64 character hex string.""" return f"{int(self):064x}" def __repr__(self): """Get a string representation of this field element.""" return f"{type(self).__qualname__}(0x{int(self):x})" class FE(APrimeFE): SIZE = 2**256 - 2**32 - 977 def sqrt(self): # Due to the fact that our modulus p is of the form (p % 4) == 3, the Tonelli-Shanks # algorithm (https://en.wikipedia.org/wiki/Tonelli-Shanks_algorithm) is simply # raising the argument to the power (p + 1) / 4. # To see why: (p-1) % 2 = 0, so 2 divides the order of the multiplicative group, # and thus only half of the non-zero field elements are squares. An element a is # a (nonzero) square when Euler's criterion, a^((p-1)/2) = 1 (mod p), holds. We're # looking for x such that x^2 = a (mod p). Given a^((p-1)/2) = 1, that is equivalent # to x^2 = a^(1 + (p-1)/2) mod p. As (1 + (p-1)/2) is even, this is equivalent to # x = a^((1 + (p-1)/2)/2) mod p, or x = a^((p+1)/4) mod p. v = int(self) s = pow(v, (self.SIZE + 1) // 4, self.SIZE) if s**2 % self.SIZE == v: return type(self)(s) return None class Scalar(APrimeFE): """TODO Docstring""" SIZE = 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141 class GE: """Objects of this class represent secp256k1 group elements (curve points or infinity) GE objects are immutable. Normal points on the curve have fields: * x: the x coordinate (a field element) * y: the y coordinate (a field element, satisfying y^2 = x^3 + 7) * infinity: False The point at infinity has field: * infinity: True """ # TODO The following two class attributes should probably be just getters as # classmethods to enforce immutability. Unfortunately Python makes it hard # to create "classproperties". `G` could then also be just a classmethod. # Order of the group (number of points on the curve, plus 1 for infinity) ORDER = Scalar.SIZE # Number of valid distinct x coordinates on the curve. ORDER_HALF = ORDER // 2 @property def infinity(self): """Whether the group element is the point at infinity.""" return self._infinity @property def x(self): """The x coordinate (a field element) of a non-infinite group element.""" assert not self.infinity return self._x @property def y(self): """The y coordinate (a field element) of a non-infinite group element.""" assert not self.infinity return self._y def __init__(self, x=None, y=None): """Initialize a group element with specified x and y coordinates, or infinity.""" if x is None: # Initialize as infinity. assert y is None self._infinity = True else: # Initialize as point on the curve (and check that it is). fx = FE(x) fy = FE(y) assert fy**2 == fx**3 + 7 self._infinity = False self._x = fx self._y = fy def __add__(self, a): """Add two group elements together.""" # Deal with infinity: a + infinity == infinity + a == a. if self.infinity: return a if a.infinity: return self if self.x == a.x: if self.y != a.y: # A point added to its own negation is infinity. assert self.y + a.y == 0 return GE() else: # For identical inputs, use the tangent (doubling formula). lam = (3 * self.x**2) / (2 * self.y) else: # For distinct inputs, use the line through both points (adding formula). lam = (self.y - a.y) / (self.x - a.x) # Determine point opposite to the intersection of that line with the curve. x = lam**2 - (self.x + a.x) y = lam * (self.x - x) - self.y return GE(x, y) @staticmethod def sum(*ps): """Compute the sum of group elements. GE.sum(a, b, c, ...) is identical to (GE() + a + b + c + ...).""" return sum(ps, start=GE()) @staticmethod def batch_mul(*aps): """Compute a (batch) scalar group element multiplication. GE.batch_mul((a1, p1), (a2, p2), (a3, p3)) is identical to a1*p1 + a2*p2 + a3*p3, but more efficient.""" # Reduce all the scalars modulo order first (so we can deal with negatives etc). naps = [(int(a), p) for a, p in aps] # Start with point at infinity. r = GE() # Iterate over all bit positions, from high to low. for i in range(255, -1, -1): # Double what we have so far. r = r + r # Add then add the points for which the corresponding scalar bit is set. for (a, p) in naps: if (a >> i) & 1: r += p return r def __rmul__(self, a): """Multiply an integer with a group element.""" if self == G: return FAST_G.mul(Scalar(a)) return GE.batch_mul((Scalar(a), self)) def __neg__(self): """Compute the negation of a group element.""" if self.infinity: return self return GE(self.x, -self.y) def __sub__(self, a): """Subtract a group element from another.""" return self + (-a) def __eq__(self, a): """Check if two group elements are equal.""" return (self - a).infinity def has_even_y(self): """Determine whether a non-infinity group element has an even y coordinate.""" assert not self.infinity return self.y.is_even() def to_bytes_compressed(self): """Convert a non-infinite group element to 33-byte compressed encoding.""" assert not self.infinity return bytes([3 - self.y.is_even()]) + self.x.to_bytes() def to_bytes_compressed_with_infinity(self): """Convert a group element to 33-byte compressed encoding, mapping infinity to zeros.""" if self.infinity: return 33 * b"\x00" return self.to_bytes_compressed() def to_bytes_uncompressed(self): """Convert a non-infinite group element to 65-byte uncompressed encoding.""" assert not self.infinity return b'\x04' + self.x.to_bytes() + self.y.to_bytes() def to_bytes_xonly(self): """Convert (the x coordinate of) a non-infinite group element to 32-byte xonly encoding.""" assert not self.infinity return self.x.to_bytes() @staticmethod def lift_x(x): """Return group element with specified field element as x coordinate (and even y).""" y = (FE(x)**3 + 7).sqrt() if y is None: raise ValueError if not y.is_even(): y = -y return GE(x, y) @staticmethod def from_bytes_compressed(b): """Convert a compressed to a group element.""" assert len(b) == 33 if b[0] != 2 and b[0] != 3: raise ValueError x = FE.from_bytes_checked(b[1:]) r = GE.lift_x(x) if b[0] == 3: r = -r return r @staticmethod def from_bytes_uncompressed(b): """Convert an uncompressed to a group element.""" assert len(b) == 65 if b[0] != 4: raise ValueError x = FE.from_bytes_checked(b[1:33]) y = FE.from_bytes_checked(b[33:]) if y**2 != x**3 + 7: raise ValueError return GE(x, y) @staticmethod def from_bytes(b): """Convert a compressed or uncompressed encoding to a group element.""" assert len(b) in (33, 65) if len(b) == 33: return GE.from_bytes_compressed(b) else: return GE.from_bytes_uncompressed(b) @staticmethod def from_bytes_xonly(b): """Convert a point given in xonly encoding to a group element.""" assert len(b) == 32 x = FE.from_bytes_checked(b) r = GE.lift_x(x) return r @staticmethod def is_valid_x(x): """Determine whether the provided field element is a valid X coordinate.""" return (FE(x)**3 + 7).is_square() def __str__(self): """Convert this group element to a string.""" if self.infinity: return "(inf)" return f"({self.x},{self.y})" def __repr__(self): """Get a string representation for this group element.""" if self.infinity: return "GE()" return f"GE(0x{int(self.x):x},0x{int(self.y):x})" def __hash__(self): """Compute a non-cryptographic hash of the group element.""" if self.infinity: return 0 # 0 is not a valid x coordinate return int(self.x) # The secp256k1 generator point G = GE.lift_x(0x79BE667EF9DCBBAC55A06295CE870B07029BFCDB2DCE28D959F2815B16F81798) class FastGEMul: """Table for fast multiplication with a constant group element. Speed up scalar multiplication with a fixed point P by using a precomputed lookup table with its powers of 2: table = [P, 2*P, 4*P, (2^3)*P, (2^4)*P, ..., (2^255)*P] During multiplication, the points corresponding to each bit set in the scalar are added up, i.e. on average ~128 point additions take place. """ def __init__(self, p): self.table = [p] # table[i] = (2^i) * p for _ in range(255): p = p + p self.table.append(p) def mul(self, a): result = GE() a = int(a) for bit in range(a.bit_length()): if a & (1 << bit): result += self.table[bit] return result # Precomputed table with multiples of G for fast multiplication FAST_G = FastGEMul(G) ================================================ FILE: bip-0374/secp256k1lab/src/secp256k1lab/util.py ================================================ import hashlib # This implementation can be sped up by storing the midstate after hashing # tag_hash instead of rehashing it all the time. def tagged_hash(tag: str, msg: bytes) -> bytes: tag_hash = hashlib.sha256(tag.encode()).digest() return hashlib.sha256(tag_hash + tag_hash + msg).digest() def bytes_from_int(x: int) -> bytes: return x.to_bytes(32, byteorder="big") def xor_bytes(b0: bytes, b1: bytes) -> bytes: return bytes(x ^ y for (x, y) in zip(b0, b1)) def int_from_bytes(b: bytes) -> int: return int.from_bytes(b, byteorder="big") def hash_sha256(b: bytes) -> bytes: return hashlib.sha256(b).digest() ================================================ FILE: bip-0374/test_vectors_generate_proof.csv ================================================ index,point_G,scalar_a,point_B,auxrand_r,message,result_proof,comment 0,02cef38f55e78b321a1f785cb1c6e33dfcef9784c18bdc4e279801c449ccdfb88e,07ff93d43f1012a5d4a44aba55240212ed39c87b3344e46757d99f24177fc576,02dad4b35c2379ba8334c9a5dda8f6e6d5cd575a7cc9d3ca4faaac51839daaa30f,cb979b0fc8ccc7f237751e719d992fcc324b6500af33999cd54a3e5c05fb1ea4,efb07d4b382d3da1079fbf24df623ba6c2e4c764993bbfa6dd7a4fe4aaf33859,7e7e934169e0bf4706e6b29e5a621c7fe199a524744a25af80071e111c0e2e94118e730d8add118dd2ee4f7d1cc183e1b87168362d1a6f85c16d8671a3fc7a8a,Success case 1 1,02464e351831efedb755223cabbf664f10564b4742c725c023034bc928ed339e0e,f4e9172285393c6ada994c811b3e50fc47e96421ea7e54f4a4e459528d4cf562,03fe589b0fa23f060f6d4d1e76b9b19d5bb3db0e56d39a4303913de0e706463008,75f12482b9209dae12230ea1f8bf69723a1b447d361db8f510dd9ab33556fd4c,76184ce9eea5b339ebf5304b57452c1ada1466610f0a58574d6c496798cee04b,6b4521a8363a7ebc5d95ac6ec6b64db81fcf21795187d7c4600c42b73fb4fb9870ab8d106c0fd2d292c1710e10437b20575ddb3cb32eb77a5618d94ddba600f2,Success case 2 2,0222db2054fef98344352a13bc0304a71da7b5e9a2f7fd1f3c9f3519a3d9377fb7,589476913e763b60d5c2a5bfb39230ec669caac1b44312e9bcd2d3f4473abfef,03bc7a19970c812118f74ba659b491e00dade6096ff62d1afe032a92b8671498ed,4da1c4c4b0f9db4eb6b2e5cb648d7e8a0aa35aa5c4ec4d07f096e0e03deca366,66503623468a78cfcef47888c85e0010ecd897f441d263448bfc7a89b882ab20,12aa2aa469b3c037871a09d18ab18d3840219b1ed169f6ef9deae6d927949884a459705ae89a57522224ce3482dee00a41ba511188ae60efdeb736223eb66e7b,Success case 3 3,03dfa65bd3711eba75fa1996a0c1d95a4419bd835304152d9aa6efa590670f2af6,24d0ed3fc189eb1b64e5dc9dd4af0f3c8c143b0c79cb5fcca0dfa08a11cc60a1,03b51081323d38fb0b75f0c1ec6755fdb79c239c327ca11269fe68ba8a878b704e,31a68d6db27f6404bbceff646ff1b26a34704a0105a36c5a845d0257cea19c9b,f2996b3766d123a949e65541baf1d89d446360d05af51bd93f0445d8c472c952,7907653d29c5722ae44510e7f2839f253450aefc833b7e0a3b38384032f847f2cf41136b2fe6a558ad125287d20c0117f2a30c4ac0c4cebbcfa1dd3a69d84200,Success case 4 4,02b15de5a3aefcfe2473916c76e619b5800ac7250ef93a9e6e0dd1505104fc58e7,73fffa796edb72d111b5e0bbda1608f098ac98120796f971b438691e1bfb7b96,03a4692be176ff89a972de9cc407083096847b950d1cae72b947665a3d5f4c2f01,1cdfb4d7cce5e50783299896a471a44e6aa2c5e2100d6c37987c6b40503c6162,0ceb45f560f2cf6b76a139ffe2c47c5ca6d26d6a3a210e59f197413bbec040b4,02277ca5a7acfe8ae13c2db4a8f74489d0ba100ed8b082381ddb6522c4510718ab88b8dbbd785c388ade79586cf6416f3c47a79670af84abccc788a5d9f2e327,Success case 5 5,0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798,c08ca8e0bb59769fc6a4e078456284e00ea34f65add988c246e1bba85824ccdc,034bccb1c570ac1f3bc42d61fe35de605b99626501ccb20297e1acbbf2d7152aa1,c8d7056abd4726eb5a0f198740af14d6c1f0c16e5d7a37eaec621b661e669ac4,,503562d36910cd2d61a4d07c8ff680265c713e63dde0dcb88e6ea3c58597bdc05b86db9af95eccc475ce2177f941c118fefed20227d4ce8ce9557cb008758de6,Success case 6 6,0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798,8e641ba6bf7f64eec76005a29585a5035376375f33e331215aedfe03b8e80e7a,0231c64e3efa506fdad6aad0f6084d5f6739de7f448d7e66f9d22f842638f41d60,02a7b2e2f5a5e9b1078dbb160502a32491fe80a091e91dd92cf77b0b7d90970f,35841ca532846e1cdd23a3d107824343584f88eff580929469865eae8355ee3c,5c7b27a33210750e9de8679d9f43497cf9f12ac642cde0a1fc26443aa2fc89bf71aabf7bac89f5d8a96cbe86daba155fa74d6f3e111136179e53b04eb6d7807f,Success case 7 7,0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798,cfb9a7ecc49bea4f2e2ee34c38a6f48b5cd5bd06f4e4d4ffb45905b3d26db842,021cb81121a00f89769903305a367ad3cc02d5b402b12c026e06ac94bde28cd608,d38466b77484154a3fcb3151094c1c8a845c73a3c036b3a8ebffd8ef62c9047f,22616bb5fb2d7c68270f305122f2a09e833239c4b1c9a04e285119fb606ac794,78a5544afa75bf152653fe55fb76926f2f65131bf090972a0b0b37d310c28a6bde0e7bfacc10ac12d36f55316ba134b6ba0b844a65ae05cad53c0b296c6639bb,Success case 8 8,0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798,0000000000000000000000000000000000000000000000000000000000000000,021cb81121a00f89769903305a367ad3cc02d5b402b12c026e06ac94bde28cd608,d38466b77484154a3fcb3151094c1c8a845c73a3c036b3a8ebffd8ef62c9047f,22616bb5fb2d7c68270f305122f2a09e833239c4b1c9a04e285119fb606ac794,INVALID,Failure case (a=0) 9,0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798,fffffffffffffffffffffffffffffffebaaedce6af48a03bbfd25e8cd0364141,021cb81121a00f89769903305a367ad3cc02d5b402b12c026e06ac94bde28cd608,d38466b77484154a3fcb3151094c1c8a845c73a3c036b3a8ebffd8ef62c9047f,22616bb5fb2d7c68270f305122f2a09e833239c4b1c9a04e285119fb606ac794,INVALID,Failure case (a=N [group order]) 10,0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798,cfb9a7ecc49bea4f2e2ee34c38a6f48b5cd5bd06f4e4d4ffb45905b3d26db842,INFINITY,d38466b77484154a3fcb3151094c1c8a845c73a3c036b3a8ebffd8ef62c9047f,22616bb5fb2d7c68270f305122f2a09e833239c4b1c9a04e285119fb606ac794,INVALID,Failure case (B is point at infinity) ================================================ FILE: bip-0374/test_vectors_verify_proof.csv ================================================ index,point_G,point_A,point_B,point_C,proof,message,result_success,comment 0,02cef38f55e78b321a1f785cb1c6e33dfcef9784c18bdc4e279801c449ccdfb88e,02b540b22c2c5ef0dc886abdaad27498453d893265560bc08a187319af6f845f58,02dad4b35c2379ba8334c9a5dda8f6e6d5cd575a7cc9d3ca4faaac51839daaa30f,03fefe00951dcd0ef10b12523393c2b8113119de4fdeeab320694e96bdccd2775b,7e7e934169e0bf4706e6b29e5a621c7fe199a524744a25af80071e111c0e2e94118e730d8add118dd2ee4f7d1cc183e1b87168362d1a6f85c16d8671a3fc7a8a,efb07d4b382d3da1079fbf24df623ba6c2e4c764993bbfa6dd7a4fe4aaf33859,TRUE,Success case 1 1,02464e351831efedb755223cabbf664f10564b4742c725c023034bc928ed339e0e,032baaf1b10845a51b551196984a91efe2adf9d41b92bec3927218e6e4ca344002,03fe589b0fa23f060f6d4d1e76b9b19d5bb3db0e56d39a4303913de0e706463008,031f59aa1df22190e00380d8c5941adf899f596593765a1251005fd24f2bf7c884,6b4521a8363a7ebc5d95ac6ec6b64db81fcf21795187d7c4600c42b73fb4fb9870ab8d106c0fd2d292c1710e10437b20575ddb3cb32eb77a5618d94ddba600f2,76184ce9eea5b339ebf5304b57452c1ada1466610f0a58574d6c496798cee04b,TRUE,Success case 2 2,0222db2054fef98344352a13bc0304a71da7b5e9a2f7fd1f3c9f3519a3d9377fb7,026aa26fcd626f8f55295859e9f8dd1f103149dd64d77c2bbba1bcf33bb37ebaa2,03bc7a19970c812118f74ba659b491e00dade6096ff62d1afe032a92b8671498ed,035628d1a69910daef614c7cae68d71ece55c5908af2360629e25c1b7de21eeb4b,12aa2aa469b3c037871a09d18ab18d3840219b1ed169f6ef9deae6d927949884a459705ae89a57522224ce3482dee00a41ba511188ae60efdeb736223eb66e7b,66503623468a78cfcef47888c85e0010ecd897f441d263448bfc7a89b882ab20,TRUE,Success case 3 3,03dfa65bd3711eba75fa1996a0c1d95a4419bd835304152d9aa6efa590670f2af6,031bf61ba89009ee1266c9003a72e8e07d77877678ccda7f15325aadcd64ed186b,03b51081323d38fb0b75f0c1ec6755fdb79c239c327ca11269fe68ba8a878b704e,02d1b1f37a80217ba73785babfa63251052775f9d3ca65060054033288b7a3f66b,7907653d29c5722ae44510e7f2839f253450aefc833b7e0a3b38384032f847f2cf41136b2fe6a558ad125287d20c0117f2a30c4ac0c4cebbcfa1dd3a69d84200,f2996b3766d123a949e65541baf1d89d446360d05af51bd93f0445d8c472c952,TRUE,Success case 4 4,02b15de5a3aefcfe2473916c76e619b5800ac7250ef93a9e6e0dd1505104fc58e7,0296c8e00dda60bb5565b77371ff913091978646b58ccf218bc591f68a75232e6e,03a4692be176ff89a972de9cc407083096847b950d1cae72b947665a3d5f4c2f01,03a7a7f9527fd387c2b2ce0c76669d646c78a3b470a4b34d3a2dabafc8505ef472,02277ca5a7acfe8ae13c2db4a8f74489d0ba100ed8b082381ddb6522c4510718ab88b8dbbd785c388ade79586cf6416f3c47a79670af84abccc788a5d9f2e327,0ceb45f560f2cf6b76a139ffe2c47c5ca6d26d6a3a210e59f197413bbec040b4,TRUE,Success case 5 5,0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798,02637b2c3ea8ca80b9caecc50f4134c86ae9cf7a269133e7afc71f30e3a3cda60c,034bccb1c570ac1f3bc42d61fe35de605b99626501ccb20297e1acbbf2d7152aa1,0285b826c8dd175805901906b6c9b4140a30cbcc94c6e7dcf36476038bf90d4718,503562d36910cd2d61a4d07c8ff680265c713e63dde0dcb88e6ea3c58597bdc05b86db9af95eccc475ce2177f941c118fefed20227d4ce8ce9557cb008758de6,,TRUE,Success case 6 6,0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798,02983a72b4cb44d4322641a7b2001900cd6ae0908a610546c73ed126accdba0514,0231c64e3efa506fdad6aad0f6084d5f6739de7f448d7e66f9d22f842638f41d60,03af1bc14b384eda28398df6a7900e567c5b6f6613cafce5027b98be015286f71b,5c7b27a33210750e9de8679d9f43497cf9f12ac642cde0a1fc26443aa2fc89bf71aabf7bac89f5d8a96cbe86daba155fa74d6f3e111136179e53b04eb6d7807f,35841ca532846e1cdd23a3d107824343584f88eff580929469865eae8355ee3c,TRUE,Success case 7 7,0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798,03611410561c35dae13135e4ad8094baac9bbcf2f4e18498181a8ff8a6d43be9d9,021cb81121a00f89769903305a367ad3cc02d5b402b12c026e06ac94bde28cd608,03d9a98624c0c74fc7eebd39ed84175f80d03c774908e75ca737a0745d1c64e20a,78a5544afa75bf152653fe55fb76926f2f65131bf090972a0b0b37d310c28a6bde0e7bfacc10ac12d36f55316ba134b6ba0b844a65ae05cad53c0b296c6639bb,22616bb5fb2d7c68270f305122f2a09e833239c4b1c9a04e285119fb606ac794,TRUE,Success case 8 8,0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798,03611410561c35dae13135e4ad8094baac9bbcf2f4e18498181a8ff8a6d43be9d9,03d9a98624c0c74fc7eebd39ed84175f80d03c774908e75ca737a0745d1c64e20a,021cb81121a00f89769903305a367ad3cc02d5b402b12c026e06ac94bde28cd608,78a5544afa75bf152653fe55fb76926f2f65131bf090972a0b0b37d310c28a6bde0e7bfacc10ac12d36f55316ba134b6ba0b844a65ae05cad53c0b296c6639bb,22616bb5fb2d7c68270f305122f2a09e833239c4b1c9a04e285119fb606ac794,FALSE,Swapped points case 1 9,0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798,021cb81121a00f89769903305a367ad3cc02d5b402b12c026e06ac94bde28cd608,03611410561c35dae13135e4ad8094baac9bbcf2f4e18498181a8ff8a6d43be9d9,03d9a98624c0c74fc7eebd39ed84175f80d03c774908e75ca737a0745d1c64e20a,78a5544afa75bf152653fe55fb76926f2f65131bf090972a0b0b37d310c28a6bde0e7bfacc10ac12d36f55316ba134b6ba0b844a65ae05cad53c0b296c6639bb,22616bb5fb2d7c68270f305122f2a09e833239c4b1c9a04e285119fb606ac794,FALSE,Swapped points case 2 10,0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798,021cb81121a00f89769903305a367ad3cc02d5b402b12c026e06ac94bde28cd608,03d9a98624c0c74fc7eebd39ed84175f80d03c774908e75ca737a0745d1c64e20a,03611410561c35dae13135e4ad8094baac9bbcf2f4e18498181a8ff8a6d43be9d9,78a5544afa75bf152653fe55fb76926f2f65131bf090972a0b0b37d310c28a6bde0e7bfacc10ac12d36f55316ba134b6ba0b844a65ae05cad53c0b296c6639bb,22616bb5fb2d7c68270f305122f2a09e833239c4b1c9a04e285119fb606ac794,FALSE,Swapped points case 3 11,0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798,03d9a98624c0c74fc7eebd39ed84175f80d03c774908e75ca737a0745d1c64e20a,03611410561c35dae13135e4ad8094baac9bbcf2f4e18498181a8ff8a6d43be9d9,021cb81121a00f89769903305a367ad3cc02d5b402b12c026e06ac94bde28cd608,78a5544afa75bf152653fe55fb76926f2f65131bf090972a0b0b37d310c28a6bde0e7bfacc10ac12d36f55316ba134b6ba0b844a65ae05cad53c0b296c6639bb,22616bb5fb2d7c68270f305122f2a09e833239c4b1c9a04e285119fb606ac794,FALSE,Swapped points case 4 12,0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798,03d9a98624c0c74fc7eebd39ed84175f80d03c774908e75ca737a0745d1c64e20a,021cb81121a00f89769903305a367ad3cc02d5b402b12c026e06ac94bde28cd608,03611410561c35dae13135e4ad8094baac9bbcf2f4e18498181a8ff8a6d43be9d9,78a5544afa75bf152653fe55fb76926f2f65131bf090972a0b0b37d310c28a6bde0e7bfacc10ac12d36f55316ba134b6ba0b844a65ae05cad53c0b296c6639bb,22616bb5fb2d7c68270f305122f2a09e833239c4b1c9a04e285119fb606ac794,FALSE,Swapped points case 5 13,0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798,03611410561c35dae13135e4ad8094baac9bbcf2f4e18498181a8ff8a6d43be9d9,021cb81121a00f89769903305a367ad3cc02d5b402b12c026e06ac94bde28cd608,03d9a98624c0c74fc7eebd39ed84175f80d03c774908e75ca737a0745d1c64e20a,78a5544afa75bf152653fe55fb76926f2f65131ff090972a0b0b37d310c28a6bde0e7bfacc10ac12d36f55316ba134b6ba0b844a65ae05cad53c0b296c6639bb,22616bb5fb2d7c68270f305122f2a09e833239c4b1c9a04e285119fb606ac794,FALSE,Tampered proof (random bit-flip) 14,0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798,03611410561c35dae13135e4ad8094baac9bbcf2f4e18498181a8ff8a6d43be9d9,021cb81121a00f89769903305a367ad3cc02d5b402b12c026e06ac94bde28cd608,03d9a98624c0c74fc7eebd39ed84175f80d03c774908e75ca737a0745d1c64e20a,78a5544afa75bf152653fe55fb76926f2f65131bf090972a0b0b37d310c28a6bde0e7bfacc10ac12d36f55316ba134b6ba0b844a65ae05cad53c0b296c6639bb,22616bb5fb6d7c68270f305122f2a09e833239c4b1c9a04e285119fb606ac794,FALSE,Tampered message (random bit-flip) ================================================ FILE: bip-0374.mediawiki ================================================
  BIP: 374
  Layer: Applications
  Title: Discrete Log Equality Proofs
  Authors: Andrew Toth 
           Ruben Somsen 
           Sebastian Falbesoner 
  Status: Draft
  Type: Specification
  Assigned: 2024-12-26
  License: BSD-2-Clause
  Discussion: https://gist.github.com/andrewtoth/df97c3260cc8d12f09d3855ee61322ea
              https://groups.google.com/g/bitcoindev/c/MezoKV5md7s
  Version: 0.2.0
== Introduction == === Abstract === This document proposes a standard for 64-byte zero-knowledge ''discrete logarithm equality proofs'' (DLEQ proofs) over an elliptic curve. For given elliptic curve points ''A'', ''B'', ''C'', ''G'', and a scalar ''a'' known only to the prover where ''A = a⋅G'' and ''C = a⋅B'', the prover proves knowledge of ''a'' without revealing anything about ''a''. This can, for instance, be useful in ECDH: if ''A'' and ''B'' are ECDH public keys, and ''C'' is their ECDH shared secret computed as ''C = a⋅B'', the proof establishes that the same secret key ''a'' is used for generating both ''A'' and ''C'' without revealing ''a''. === Copyright === This document is licensed under the 2-clause BSD license. === Motivation === [https://github.com/bitcoin/bips/blob/master/bip-0352.mediawiki#specification BIP352] requires senders to compute output scripts using ECDH shared secrets from the same secret keys used to sign the inputs. Generating an incorrect signature will produce an invalid transaction that will be rejected by consensus. An incorrectly generated output script can still be consensus-valid, meaning funds may be lost if it gets broadcast. By producing a DLEQ proof for the generated ECDH shared secrets, the signing entity can prove to other entities that the output scripts have been generated correctly without revealing the private keys. == Specification == All conventions and notations are used as defined in [https://github.com/bitcoin/bips/blob/master/bip-0327.mediawiki#user-content-Notation BIP327]. === Description === The basic proof generation uses a random scalar ''k'', the secret ''a'', and the point being proven ''C = a⋅B''. * Let ''R1 = k⋅G''. * Let ''R2 = k⋅B''. * Let ''e = hash(R1 || R2)''. * Let ''s = (k + e⋅a)''. Providing only ''C'', ''e'' and ''s'' as a proof does not reveal ''a'' or ''k''. Verifying the proof involves recreating ''R1'' and ''R2'' with only ''e'' and ''s'' as follows: * Let ''R1 = s⋅G - e⋅A''. * Let ''R2 = s⋅B - e⋅C''. This can be verified by substituting ''s = (k + e⋅a)'': * ''s⋅G - e⋅A = (k + e⋅a)⋅G - e⋅A = k⋅G + e⋅(a⋅G) - e⋅A = k⋅G + e⋅A - e⋅A = k⋅G''. * ''s⋅B - e⋅C = (k + e⋅a)⋅B - e⋅C = k⋅B + e⋅(a⋅B) - e⋅C = k⋅B + e⋅C - e⋅C = k⋅B''. Thus verifying ''e = hash(R1 || R2)'' proves the discrete logarithm equivalency of ''A'' and ''C''. === DLEQ Proof Generation === The following generates a proof that the result of ''a⋅B'' and the result of ''a⋅G'' are both generated from the same scalar ''a'' without having to reveal ''a''. Input: * The secret key ''a'': a 256-bit unsigned integer * The public key ''B'': a point on the curve * Auxiliary random data ''r'': a 32-byte array ''' Why include auxiliary random data?''' The auxiliary random data should be set to fresh randomness for each proof. The same rationale and recommendations from [https://github.com/bitcoin/bips/blob/master/bip-0340.mediawiki#default-signing BIP340] should be applied. * The generator point ''G'': a point on the curve ''' Why include the generator point G as an input?''' While all other BIPs have used the generator point from secp256k1, passing it as an input here lets this algorithm be used for other curves. * An optional message ''m'': a 32-byte array ''' Why include a message as an input?''' This could be useful for protocols that want to authorize on a compound statement, not just knowledge of a scalar. This allows the protocol to combine knowledge of the scalar and the statement. The algorithm ''GenerateProof(a, B, r, G, m)'' is defined as: * Fail if ''a = 0'' or ''a ≥ n''. * Fail if ''is_infinite(B)''. * Let ''A = a⋅G''. * Let ''C = a⋅B''. * Let ''t'' be the byte-wise xor of ''bytes(32, a)'' and ''hashBIP0374/aux(r)''. * Let ''m' = m if m is provided, otherwise an empty byte array''. * Let ''rand = hashBIP0374/nonce(t || cbytes(A) || cbytes(C) || m')''. ''' Why include the message in the rand computation?''' Not including the message in the rand computation could leak ''a'' if two proofs were constructed for the same ''a'', ''B'', and ''G'' but a different message ''m'' and an all-zero ''r''. * Let ''k = int(rand) mod n''. * Fail if ''k = 0''. * Let ''R1 = k⋅G''. * Let ''R2 = k⋅B''. * Let ''e = int(hashBIP0374/challenge(cbytes(A) || cbytes(B) || cbytes(C) || cbytes(G) || cbytes(R1) || cbytes(R2) || m'))''. * Let ''s = (k + e⋅a) mod n''. * Let ''proof = bytes(32, e) || bytes(32, s)''. * If ''VerifyProof(A, B, C, proof, G, m)'' (see below) returns failure, abort. * Return the proof ''proof''. === DLEQ Proof Verification === The following verifies the proof generated in the previous section. If the following algorithm succeeds, the points ''A'' and ''C'' were both generated from the same scalar. The former from multiplying by ''G'', and the latter from multiplying by ''B''. Input: * The public key of the secret key used in the proof generation ''A'': a point on the curve * The public key used in the proof generation ''B'': a point on the curve * The result of multiplying the secret and public keys used in the proof generation ''C'': a point on the curve * A proof ''proof'': a 64-byte array * The generator point used in the proof generation ''G'': a point on the curve ''' Why include the generator point G as an input?''' While all other BIPs have used the generator point from Secp256k1, passing it as an input here lets this algorithm be used for other curves. * An optional message ''m'': a 32-byte array ''' Why include a message as an input?''' This could be useful for protocols that want to authorize on a compound statement, not just knowledge of a scalar. This allows the protocol to combine knowledge of the scalar and the statement. The algorithm ''VerifyProof(A, B, C, proof, G, m)'' is defined as: * Fail if any of ''is_infinite(A)'', ''is_infinite(B)'', ''is_infinite(C)'', ''is_infinite(G)'' * Let ''e = int(proof[0:32])''. * Let ''s = int(proof[32:64])''; fail if ''s ≥ n''. * Let ''R1 = s⋅G - e⋅A''. * Fail if ''is_infinite(R1)''. * Let ''R2 = s⋅B - e⋅C''. * Fail if ''is_infinite(R2)''. * Let ''m' = m if m is provided, otherwise an empty byte array''. * Fail if ''e ≠ int(hashBIP0374/challenge(cbytes(A) || cbytes(B) || cbytes(C) || cbytes(G) || cbytes(R1) || cbytes(R2) || m'))''. * Return success iff no failure occurred before reaching this point. ==Backwards Compatibility== This proposal is compatible with all older clients. == Test Vectors and Reference Code == A reference python implementation is included [https://github.com/bitcoin/bips/blob/master/bip-0374/reference.py here]. It uses a vendored copy of the [https://github.com/secp256k1lab/secp256k1lab/ secp256k1lab] library at version 1.0.0 (commit [https://github.com/secp256k1lab/secp256k1lab/commit/44dc4bd893b8f03e621585e3bf255253e0e0fbfb 44dc4bd893b8f03e621585e3bf255253e0e0fbfb]). Test vectors can be generated by running ./bip-0374/gen_test_vectors.py which will produce a CSV file of random test vectors for both generating and verifying proofs. These can be run against the reference implementation with ./bip-0374/run_test_vectors.py. == Changelog == * 0.2.0 (2025-02-27): ** Add the message to the rand computation * 0.1.0 (2024-12-26): ** Initial version == Footnotes == == Acknowledgements == Thanks to josibake, Tim Ruffing, benma, stratospher, waxwing, Yuval Kogman and all others who participated in discussions on this topic. ================================================ FILE: bip-0375.mediawiki ================================================
  BIP: 375
  Layer: Applications
  Title: Sending Silent Payments with PSBTs
  Authors: Andrew Toth 
           Ava Chow 
           josibake 
  Status: Draft
  Type: Specification
  Assigned: 2025-01-08
  License: BSD-2-Clause
  Discussion: https://groups.google.com/g/bitcoindev/c/5G5wzqUXyk4
  Requires: 352, 370, 374
==Introduction== ===Abstract=== This document proposes additional fields and updated role responsibilities for BIP370 PSBTv2 which adds support for sending to silent payments as described in BIP352. ===Copyright=== This BIP is licensed under the 2-clause BSD license. ===Motivation=== Partially Signed Bitcoin Transaction Version 2 as described in BIP370 is not compatible with sending to silent payments as described in BIP352. In particular, the output script of a silent payment cannot be computed until after all transaction inputs have been added. Additionally, the silent payment outputs computed by a signer must be verifiable by other entities, otherwise funds could be sent to an incorrect output script. Therefore, new fields and role responsibilities must be added to carry, compute, and verify the silent payment data. ==Specification== This document specifies new fields and new field inclusion/exclusion requirements. The new global types are defined as follows: {| ! Name ! ! ! Description ! ! Description ! Versions Requiring Inclusion ! Versions Requiring Exclusion ! Versions Allowing Inclusion |- | Silent Payment Global ECDH Share | PSBT_GLOBAL_SP_ECDH_SHARE = 0x07 | <33 byte scan key> | The scan key that this ECDH share is for. | <33 byte share> | An ECDH share for a scan key. The ECDH shared is computed with ''a * B_scan'', where ''a'' is the sum of all private keys of all eligible inputs, and ''B_scan'' is the scan key of a recipient. | | 0 | 2 |- | Silent Payment Global DLEQ Proof | PSBT_GLOBAL_SP_DLEQ = 0x08 | <33 byte scan key> | The scan key that this proof covers. | <64-byte proof> | A BIP374 DLEQ proof computed for the matching ECDH share. | | 0 | 2 |} The new per-input types are defined as follows: {| ! Name ! ! ! Description ! ! Description ! Versions Requiring Inclusion ! Versions Requiring Exclusion ! Versions Allowing Inclusion |- | Silent Payment Input ECDH Share | PSBT_IN_SP_ECDH_SHARE = 0x1d | <33 byte scan key> | The scan key that this ECDH share is for. | <33 byte share> | An ECDH share for a scan key. The ECDH shared is computed with ''a * B_scan'', where ''a'' is the private key of the corresponding prevout public key, and ''B_scan'' is the scan key of a recipient. | | 0 | 2 |- | Silent Payment Input DLEQ Proof | PSBT_IN_SP_DLEQ = 0x1e | <33 byte scan key> | The scan key that this proof covers. | <64-byte proof> | A BIP374 DLEQ proof computed for the matching ECDH share. | | 0 | 2 |} The new per-output types are defined as follows: {| ! Name ! ! ! Description ! ! Description ! Versions Requiring Inclusion ! Versions Requiring Exclusion ! Versions Allowing Inclusion |- | Silent Payment Data | PSBT_OUT_SP_V0_INFO = 0x09 | None | No key data | <33 byte scan key> <33 byte spend key> | The scan and spend public keys from the silent payments address. | | 0 | 2 |- | Silent Payment Label | PSBT_OUT_SP_V0_LABEL = 0x0a | None | No key data | <32-bit little endian uint label> | The label to use to compute the spend key of the silent payments address to verify change. | | 0 | 2 |} PSBT_OUT_SCRIPT is modified to be optional for outputs in silent payments capable PSBTs. If this field is not included in the output, then the field PSBT_OUT_SP_V0_INFO must be included. If a PSBT_OUT_SCRIPT is not present for an output, then that output is being sent to a silent payment address represented by PSBT_OUT_SP_V0_INFO but the script has not yet been computed. If both PSBT_OUT_SCRIPT and PSBT_OUT_SP_V0_INFO are present for an output, then the PSBT_OUT_SCRIPT is the computed output script corresponding to the silent payment address in PSBT_OUT_SP_V0_INFO. If only PSBT_OUT_SCRIPT is present for an output, then the output is not being sent to a silent payment address. ===Unique Identification=== Silent payment capable PSBTs can be uniquely identified the same way as PSBTv2s, except when including silent payment outputs. If an output contains the PSBT_OUT_SP_V0_INFO field, it must use that field instead of PSBT_OUT_SCRIPT as the output script when creating the unsigned transaction used for unique identification. ''' Why use PSBT_OUT_SP_V0_INFO when serializing for a unique identifier?''' Since the same silent payment capable PSBT is valid whether or not a PSBT_OUT_SCRIPT is included in an output that has PSBT_OUT_SP_V0_INFO set, using the PSBT_OUT_SCRIPT if present for the unique identifier will cause malleability. The identifier will be different depending on whether PSBT_OUT_SCRIPT is present, so always using PSBT_OUT_SP_V0_INFO if it exists makes sure the PSBT is always identified uniquely. The PSBT_OUT_SP_V0_INFO should be serialized as a zero byte for the version, followed by the 33 bytes of the scan key and then 33 bytes for the spend key. ==Roles== This document modifies some existing roles. ===Constructor=== All rules must be followed from PSBTv2 for this role, with the following exception: When an output is added, it must have either PSBT_OUT_SCRIPT or PSBT_OUT_SP_V0_INFO, or both, set. Additionally to PSBTv2, the Constructor must also follow additional rules: Inputs spending an output with script using Segwit version > 1 may only be added if there are no outputs with PSBT_OUT_SP_V0_INFO set. Outputs with PSBT_OUT_SP_V0_INFO set may only be added if there are no inputs spending an output script using Segwit version > 1. ===Updater=== The updater should add a PSBT_IN_BIP32_DERIVATION for any p2wpkh, p2sh-p2wpkh, or p2pkh input so the public key is available for creating the ecdh_shared_secret when the private key is not known. If the updater does not want to reveal the fingerprint or derivation path, it can set the value of the field to zero. ====Change Detection==== Updaters may add two PSBT_OUT_BIP32_DERIVATION key-value-pairs with the corresponding derivation path of both the scan and spend keys. A label can be specified in PSBT_OUT_SP_V0_LABEL. The Signer can then use these fields to verify that the silent payment code is change. ===Signer=== All rules must be followed from PSBTv2 for this role. If there are any outputs with PSBT_OUT_SP_V0_INFO set, then the following additional rules must also be adhered to: If any input is spending an output with script using Segwit version > 1, the Signer must fail. For each output with PSBT_OUT_SP_V0_INFO set, the Signer should: * Compute and set an ECDH share and DLEQ proof for each input it has the private key for, or set a global ECDH share and DLEQ proof if it has private keys for all eligible inputs. * Verify the DLEQ proofs for all inputs it does not have the private keys for, or the global DLEQ proof if it is set. * If all eligible inputs have an ECDH share or the global ECDH share is set, compute and set the PSBT_OUT_SCRIPT. If the Signer sets any missing PSBT_OUT_SCRIPTs, it must set the Inputs Modifiable and Outputs Modifiable flags to False. If any output does not have PSBT_OUT_SCRIPT set, the Signer must not yet add a signature. The Signer should additionally compute the silent payment addresses, optionally showing this data to the user instead of the computed segwit v1 addresses. If a sighash type is provided and there are silent payment outputs present, the signer must fail if the sighash type is not SIGHASH_ALL. If a sighash type is not provided and there are silent payment outputs present, the signer must sign using SIGHASH_ALL. ''' Why use only SIGHASH_ALL?''' BIP352 allows signing with SIGHASH_NONE and SIGHASH_SINGLE. However, silent payment capable PSBTs compute the output scripts deterministically based on the number and position of silent payment codes with the same scan key. SIGHASH_NONE and SIGHASH_SINGLE allow changing the amount or position of silent payment codes with the same scan and spend keys, which would invalidate computed output scripts. ====Computing the ECDH Shares and DLEQ Proofs==== For each output with PSBT_OUT_SP_V0_INFO set, the Signer may generate a proof for other entities to generate the output scripts and verify that the output scripts were generated correctly. If the Signer has the private keys for all eligible inputs, the Signer should generate a global ECDH share for each scan key ''Bscan'' as follows: Using the notation from [https://github.com/bitcoin/bips/blob/master/bip-0352.mediawiki#specification BIP352] * Let ''an'' be the sum of the private keys ''a'' of all eligible inputs * Let ''C = an·Bscan'' Set the key as ''Bscan'' and the value as ''C'' for the PSBT_GLOBAL_SP_ECDH_SHARE field. Compute the DLEQ proof for ''C'' using [https://github.com/bitcoin/bips/blob/master/bip-0374.mediawiki#user-content-DLEQ_Proof_Generation BIP374 GenerateProof] and passing ''an'' as ''a'' and ''Bscan'' as ''B''. Set the key as ''Bscan'' and the value as the proof for the PSBT_GLOBAL_SP_DLEQ field. If the Signer has the private keys for some eligible inputs or does not want to create a global ECDH share, the Signer should generate a per-input ECDH share for each scan key ''Bscan'' as follows: Using the notation from [https://github.com/bitcoin/bips/blob/master/bip-0352.mediawiki#specification BIP352], for each eligible input: * Let ''a'' be the private key of the input * Let ''C = a·Bscan'' Set the key as ''Bscan'' and the value as ''C'' for the PSBT_IN_SP_ECDH_SHARE field of the input. Compute the DLEQ proof for ''C'' using [https://github.com/bitcoin/bips/blob/master/bip-0374.mediawiki#user-content-DLEQ_Proof_Generation BIP374 GenerateProof] and passing ''Bscan'' as ''B''. Set the key as ''Bscan'' and the value as the proof for the PSBT_IN_SP_DLEQ field of the input. ====Verifying the DLEQ Proof==== For each output with PSBT_OUT_SP_V0_INFO set, the Signer should verify the ECDH shares for all eligible inputs it does not have the private key for using the proofs provided by other Signers. If PSBT_GLOBAL_SP_ECDH_SHARE and PSBT_GLOBAL_SP_DLEQ are set, verify as follows: * Let ''An'' be the sum of the public keys ''A'' of all eligible inputs Using [https://github.com/bitcoin/bips/blob/master/bip-0374.mediawiki#dleq-proof-verification BIP374 VerifyProof] and passing ''A'' as ''An'', ''B'' as ''Bscan'', ''C'' as the value of PSBT_GLOBAL_SP_ECDH_SHARE, and ''proof'' as the value of PSBT_GLOBAL_SP_DLEQ. If PSBT_IN_SP_ECDH_SHARE and PSBT_IN_SP_DLEQ are set for a particular input, verify as follows: Using [https://github.com/bitcoin/bips/blob/master/bip-0374.mediawiki#dleq-proof-verification BIP374 VerifyProof] and passing ''A'' as the public key of the input, ''B'' as ''Bscan'', ''C'' as the value of PSBT_IN_SP_ECDH_SHARE, and ''proof'' as the value of PSBT_IN_SP_DLEQ. ====Computing the Output Scripts==== Compute the PSBT_OUT_SCRIPT using the procedure in [https://github.com/bitcoin/bips/blob/master/bip-0352.mediawiki#user-content-Creating_outputs BIP352] but substituting ''a·Bscan'' with the PSBT_GLOBAL_SP_ECDH_SHARE for that scan key if available, or the sum of all PSBT_IN_SP_ECDH_SHAREs for that scan key. If there are multiple silent payment codes with the same scan key, sort the codes lexicographically in ascending order to determine the ordering of the ''k'' value. If there are multiple silent payment codes with both the same scan and spend keys, sort the subgroup by output index in ascending order. ===Transaction Extractor=== For silent payment capable PSBTs, the transaction extractor should compute all output scripts for silent payment codes and verify they are correct using the ECDH shares and DLEQ proofs, otherwise fail. ==Backwards Compatibility== Silent payment capable PSBTs are backwards compatible with PSBTv2 once all outputs have PSBT_OUT_SCRIPT set. Otherwise they are not backwards compatible. ==Test Vectors== Todo ==Rationale== ==Reference implementation== Todo ================================================ FILE: bip-0379.md ================================================ ``` BIP: 379 Layer: Applications Title: Miniscript Authors: Pieter Wuille Andrew Poelstra Sanket Kanjalkar Antoine Poinsot Ava Chow Status: Draft Type: Informational Assigned: 2023-10-10 License: CC0-1.0 Requires: 380 ``` ## Abstract This document specifies Miniscript, a language for writing (a subset of) Bitcoin Scripts in a structured way, enabling analysis, composition, generic signing and more. ## Copyright This document is licensed under the Creative Commons CC0 1.0 Universal license. ## Motivation Bitcoin Script is an unusual stack-based language with many edge cases, designed for implementing spending conditions consisting of various combinations of signatures, hash locks, and time locks. Yet, despite being limited in functionality, it is still highly nontrivial to: * Given a combination of spending conditions, finding the most economical script to implement it. * Given two scripts, construct a script that implements a composition of their spending conditions (e.g. a multisig where one of the "keys" is another multisig). * Given a script, find out what spending conditions it permits. * Given a script and access to a sufficient set of private keys, construct a general satisfying witness for it. * Given a script, be able to predict the cost of spending an output. * Given a script, know whether particular resource limitations like the ops limit might be hit when spending. Miniscript functions as a representation for scripts that makes this sort of operations possible. It has a structure that allows composition. It is very easy to statically analyze for various properties (spending conditions, correctness, security properties, malleability, ...). It can be targeted by spending policy compilers. Finally, compatible scripts can easily be converted to Miniscript form - avoiding the need for additional metadata for e.g. signing devices that support it. ## Specification These specifications apply to P2WSH ([BIP 141](bip-0141.mediawiki)) and Tapscript ([BIP 342](bip-0342.mediawiki)) scripts, with only minor variations between the two. Differences are noted inline. Unless explicitly stated otherwise, specifications apply to both. P2SH and bare scripts are excluded from this specification. ### Translation Table Miniscript consists of a set of script *fragments* which are designed to be safely and correctly composable. This table shows all Miniscript *fragments* and their associated semantics and Bitcoin Script. Fragments that do not change the semantics of their subexpressions are called *wrappers*. Normal fragments use a `fragment(arg1,arg2,...)` notation, while wrappers are written using prefixes separated from other fragments by a colon. The colon is dropped between subsequent wrappers; e.g. `dv:older(144)` is the `d:` wrapper applied to the `v:` wrapper applied to the `older` fragment for 144 blocks. The `pk`, `pkh`, and `and_n` fragments and `t:`, `l:`, and `u:` wrappers are syntactic sugar for other Miniscripts, as listed in the table below. Note that `<20>` are in hex representation in this document. Miniscript fragments are expected to be used in [BIP 382](bip-0382.mediawiki) `wsh()` descriptors and [BIP 386](bip-0386.mediawiki) `tr()` descriptors. Key expressions are specified in [BIP 380](bip-0380.mediawiki#user-content-Key_Expressions). Additionally, BIPs 382 and 386 specify restrictions on key expressions and what they resolve to - these apply to key expressions in Miniscript. BIP 382's key expression restrictions apply to Miniscript in P2WSH contexts, and BIP 386's key expression restrictions apply to Miniscript in P2TR contexts. From a user's perspective, Miniscript is not a separate language, but rather a significant expansion of the descriptor language. | Semantics | Miniscript Fragment | Bitcoin Script |----------------------------------------------------------|-------------------------------|--------------- | false | `0` | `0` | true | `1` | `1` | check(key) | `pk_k(key)` | `` | | `pk_h(key)` | `DUP HASH160 EQUALVERIFY ` | | `pk(key)` = `c:pk_k(key)` | ` CHECKSIG` | | `pkh(key)` = `c:pk_h(key)` | `DUP HASH160 EQUALVERIFY CHECKSIG` | nSequence ≥ n (and compatible) | `older(n)` | ` CHECKSEQUENCEVERIFY` | nLockTime ≥ n (and compatible) | `after(n)` | ` CHECKLOCKTIMEVERIFY` | len(x) = 32 and SHA256(x) = h | `sha256(h)` | `SIZE <0x20> EQUALVERIFY SHA256 EQUAL` | len(x) = 32 and HASH256(x) = h | `hash256(h)` | `SIZE <0x20> EQUALVERIFY HASH256 EQUAL` | len(x) = 32 and RIPEMD160(x) = h | `ripemd160(h)` | `SIZE <0x20> EQUALVERIFY RIPEMD160 EQUAL` | len(x) = 32 and HASH160(x) = h | `hash160(h)` | `SIZE <0x20> EQUALVERIFY HASH160 EQUAL` | (X and Y) or Z | `andor(X,Y,Z)` | `[X] NOTIF [Z] ELSE [Y] ENDIF` | X and Y | `and_v(X,Y)` | `[X] [Y]` | | `and_b(X,Y)` | `[X] [Y] BOOLAND` | | `and_n(X,Y)` = `andor(X,Y,0)` | `[X] NOTIF 0 ELSE [Y] ENDIF` | X or Z | `or_b(X,Z)` | `[X] [Z] BOOLOR` | | `or_c(X,Z)` | `[X] NOTIF [Z] ENDIF` | | `or_d(X,Z)` | `[X] IFDUP NOTIF [Z] ENDIF` | | `or_i(X,Z)` | `IF [X] ELSE [Z] ENDIF` | X_1 + ... + X_n = k | `thresh(k,X_1,...,X_n)` | `[X_1] [X_2] ADD ... [X_n] ADD ... EQUAL` | check(key_1) + ... + check(key_n) = k *(P2WSH only)* | `multi(k,key_1,...,key_n)` | ` ... CHECKMULTISIG` | check(key_1) + ... + check(key_n) = k *(Tapscript only)* | `multi_a(k,key_1,...,key_n)` | ` CHECKSIG CHECKSIGADD ... CHECKSIGADD NUMEQUAL` | X (identities) | `a:X` | `TOALTSTACK [X] FROMALTSTACK` | | `s:X` | `SWAP [X]` | | `c:X` | `[X] CHECKSIG` | | `t:X` = `and_v(X,1)` | `[X] 1` | | `d:X` | `DUP IF [X] ENDIF` | | `v:X` | `[X] VERIFY (or VERIFY version of last opcode in [X])` | | `j:X` | `SIZE 0NOTEQUAL IF [X] ENDIF` | | `n:X` | `[X] 0NOTEQUAL` | | `l:X` = `or_i(0,X)` | `IF 0 ELSE [X] ENDIF` | | `u:X` = `or_i(X,0)` | `IF [X] ELSE 0 ENDIF` ### Type System Not every Miniscript expression can be composed with every other. Some return their result by putting true or false on the stack; others can only abort or continue. Some require subexpressions that consume an exactly known number of arguments, while others need a subexpression that has a nonzero top stack element to satisfy. To model all these properties, we define a correctness type system for Miniscript. #### Correctness Every miniscript expression has one of four basic types: "**B**" (base), "**V**" (verify), "**K**" (key) and "**W**" (wrapped). Then there are 5 type modifiers that guarantee additional properties: "**z**" (zero-arg), "**o**" (one-arg), "**n**" (nonzero), "**d**" (dissatisfiable), and "**u**" (unit). The following table lists the correctness requirements for each of the Miniscript expressions, and its type properties in function of those of their subexpressions. | Miniscript | Requires | Type | Properties |------------------------------|-------------------------------------------------------|-------------|----------- | `0` | | B | z; u; d | `1` | | B | z; u | `pk_k(key)` | | K | o; n; d; u | `pk_h(key)` | | K | n; d; u | `older(n)`, `after(n)` | 1 ≤ n < 231 | B | z | `sha256(h)` | | B | o; n; d; u | `ripemd160(h)` | | B | o; n; d; u | `hash256(h)` | | B | o; n; d; u | `hash160(h)` | | B | o; n; d; u | `andor(X,Y,Z)` | X is Bdu; Y and Z are both B, K, or V | same as Y/Z | z=zXzYzZ; o=zXoYoZ or oXzYzZ; u=uYuZ; d=dZ | `and_v(X,Y)` | X is V; Y is B, K, or V | same as Y | z=zXzY; o=zXoY or zYoX; n=nX or zXnY; u=uY | `and_b(X,Y)` | X is B; Y is W | B | z=zXzY; o=zXoY or zYoX; n=nX or zXnY; d=dXdY; u | `or_b(X,Z)` | X is Bd; Z is Wd | B | z=zXzZ; o=zXoZ or zZoX; d; u | `or_c(X,Z)` | X is Bdu; Z is V | V | z=zXzZ; o=oXzZ | `or_d(X,Z)` | X is Bdu; Z is B | B | z=zXzZ; o=oXzZ; d=dZ; u=uZ | `or_i(X,Z)` | both are B, K, or V | same as X/Z | o=zXzZ; u=uXuZ; d=dX or dZ | `thresh(k,X_1,...,X_n)` | 1 ≤ k ≤ n; X1 is Bdu; others are Wdu | B | z=all are z; o=all are z except one is o; d; u | `multi(k,key_1,...,key_n)` | 1 ≤ k ≤ n ≤ 20 | B | n; d; u | `multi_a(k,key_1,...,key_n)` | 1 ≤ k ≤ n | B | d; u | `a:X` | X is B | W | d=dX; u=uX | `s:X` | X is Bo | W | d=dX; u=uX | `c:X` | X is K | B | o=oX; n=nX; d=dX; u | `d:X` | X is Vz | B | o; n; d; *(Tapscript only)* u | `v:X` | X is B | V | z=zX; o=oX; n=nX | `j:X` | X is Bn | B | o=oX; n; d; u=uX | `n:X` | X is B | B | z=zX; o=oX; n=nX; d=dX; u #### Timelock Type Mixing There is one additional correctness property that Miniscript expressions must satisfy: the four timelock types (absolute time based, absolute height based, relative time based, and relative height based) must not be mixed in an incompatible way. Within `and` combinators and the `thresh` combinator where k >= 2, it is illegal for both absolute height based and time based timelocks to appear, or for both relative height based and time based timelocks to appear. For all other combinators, it is legal to mix timelock types. It is also always legal to mix absolute and relative timelocks (even if one is height based and the other is time based). #### Malleability Malleability is the ability for a third party (someone who does *not* hold a participating private key) to modify an existing satisfaction into another valid satisfaction. To analyze the malleability guarantees of a script we define three additional type properties: "**s**" (signed), "**f**" (forced) and "**e**" (expressive). The following table lists the malleability properties and requirement of each fragment. | Miniscript | Requires | Properties |------------------------------|---------------------------------------------------------------------|----------- | `0` | | s, e | `1` | | f | `pk_k(key)` | | s, e | `pk_h(key)` | | s, e | `older(n)` | | f | `after(n)` | | f | `sha256(h)` | | | `ripemd160(h)` | | | `hash256(h)` | | | `hash160(h)` | | | `andor(X,Y,Z)` | eX and (sX or sY or sZ) | s=sZ and (sX or sY); f=fZ and (sX or fY); e=eZ and (sX or fY) | `and_v(X,Y)` | | s=sX or sY; f=sX or fY | `and_b(X,Y)` | | s=sX or sY; f=fXfY or sXfX or sYfY; e=eXeYsXsY | `or_b(X,Z)` | eXeZ and (sX or sZ) | s=sXsZ; e | `or_c(X,Z)` | eX and (sX or sZ) | s=sXsZ; f | `or_d(X,Z)` | eX and (sX or sZ) | s=sXsZ; f=fZ; e=eZ | `or_i(X,Z)` | sX or sZ | s=sXsZ; f=fXfZ; e=eXfZ or eZfX | `thresh(k,X_1,...,X_n)` | all are e; at most k are non-s | s=at most k-1 are non-s; e=all are s | `multi(k,key_1,...,key_n)` | | s; e | `multi_a(k,key_1,...,key_n)` | | s; e | `a:X` | | s=sX; f=fX; e=eX | `s:X` | | s=sX; f=fX; e=eX | `c:X` | | s; f=fX; e=eX | `d:X` | | s=sX; e | `v:X` | | s=sX; f | `j:X` | | s=sX; e=fX | `n:X` | | s=sX; f=fX; e=eX ### Satisfaction The following table shows all valid satisfactions and dissatisfactions for every Miniscript, using satisfactions and dissatisfactions of its subexpressions. Multiple possibilities are separated by semicolons. Some options are inefficient and provably unnecessary to the satisfaction algorithm described below, but are valid according to script rules and could be used by a malleator or other non-standard actor. These are called *non-canonical* options, and are listed for completeness, but ~~[struckthrough]~~. The fragments where a satisfaction or dissatisfaction does not exist will contain *(none)*. The fragments where the satisfaction or dissatisfaction is to provide no data will contain *(empty)*. | Miniscript | Dissatisfactions (dsat) | Satisfactions (sat) |------------------------------|---------------------------------------------------------|-------------------- | `0` | *(empty)* | *(none)* | `1` | *(none)* | *(empty)* | `pk_k(key)` | 0 | sig | `pk_h(key)` | 0 key | sig key | `older(n)` | *(none)* | *(empty)* | `after(n)` | *(none)* | *(empty)* | `sha256(h)` | any 32-byte vector except the preimage | preimage | `ripemd160(h)` | any 32-byte vector except the preimage | preimage | `hash256(h)` | any 32-byte vector except the preimage | preimage | `hash160(h)` | any 32-byte vector except the preimage | preimage | `andor(X,Y,Z)` | dsat(Z) dsat(X); ~~[dsat(Y) sat(X)]~~ | sat(Y) sat(X); sat(Z) dsat(X) | `and_v(X,Y)` | *(none)*; ~~[dsat(Y) sat(X)]~~ | sat(Y) sat(X) | `and_b(X,Y)` | dsat(Y) dsat(X); ~~[sat(Y) dsat(X)]; [dsat(Y) sat(X)]~~ | sat(Y) sat(X) | `or_b(X,Z)` | dsat(Z) dsat(X) | dsat(Z) sat(X); sat(Z) dsat(X); ~~[sat(Z) sat(X)]~~ | `or_c(X,Z)` | *(none)* | sat(X); sat(Z) dsat(X) | `or_d(X,Z)` | dsat(Z) dsat(X) | sat(X); sat(Z) dsat(X) | `or_i(X,Z)` | dsat(X) 1; dsat(Z) 0 | sat(X) 1; sat(Z) 0 | `thresh(k,X_1,...,X_n)` | All dsats; ~~[Sats/dsats with 1 ≤ #(sats) ≠ k]~~ | Sats/dsats with #(sats) = k | `multi(k,key_1,...,key_n)` | 0 0 ... 0 (k+1 times) | 0 sig ... sig | `multi_a(k,key_1,...,key_n)` | 0 ... 0 (n times); ~~[sig/0 with #(sig) ≠ k]~~ | sig/0 with #(sig) = k and #(sigs/0) = n | `a:X` | dsat(X) | sat(X) | `s:X` | dsat(X) | sat(X) | `c:X` | dsat(X) | sat(X) | `d:X` | 0 | sat(X) 1 | `v:X` | *(none)* | sat(X) | `j:X` | 0; ~~[dsat(X) (if nonzero top stack)]~~ | sat(X) | `n:X` | dsat(X) | sat(X) #### Non-malleable Satisfaction Algorithm In order to produce non-malleable satisfactions we make use of a function that returns the optimal satisfaction and dissatisfaction for a given expression (if any exist), or a special DONTUSE ("don't use") value, together with an optional HASSIG ("has signature") marker that tracks whether the solution contains at least one signature. To implement the function: * Invoke the function recursively for all subexpressions, obtaining all their satisfactions/dissatisfactions. * Iterate over all the valid satisfactions/dissatisfactions in the table above (including the non-canonical ones), taking into account: * The dissatisfactions for `sha256`, `ripemd160`, `hash256`, and `hash160` are always malleable, so instead use DONTUSE there. * The non-canonical options for `and_b`, `or_b`, and `thresh` are always overcomplete, so instead use DONTUSE there as well (with HASSIG flag if the original non-canonical solution had one). * The satisfactions for `pk_k`, `pk_h`, and `multi` can be marked HASSIG. * When constructing solutions by combining results for subexpressions, the result is DONTUSE if any of the constituent results is DONTUSE. Furthermore, the result gets the HASSIG tag if any of the constituents does. * If among all valid solutions (including DONTUSE ones) more than one does not have the HASSIG marker, return DONTUSE. * If instead exactly one does not have the HASSIG marker, return that solution. * If all valid solutions have the HASSIG marker, but all of them are DONTUSE, return DONTUSE-HASSIG. The HASSIG marker is important because while this represents a choice between multiple options that would cause malleability if used, they are not available to the attacker, and we may be able to avoid them entirely still. * Otherwise, all not-DONTUSE options are valid, so return the smallest one (in terms of witness size). To produce an overall satisfaction, invoke the function on the toplevel expression. If no valid satisfaction is returned, or it is DONTUSE, fail. Otherwise, if any timelocking is used in the script but the result does not have the HASSIG flag, also fail. If the satisfaction is both not DONTUSE and HASSIG, return it. ## Discussion ## Security Miniscript primarily aims to provide guarantees on the correctness of a Bitcoin Script. That is, to guarantee **consensus soundness** and **standardness completeness**. Consensus soundness means it is not possible to construct a consensus-valid witness for a Bitcoin Script unless the Miniscript spending conditions are met. Standardness completeness means a standardness-valid witness can be created for all spending paths of a Miniscript, assuming the resource limits are respected and there is no timelock mixing. Additionally, Miniscript can guarantee the non-malleability and maximum size of a witness. These can assist in assessing the soundness of protocols where transaction fees (and therefore transaction size) are security-critical parameters. Hash preimages are constrained to 32 bytes to disallow various forms of griefing, including making non-standard (un-relayable) transactions, consensus-invalid swaps across blockchains, as well as ensure that satisfaction cost can be accurately calculated. In order for these properties to not just apply to script, but to an entire transaction, it's important that the witness commits to all data relevant for verification. In practice this means that scripts whose conditions can be met without any digital signature are insecure. Besides being trivially insecure, note how a transaction lacking a signature check allows an attacker to change its nLockTime and nSequence fields to meet additional timelock conditions. ### Type System To statically verify the correctness and malleability guarantees discussed in the previous section, we define a type system. See the specifications above for a reference of each fragment's requirements and properties. Here we give more information about each type. Every expression has one of four basic types: * "**B**" Base expressions. These take their inputs from the top of the stack. When satisfied, they push a nonzero value of up to 4 bytes onto the stack. When dissatisfied, they push an exact 0 onto the stack (if dissatisfaction without aborting is possible at all). This type is used for most expressions, and required for the top level expression. An example is `older(n)` = ` CHECKSEQUENCEVERIFY`. * "**V**" Verify expressions. Like "B", these take their inputs from the top of the stack. Upon satisfaction however, they continue without pushing anything. They cannot be dissatisfied (will abort instead). A "V" can be obtained using the `v:` wrapper on a "B" expression, or by combining other "V" expressions using `and_v`, `or_i`, `or_c`, or `andor`. An example is `v:pk(key)` = ` CHECKSIGVERIFY`. * "**K**" Key expressions. They again take their inputs from the top of the stack, but instead of verifying a condition directly they always push a public key onto the stack, for which a signature is still required to satisfy the expression. A "K" can be converted into a "B" using the `c:` wrapper. An example is `pk_h(key)` = `DUP HASH160 EQUALVERIFY`. * "**W**" Wrapped expressions. They take their inputs from one below the top of the stack, and push a nonzero (in case of satisfaction) or zero (in case of dissatisfaction) either on top of the stack, or one below. So for example a 3-input "W" would take the stack "A B C D E F" and turn it into "A B F 0" or "A B 0 F" in case of dissatisfaction, and "A B F n" or "A B n F" in case of satisfaction (with n a nonzero value). Every "W" is either `s:B` (SWAP B) or `a:B` (TOALTSTACK B FROMALTSTACK). An example is `s:pk(key)` = `SWAP CHECKSIG`. Then there are 6 type modifiers, which guarantee additional properties: * "**z**" Zero-arg: this expression always consumes exactly 0 stack elements. * "**o**" One-arg: this expression always consumes exactly 1 stack element. * "**n**" Nonzero: this expression always consumes at least 1 stack element, no satisfaction for this expression requires the top input stack element to be zero. * "**d**" Dissatisfiable: a dissatisfaction for this expression can unconditionally be constructed. This implies the dissatisfaction cannot include any signature or hash preimage, and cannot rely on timelocks being satisfied. * "**u**" Unit: when satisfied, this expression will put an exact 1 on the stack (as opposed to any nonzero value). * "**k**" No timelock mixing. This expression does not contain a mix of heightlock and timelock of the same type. If the miniscript does not have the "k" property, the miniscript template will not match the user expectation of the corresponding spending policy. Finally to analyze malleability guarantees we introduce 3 new type modifiers: * "**s**" Signed: satisfying this expression always requires a signature (predicting whether all satisfactions will be HASSIG). * "**f**" Forced: dissatisfying this expression always requires a signature (predicting whether all dissatisfactions will be HASSIG). * "**e**" Expressive: this requires a unique unconditional dissatisfaction to exist, and forces all conditional dissatisfactions (if any) to require a signature. ### Malleability Since Segwit, malleating a transaction no longer breaks the validity of unconfirmed descendant transactions. However, unintentional malleability may still have a number of much weaker undesirable effects. If a witness can be stuffed with additional data, the transaction's feerate will go down, potentially to the point where its ability to propagate and get confirmed is impacted. Additionally, malleability can be exploited to add roundtrips to BIP152 block propagation, by trying to get different miners to mine different versions of the same transaction. Finally, malleability may interfere with the usage of hash locks as a mechanism for publishing preimages. Using the malleability type properties it is possible to determine statically whether a script can be non-malleably satisfied under all circumstances. In many cases it is reasonable to only accept such guaranteed-non-malleable scripts, as unexpected behavior can occur when using other scripts. For example, when running the non-malleable satisfaction algorithm above, adding available preimages, or increasing the nLockTime/nSequence values actually may make it fail where it succeeded before. This is because a larger set of met conditions may mean an existing satisfaction goes from non-malleable to malleable. Restricting things to scripts that are guaranteed to be satisfiable in a non-malleable way avoids this problem. When analysing Miniscripts for resource limits, restricting yourself to just non-malleable solutions (or even non-malleable scripts) also leads to tighter bounds, as all non-canonical satisfactions and dissatisfactions can be left out of consideration. The malleability analysis makes the following assumptions: * The attacker does not have access to any of the private keys of public keys that participate in the Script. Participants with private keys inherently have the ability to produce different satisfactions by creating multiple signatures. While it is also interesting to study the impact rogue participants can have, we treat it as a distinct problem. * The attacker only has access to hash preimages that honest users have access to as well. This is a reasonable assumption because hash preimages are revealed once globally, and then available to everyone. On the other hand, making the assumption that attackers may have access to more preimages than honest users makes a large portion of scripts impossible to satisfy in a non-malleable way. * The attacker gets to see exactly one satisfying witness of any transaction. If he sees multiple, it becomes possible for the attacker to mix and match different satisfactions. This is very hard to reason about. * We restrict this analysis to scripts where no public key is repeated. If signatures constructed for one part of the script can be bound to other checks in the same script, a variant of the mixing from the previous point becomes available that is equally hard to reason about. Furthermore this situation can be avoided by using separate keys. * The attacker is constrained by common standardness rules. A miner may be able to malleate a witness considered non-malleable by Miniscript. #### Non-Malleable Satisfaction Malleable satisfactions or dissatisfactions appear whenever options are available to attackers distinct from the one taken by honest users. This can happen for multiple reasons: 1. Two or more options for a satisfaction or dissatisfaction are listed in the table above which are both available to attackers directly. Regardless of which option is used in the honest solution, the attacker can change the solution to the other one. 2. Two or more options for a satisfaction or dissatisfaction are listed in the table above, only one of which is available to attackers, but the honest solution uses another one. In that case, the attacker can modify the solution to pick the one available to him. 3. The honest users pick a solution that contains a satisfaction which can be turned into a dissatisfaction without invalidating the overall witness. Those are called overcomplete solutions. Because we assume attackers never have access to private keys, we can treat any solution that includes a signature as one that is unavailable to attackers. For others, the worst case is that the attacker has access to every solution the honest users have, but no others: for preimages this is an explicit assumption, while timelock availability is determined by the nLockTime and nSequence fields in the transaction. As long as the overall satisfaction includes at least one signature, those values are fixed, and timelock availability is identical for attackers and honest users. The description of the non-malleable satisfaction algorithm can be used to show that no non-canonical solutions listed in the satisfaction table can occur inside non-malleable satisfaction: * Some of the non-canonical options (the `or_b`, `and_b`, and `thresh` ones) are overcomplete, and thus can clearly not appear in non-malleable satisfactions. * The fact that non-"d" expressions cannot be dissatisfied in valid witnesses rules out the usage of the non-canonical `and_v` dissatisfaction. * "d" expressions are defined to be unconditionally dissatisfiable, which implies that for those a non-HASSIG dissatisfaction must exist. Non-HASSIG solutions must be preferred over HASSIG ones (reason 2), and when multiple non-HASSIG ones exist, none can be used (reason 1). This lets us rule out the other non-canonical options in the table: * `j:X` is always "d", its non-HASSIG dissatisfaction "0" always exists, and thus rules out any usage of "dsat(X)". * If `andor(X,Y,Z)` is "d", a non-HASSIG dissatisfaction "dsat(Z) dsat(X)" must exist, and thus rules out any usage of "dsat(Y) sat(X)". * If `and_b(X,Y)` is "d", a non-HASSIG dissatisfaction "dsat(Y) dsat(X)" must exist, and thus rules out any usage of "dsat(Y) sat(X)" and "sat(Y) dsat(X)". Those are also overcomplete. * `thresh(k,...)` is always "d", a non-HASSIG dissatisfaction with just dissatisfactions must exist due to typing rules, and thus rules out usage of the other dissatisfactions. They are also overcomplete. ### Resource Limits Various types of Bitcoin Scripts have different resource limitations, either through consensus or standardness. Some of them affect otherwise valid Miniscripts: * In P2WSH, scripts larger than 3600 bytes are invalid by standardness. In Tapscript, scripts are implicitly bounded by the maximum size of a block (1 million virtual bytes). * In P2WSH, script satisfactions where the total number of non-push opcodes plus the number of keys participating in all executed `CHECKMULTISIG` is above 201 are invalid by consensus. * In both Tapscript and P2WSH, script satisfactions which make the stack exceed 1000 elements before or during execution are invalid. * In P2WSH, satisfactions with a witness consisting of over 100 stack elements (excluding the script itself) are invalid by standardness. A static analysis can be performed on a Miniscript to verify if none, all or any of the spending paths hit any of the limits. ## Test Vectors TBD ## Backwards Compatibility Miniscript's syntax is compatible with BIP 380 Output Script Descriptors, and should be considered an extension to it that provides a new type of Script expression that is only valid in `wsh()` and `tr()` contexts. As these are wholly new expressions, they are not compatible with any existing implementation of descriptors. Additionally, the scripts produced are unlikely to be standard scripts. The `pk()`, `pkh()`, `multi()`, and `multi_a()` fragments overlap with existing descriptors. These parse to the same semantic meanings as those descriptors and produce the same scripts. ## Reference Implementation A first reference implementation and documentation for Miniscript in P2WSH was originally published at https://github.com/sipa/miniscript . The reference implementation for Miniscript in P2WSH was introduced in Bitcoin Core through PRs [24147](https://github.com/bitcoin/bitcoin/pull/24147), [24148](https://github.com/bitcoin/bitcoin/pull/24148), and [24149](https://github.com/bitcoin/bitcoin/pull/24149). The last one to be merged was released in Bitcoin Core version 25.0. The reference implementation for Miniscript in Tapscript was introduced in Bitcoin Core in PR [27255](https://github.com/bitcoin/bitcoin/pull/27255). This PR was merged and released in Bitcoin Core version 26.0. ================================================ FILE: bip-0380.mediawiki ================================================
  BIP: 380
  Layer: Applications
  Title: Output Script Descriptors General Operation
  Authors: Pieter Wuille 
           Ava Chow 
  Status: Deployed
  Type: Informational
  Assigned: 2021-06-27
  License: BSD-2-Clause
==Abstract== Output Script Descriptors are a simple language which can be used to describe collections of output scripts. There can be many different descriptor fragments and functions. This document describes the general syntax for descriptors, descriptor checksums, and common expressions. ==Copyright== This BIP is licensed under the BSD 2-clause license. ==Motivation== Bitcoin wallets traditionally have stored a set of keys which are later serialized and mutated to produce the output scripts that the wallet watches and the addresses it provides to users. Typically backups have consisted of solely the private keys, nowadays primarily in the form of BIP 39 mnemonics. However this backup solution is insufficient, especially since the introduction of Segregated Witness which added new output types. Given just the private keys, it is not possible for restored wallets to know which kinds of output scripts and addresses to produce. This has lead to incompatibilities between wallets when restoring a backup or exporting data for a watch only wallet. Further complicating matters are BIP 32 derivation paths. Although BIPs 44, 49, and 84 have specified standard BIP 32 derivation paths for different output scripts and addresses, not all wallets support those derivation paths nor use them. The lack of derivation path information in these backups and exports leads to further incompatibilities between wallets. Current solutions to these issues have not been generic and can be viewed as being layer violations. Solutions such as introducing different version bytes for extended key serialization both are a layer violation (key derivation should be separate from script type meaning) and specific only to a particular derivation path and script type. Output Script Descriptors introduce a generic solution to these issues. Script types are specified explicitly through the use of Script Expressions. Key derivation paths are specified explicitly in Key Expressions. These allow for creating wallet backups and exports which specify the exact scripts, subscripts (redeemScript, witnessScript, etc.), and keys to produce. With the general structure specified in this BIP, new Script Expressions can be introduced as new script types are added. Lastly, the use of common terminology and existing standards allow for Output Script Descriptors to be engineer readable so that the results can be understood at a glance. ==Specification== Descriptors consist of several types of expressions. The top level expression is a SCRIPT. This expression may be followed by #CHECKSUM, where CHECKSUM is an 8 character alphanumeric descriptor checksum. Although the checksum is optional for parsing, applications may choose to reject descriptors that do not contain a checksum. ===Script Expressions=== Script Expressions (denoted SCRIPT) are expressions which correspond directly with a Bitcoin script. These expressions are written as functions and take arguments. Such expressions have a script template which is filled with the arguments correspondingly. Expressions are written with a human readable identifier string with the arguments enclosed with parentheses. The identifier string should be alphanumeric and may include underscores. The arguments to a script expression are defined by that expression itself. They could be a script expression, a key expression, or some other expression entirely. ===Key Expressions=== A common expression used as an argument to script expressions are key expressions (denoted KEY). These represent a public or private key and, optionally, information about the origin of that key. Key expressions can only be used as arguments to script expressions. Key expressions consist of: * Optionally, key origin information, consisting of: ** An open bracket [ ** Exactly 8 hex characters for the fingerprint of the key where the derivation starts (see BIP 32 for details) ** Followed by zero or more /NUM or /NUMh path elements to indicate the unhardened or hardened derivation steps between the fingerprint and the key that follows. ** A closing bracket ] * Followed by the actual key, which is either: ** A hex encoded public key, which depending on the script expression, may be either: *** 66 hex character string beginning with 02 or 03 representing a compressed public key *** 130 hex character string beginning with 04 representing an uncompressed public key ** A [[https://en.bitcoin.it/wiki/Wallet_import_format|WIF]] encoded private key ** xpub encoded extended public key or xprv encoded extended private key (as defined in BIP 32) *** Followed by zero or more /NUM or /NUMh path elements indicating BIP 32 derivation steps to be taken after the given extended key. *** Optionally followed by a single /* or /*h final step to denote all direct unhardened or hardened children. If the KEY is a BIP 32 extended key, before output scripts can be created, child keys must be derived using the derivation information that follows the extended key. When the final step is /* or /*', an output script will be produced for every child key index. The derived key must be not be serialized as an uncompressed public key. Script Expressions may have further requirements on how derived public keys are serialized for script creation. In the above specification, the hardened indicator h may be replaced with alternative hardened indicator of '. ====Normalization of Key Expressions with Hardened Derivation==== When a descriptor is exported without private keys, it is necessary to do additional derivation to remove any intermediate hardened derivation steps for the exported descriptor to be useful. The exporter should derive the extended public key at the last hardened derivation step and use that extended public key as the key in the descriptor. The derivation steps that were taken to get to that key must be added to the previous key origin information. If there is no key origin information, then one must be added for the newly derived extended public key. If the final derivation is hardened, then it is not necessary to do additional derivation. ===Character Set=== The expressions used in descriptors must only contain characters within this character set so that the descriptor checksum will work. The allowed characters are:
0123456789()[],'/*abcdefgh@:$%{}
IJKLMNOPQRSTUVWXYZ&+-.;<=>?!^_|~
ijklmnopqrstuvwxyzABCDEFGH`#"\
Note that on the last line is a space character. This character set is written as 3 groups of 32 characters in this specific order so that the checksum below can identify more errors. The first group are the most common "unprotected" characters (i.e. things such as hex and keypaths that do not already have their own checksums). Case errors cause an offset that is a multiple of 32 while as many alphabetic characters are in the same group while following the previous restrictions. ===Checksum=== Following the top level script expression is a single octothorpe (#) followed by the 8 character checksum. The checksum is an error correcting checksum similar to bech32. The checksum has the following properties: * Mistakes in a descriptor string are measured in "symbol errors". The higher the number of symbol errors, the harder it is to detect: ** An error substituting a character from 0123456789()[],'/*abcdefgh@:$%{} for another in that set always counts as 1 symbol error. *** Note that hex encoded keys are covered by these characters. Extended keys (xpub and xprv) use other characters too, but also have their own checksum mechanism. *** SCRIPT expression function names use other characters, but mistakes in these would generally result in an unparsable descriptor. ** A case error always counts as 1 symbol error. ** Any other 1 character substitution error counts as 1 or 2 symbol errors. * Any 1 symbol error is always detected. * Any 2 or 3 symbol error in a descriptor of up to 49154 characters is always detected. * Any 4 symbol error in a descriptor of up to 507 characters is always detected. * Any 5 symbol error in a descriptor of up to 77 characters is always detected. * Is optimized to minimize the chance of a 5 symbol error in a descriptor up to 387 characters is undetected * Random errors have a chance of 1 in 240 of being undetected. The checksum itself uses the same character set as bech32: qpzry9x8gf2tvdw0s3jn54khce6mua7l Valid descriptor strings with a checksum must pass the criteria for validity specified by the Python3 code snippet below. The function descsum_check must return true when its argument s is a descriptor consisting in the form SCRIPT#CHECKSUM.
INPUT_CHARSET = "0123456789()[],'/*abcdefgh@:$%{}IJKLMNOPQRSTUVWXYZ&+-.;<=>?!^_|~ijklmnopqrstuvwxyzABCDEFGH`#\"\\ "
CHECKSUM_CHARSET = "qpzry9x8gf2tvdw0s3jn54khce6mua7l"
GENERATOR = [0xf5dee51989, 0xa9fdca3312, 0x1bab10e32d, 0x3706b1677a, 0x644d626ffd]

def descsum_polymod(symbols):
    """Internal function that computes the descriptor checksum."""
    chk = 1
    for value in symbols:
        top = chk >> 35
        chk = (chk & 0x7ffffffff) << 5 ^ value
        for i in range(5):
            chk ^= GENERATOR[i] if ((top >> i) & 1) else 0
    return chk

def descsum_expand(s):
    """Internal function that does the character to symbol expansion"""
    groups = []
    symbols = []
    for c in s:
        if not c in INPUT_CHARSET:
            return None
        v = INPUT_CHARSET.find(c)
        symbols.append(v & 31)
        groups.append(v >> 5)
        if len(groups) == 3:
            symbols.append(groups[0] * 9 + groups[1] * 3 + groups[2])
            groups = []
    if len(groups) == 1:
        symbols.append(groups[0])
    elif len(groups) == 2:
        symbols.append(groups[0] * 3 + groups[1])
    return symbols

def descsum_check(s):
    """Verify that the checksum is correct in a descriptor"""
    if s[-9] != '#':
        return False
    if not all(x in CHECKSUM_CHARSET for x in s[-8:]):
        return False
    symbols = descsum_expand(s[:-9]) + [CHECKSUM_CHARSET.find(x) for x in s[-8:]]
    return descsum_polymod(symbols) == 1
This implements a BCH code that has the properties described above. The entire descriptor string is first processed into an array of symbols. The symbol for each character is its position within its group. After every 3rd symbol, a 4th symbol is inserted which represents the group numbers combined together. This means that a change that only affects the position within a group, or only a group number change, will only affect a single symbol. To construct a valid checksum given a script expression, the code below can be used:
def descsum_create(s):
    """Add a checksum to a descriptor without"""
    symbols = descsum_expand(s) + [0, 0, 0, 0, 0, 0, 0, 0]
    checksum = descsum_polymod(symbols) ^ 1
    return s + '#' + ''.join(CHECKSUM_CHARSET[(checksum >> (5 * (7 - i))) & 31] for i in range(8))

==Test Vectors== The following tests cover the checksum and character set: * Valid checksum: raw(deadbeef)#89f8spxm * No checksum: raw(deadbeef) * Missing checksum: raw(deadbeef)# * Too long checksum (9 chars): raw(deadbeef)#89f8spxmx * Too short checksum (7 chars): raw(deadbeef)#89f8spx * Error in payload: raw(deedbeef)#89f8spxm * Error in checksum: raw(deedbeef)##9f8spxm * Invalid characters in payload: raw(Ü)#00000000 The following tests cover key expressions: Valid expressions: * Compressed public key: 0260b2003c386519fc9eadf2b5cf124dd8eea4c4e68d5e154050a9346ea98ce600 * Uncompressed public key: 04a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd5b8dec5235a0fa8722476c7709c02559e3aa73aa03918ba2d492eea75abea235 * Public key with key origin: [deadbeef/0h/0h/0h]0260b2003c386519fc9eadf2b5cf124dd8eea4c4e68d5e154050a9346ea98ce600 * Public key with key origin (' as hardened indicator): [deadbeef/0'/0'/0']0260b2003c386519fc9eadf2b5cf124dd8eea4c4e68d5e154050a9346ea98ce600 * Public key with key origin (mixed hardened indicator): [deadbeef/0'/0h/0']0260b2003c386519fc9eadf2b5cf124dd8eea4c4e68d5e154050a9346ea98ce600 * WIF uncompressed private key 5KYZdUEo39z3FPrtuX2QbbwGnNP5zTd7yyr2SC1j299sBCnWjss * WIF compressed private key L4rK1yDtCWekvXuE6oXD9jCYfFNV2cWRpVuPLBcCU2z8TrisoyY1 * Extended public key: xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL * Extended public key with key origin: [deadbeef/0h/1h/2h]xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL * Extended public key with derivation: [deadbeef/0h/1h/2h]xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL/3/4/5 * Extended public key with derivation and children: [deadbeef/0h/1h/2h]xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL/3/4/5/* * Extended public key with hardened derivation and unhardened children: xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL/3h/4h/5h/* * Extended public key with hardened derivation and children: xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL/3h/4h/5h/*h * Extended public key with key origin, hardened derivation and children: [deadbeef/0h/1h/2]xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL/3h/4h/5h/*h * Extended private key: xprvA1RpRA33e1JQ7ifknakTFpgNXPmW2YvmhqLQYMmrj4xJXXWYpDPS3xz7iAxn8L39njGVyuoseXzU6rcxFLJ8HFsTjSyQbLYnMpCqE2VbFWc * Extended private key with key origin: [deadbeef/0h/1h/2h]xprvA1RpRA33e1JQ7ifknakTFpgNXPmW2YvmhqLQYMmrj4xJXXWYpDPS3xz7iAxn8L39njGVyuoseXzU6rcxFLJ8HFsTjSyQbLYnMpCqE2VbFWc * Extended private key with derivation: [deadbeef/0h/1h/2h]xprvA1RpRA33e1JQ7ifknakTFpgNXPmW2YvmhqLQYMmrj4xJXXWYpDPS3xz7iAxn8L39njGVyuoseXzU6rcxFLJ8HFsTjSyQbLYnMpCqE2VbFWc/3/4/5 * Extended private key with derivation and children: [deadbeef/0h/1h/2h]xprvA1RpRA33e1JQ7ifknakTFpgNXPmW2YvmhqLQYMmrj4xJXXWYpDPS3xz7iAxn8L39njGVyuoseXzU6rcxFLJ8HFsTjSyQbLYnMpCqE2VbFWc/3/4/5/* * Extended private key with hardened derivation and unhardened children: xprvA1RpRA33e1JQ7ifknakTFpgNXPmW2YvmhqLQYMmrj4xJXXWYpDPS3xz7iAxn8L39njGVyuoseXzU6rcxFLJ8HFsTjSyQbLYnMpCqE2VbFWc/3h/4h/5h/* * Extended private key with hardened derivation and children: xprvA1RpRA33e1JQ7ifknakTFpgNXPmW2YvmhqLQYMmrj4xJXXWYpDPS3xz7iAxn8L39njGVyuoseXzU6rcxFLJ8HFsTjSyQbLYnMpCqE2VbFWc/3h/4h/5h/*h * Extended private key with key origin, hardened derivation and children: [deadbeef/0h/1h/2]xprvA1RpRA33e1JQ7ifknakTFpgNXPmW2YvmhqLQYMmrj4xJXXWYpDPS3xz7iAxn8L39njGVyuoseXzU6rcxFLJ8HFsTjSyQbLYnMpCqE2VbFWc/3h/4h/5h/*h Invalid expression: * Children indicator in key origin: [deadbeef/0h/0h/0h/*]0260b2003c386519fc9eadf2b5cf124dd8eea4c4e68d5e154050a9346ea98ce600 * Trailing slash in key origin: [deadbeef/0h/0h/0h/]0260b2003c386519fc9eadf2b5cf124dd8eea4c4e68d5e154050a9346ea98ce600 * Too short fingerprint: [deadbef/0h/0h/0h]0260b2003c386519fc9eadf2b5cf124dd8eea4c4e68d5e154050a9346ea98ce600 * Too long fingerprint: [deadbeeef/0h/0h/0h]0260b2003c386519fc9eadf2b5cf124dd8eea4c4e68d5e154050a9346ea98ce600 * Invalid hardened indicators: [deadbeef/0f/0f/0f]0260b2003c386519fc9eadf2b5cf124dd8eea4c4e68d5e154050a9346ea98ce600 * Invalid hardened indicators: [deadbeef/-0/-0/-0]0260b2003c386519fc9eadf2b5cf124dd8eea4c4e68d5e154050a9346ea98ce600 * Invalid hardened indicators: [deadbeef/0H/0H/0H]0260b2003c386519fc9eadf2b5cf124dd8eea4c4e68d5e154050a9346ea98ce600 * Invalid hardened indicators: [deadbeef/0h/1h/2]xprvA1RpRA33e1JQ7ifknakTFpgNXPmW2YvmhqLQYMmrj4xJXXWYpDPS3xz7iAxn8L39njGVyuoseXzU6rcxFLJ8HFsTjSyQbLYnMpCqE2VbFWc/3H/4h/5h/*H * Private key with derivation: L4rK1yDtCWekvXuE6oXD9jCYfFNV2cWRpVuPLBcCU2z8TrisoyY1/0 * Private key with derivation children: L4rK1yDtCWekvXuE6oXD9jCYfFNV2cWRpVuPLBcCU2z8TrisoyY1/* * Derivation index out of range: xprv9s21ZrQH143K31xYSDQpPDxsXRTUcvj2iNHm5NUtrGiGG5e2DtALGdso3pGz6ssrdK4PFmM8NSpSBHNqPqm55Qn3LqFtT2emdEXVYsCzC2U/2147483648 * Invalid derivation index: xprv9s21ZrQH143K31xYSDQpPDxsXRTUcvj2iNHm5NUtrGiGG5e2DtALGdso3pGz6ssrdK4PFmM8NSpSBHNqPqm55Qn3LqFtT2emdEXVYsCzC2U/1aa * Multiple key origins: [aaaaaaaa][aaaaaaaa]xprv9s21ZrQH143K31xYSDQpPDxsXRTUcvj2iNHm5NUtrGiGG5e2DtALGdso3pGz6ssrdK4PFmM8NSpSBHNqPqm55Qn3LqFtT2emdEXVYsCzC2U/2147483647'/0 * Missing key origin start: aaaaaaaa]xprv9s21ZrQH143K31xYSDQpPDxsXRTUcvj2iNHm5NUtrGiGG5e2DtALGdso3pGz6ssrdK4PFmM8NSpSBHNqPqm55Qn3LqFtT2emdEXVYsCzC2U/2147483647'/0 * Non hex fingerprint: [gaaaaaaa]xprv9s21ZrQH143K31xYSDQpPDxsXRTUcvj2iNHm5NUtrGiGG5e2DtALGdso3pGz6ssrdK4PFmM8NSpSBHNqPqm55Qn3LqFtT2emdEXVYsCzC2U/2147483647'/0 * Key origin with no public key: [deadbeef] ==Backwards Compatibility== Output script descriptors are an entirely new language which is not compatible with any existing software. However many components of the expressions reuse encodings and serializations defined by previous BIPs. Output script descriptors are designed for future extension with further fragment types and new script expressions. These will be specified in additional BIPs. ==Reference Implementation== Descriptors have been implemented in Bitcoin Core since version 0.17. ==Appendix A: Index of Expressions== Future BIPs may specify additional types of expressions. All available expression types are listed in this table. {| ! Name ! Denoted As ! BIP |- | Script | SCRIPT | 380 |- | Key | KEY | 380 |- | Tree | TREE | [[bip-0386.mediawiki|386]] |} ==Appendix B: Index of Script Expressions== Script expressions will be specified in additional BIPs. This Table lists all available Script expressions and the BIPs specifying them. {| ! Expression ! BIP |- | pk(KEY) | [[bip-0381.mediawiki|381]] |- | pkh(KEY) | [[bip-0381.mediawiki|381]] |- | sh(SCRIPT) | [[bip-0381.mediawiki|381]] |- | wpkh(KEY) | [[bip-0382.mediawiki|382]] |- | wsh(SCRIPT) | [[bip-0382.mediawiki|382]] |- | multi(NUM, KEY, ..., KEY) | [[bip-0383.mediawiki|383]] |- | sortedmulti(NUM, KEY, ..., KEY) | [[bip-0383.mediawiki|383]] |- | combo(KEY) | [[bip-0384.mediawiki|384]] |- | raw(HEX) | [[bip-0385.mediawiki|385]] |- | addr(ADDR) | [[bip-0385.mediawiki|385]] |- | tr(KEY), tr(KEY, TREE) | [[bip-0386.mediawiki|386]] |- | musig(KEY, KEY, ..., KEY) | [[bip-0390.mediawiki|390]] |- | sp(KEY), sp(KEY, KEY) | [[bip-0392.mediawiki|392]] |} ================================================ FILE: bip-0381.mediawiki ================================================
  BIP: 381
  Layer: Applications
  Title: Non-Segwit Output Script Descriptors
  Authors: Pieter Wuille 
           Ava Chow 
  Status: Deployed
  Type: Informational
  Assigned: 2021-06-27
  License: BSD-2-Clause
  Requires: 380
==Abstract== This document specifies pk(), pkh(), and sh() output script descriptors. pk() descriptors take a key and produces a P2PK output script. pkh() descriptors take a key and produces a P2PKH output script. sh() descriptors take a script and produces a P2SH output script. ==Copyright== This BIP is licensed under the BSD 2-clause license. ==Motivation== Prior to the activation of Segregated Witness, there were 3 main standard output script formats: P2PK, P2PKH, and P2SH. These expressions allow specifying those formats as a descriptor. ==Specification== Three new script expressions are defined: pk(), pkh(), and sh(). ===pk()=== The pk(KEY) expression can be used in any context or level of a descriptor. It takes a single key expression as an argument and produces a P2PK output script. Depending on the higher level descriptors, there may be restrictions on the type of public keys that can be included. Such restrictions will be specified by those descriptors. The output script produced is:
 OP_CHECKSIG
===pkh()=== The pkh(KEY) expression can be used as a top level expression, or inside of either a sh() or wsh() descriptor. It takes a single key expression as an argument and produces a P2PKH output script. Depending on the higher level descriptors, there may be restrictions on the type of public keys that can be included. Such restrictions will be specified by those descriptors. The output script produced is:
OP_DUP OP_HASH160  OP_EQUALVERIFY OP_CHECKSIG
===sh()=== The sh(SCRIPT) expression can only be used as a top level expression. It takes a single script expression as an argument and produces a P2SH output script. sh() expressions also create a redeemScript which is required in order to spend outputs which use its output script. This redeemScript is the output script produced by the SCRIPT argument to sh(). The output script produced is:
OP_HASH160  OP_EQUAL
==Test Vectors== Valid descriptors followed by the scripts they produce. Descriptors involving derived child keys will have the 0th, 1st, and 2nd scripts listed. * pk(L4rK1yDtCWekvXuE6oXD9jCYfFNV2cWRpVuPLBcCU2z8TrisoyY1) ** 2103a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bdac * pk(03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd) ** 2103a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bdac * pkh([deadbeef/1/2'/3/4']L4rK1yDtCWekvXuE6oXD9jCYfFNV2cWRpVuPLBcCU2z8TrisoyY1) ** 76a9149a1c78a507689f6f54b847ad1cef1e614ee23f1e88ac * pkh([deadbeef/1/2'/3/4']03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd) ** 76a9149a1c78a507689f6f54b847ad1cef1e614ee23f1e88ac * pkh([deadbeef/1/2h/3/4h]03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd) ** 76a9149a1c78a507689f6f54b847ad1cef1e614ee23f1e88ac * pk(5KYZdUEo39z3FPrtuX2QbbwGnNP5zTd7yyr2SC1j299sBCnWjss) ** 4104a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd5b8dec5235a0fa8722476c7709c02559e3aa73aa03918ba2d492eea75abea235ac * pk(04a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd5b8dec5235a0fa8722476c7709c02559e3aa73aa03918ba2d492eea75abea235) ** 4104a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd5b8dec5235a0fa8722476c7709c02559e3aa73aa03918ba2d492eea75abea235ac * pkh(5KYZdUEo39z3FPrtuX2QbbwGnNP5zTd7yyr2SC1j299sBCnWjss) ** 76a914b5bd079c4d57cc7fc28ecf8213a6b791625b818388ac * pkh(04a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd5b8dec5235a0fa8722476c7709c02559e3aa73aa03918ba2d492eea75abea235) ** 76a914b5bd079c4d57cc7fc28ecf8213a6b791625b818388ac * sh(pk(L4rK1yDtCWekvXuE6oXD9jCYfFNV2cWRpVuPLBcCU2z8TrisoyY1)) ** a9141857af51a5e516552b3086430fd8ce55f7c1a52487 * sh(pk(03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd)) ** a9141857af51a5e516552b3086430fd8ce55f7c1a52487 * sh(pkh(L4rK1yDtCWekvXuE6oXD9jCYfFNV2cWRpVuPLBcCU2z8TrisoyY1)) ** a9141a31ad23bf49c247dd531a623c2ef57da3c400c587 * sh(pkh(03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd)) ** a9141a31ad23bf49c247dd531a623c2ef57da3c400c587 * pkh(xprv9s21ZrQH143K31xYSDQpPDxsXRTUcvj2iNHm5NUtrGiGG5e2DtALGdso3pGz6ssrdK4PFmM8NSpSBHNqPqm55Qn3LqFtT2emdEXVYsCzC2U/2147483647'/0) ** 76a914ebdc90806a9c4356c1c88e42216611e1cb4c1c1788ac * pkh([bd16bee5/2147483647h]xpub69H7F5dQzmVd3vPuLKtcXJziMEQByuDidnX3YdwgtNsecY5HRGtAAQC5mXTt4dsv9RzyjgDjAQs9VGVV6ydYCHnprc9vvaA5YtqWyL6hyds/0) ** 76a914ebdc90806a9c4356c1c88e42216611e1cb4c1c1788ac * pk(xprv9uPDJpEQgRQfDcW7BkF7eTya6RPxXeJCqCJGHuCJ4GiRVLzkTXBAJMu2qaMWPrS7AANYqdq6vcBcBUdJCVVFceUvJFjaPdGZ2y9WACViL4L/0) ** 210379e45b3cf75f9c5f9befd8e9506fb962f6a9d185ac87001ec44a8d3df8d4a9e3ac * pk(xpub68NZiKmJWnxxS6aaHmn81bvJeTESw724CRDs6HbuccFQN9Ku14VQrADWgqbhhTHBaohPX4CjNLf9fq9MYo6oDaPPLPxSb7gwQN3ih19Zm4Y/0) ** 210379e45b3cf75f9c5f9befd8e9506fb962f6a9d185ac87001ec44a8d3df8d4a9e3ac Invalid descriptors * pk() only accepts key expressions: pk(pk(03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd)) * pkh() only accepts key expressions: pkh(pk(03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd)) * sh() only accepts script expressions: sh(03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd) * sh() is top level only: sh(sh(pkh(03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd))) ==Backwards Compatibility== pk(), pkh(), and sh() descriptors use the format and general operation specified in [[bip-0380.mediawiki|380]]. As these are wholly new descriptors, they are not compatible with any implementation. However the scripts produced are standard scripts so existing software are likely to be familiar with them. ==Reference Implementation== pk(), pkh(), and sh() descriptors have been implemented in Bitcoin Core since version 0.17. ================================================ FILE: bip-0382.mediawiki ================================================
  BIP: 382
  Layer: Applications
  Title: Segwit Output Script Descriptors
  Authors: Pieter Wuille 
           Ava Chow 
  Status: Deployed
  Type: Informational
  Assigned: 2021-06-27
  License: BSD-2-Clause
  Requires: 380
==Abstract== This document specifies wpkh(), and wsh() output script descriptors. wpkh() descriptors take a key and produces a P2WPKH output script. wsh() descriptors take a script and produces a P2WSH output script. ==Copyright== This BIP is licensed under the BSD 2-clause license. ==Motivation== Segregated Witness added 2 additional standard output script formats: P2WPKH and P2WSH. These expressions allow specifying those formats as a descriptor. ==Specification== Two new script expressions are defined: wpkh(), and wsh(). ===wpkh()=== The wpkh(KEY) expression can be used as a top level expression, or inside of a sh() descriptor. It takes a single key expression as an argument and produces a P2WPKH output script. Only keys which are/have compressed public keys can be contained in a wpkh() expression. The output script produced is:
OP_0 
===wsh()=== The wsh(SCRIPT) expression can be used as a top level expression, or inside of a sh() descriptor. It takes a single script expression as an argument and produces a P2WSH output script. wsh() expressions also create a witnessScript which is required in order to spend outputs which use its output script. This redeemScript is the output script produced by the SCRIPT argument to wsh(). Any key expression found in any script expression contained by a wsh() expression must only produce compressed public keys. The output script produced is:
OP_0 
==Test Vectors== Valid descriptors followed by the scripts they produce. Descriptors involving derived child keys will have the 0th, 1st, and 2nd scripts listed. * wpkh(L4rK1yDtCWekvXuE6oXD9jCYfFNV2cWRpVuPLBcCU2z8TrisoyY1) ** 00149a1c78a507689f6f54b847ad1cef1e614ee23f1e * wpkh(03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd) ** 00149a1c78a507689f6f54b847ad1cef1e614ee23f1e * wpkh([ffffffff/13']xprv9vHkqa6EV4sPZHYqZznhT2NPtPCjKuDKGY38FBWLvgaDx45zo9WQRUT3dKYnjwih2yJD9mkrocEZXo1ex8G81dwSM1fwqWpWkeS3v86pgKt/1/2/0) ** 0014326b2249e3a25d5dc60935f044ee835d090ba859 * wpkh([ffffffff/13']xpub69H7F5d8KSRgmmdJg2KhpAK8SR3DjMwAdkxj3ZuxV27CprR9LgpeyGmXUbC6wb7ERfvrnKZjXoUmmDznezpbZb7ap6r1D3tgFxHmwMkQTPH/1/2/*) ** 0014326b2249e3a25d5dc60935f044ee835d090ba859 ** 0014af0bd98abc2f2cae66e36896a39ffe2d32984fb7 ** 00141fa798efd1cbf95cebf912c031b8a4a6e9fb9f27 * sh(wpkh(xprv9s21ZrQH143K3QTDL4LXw2F7HEK3wJUD2nW2nRk4stbPy6cq3jPPqjiChkVvvNKmPGJxWUtg6LnF5kejMRNNU3TGtRBeJgk33yuGBxrMPHi/10/20/30/40/*')) ** a9149a4d9901d6af519b2a23d4a2f51650fcba87ce7b87 ** a914bed59fc0024fae941d6e20a3b44a109ae740129287 ** a9148483aa1116eb9c05c482a72bada4b1db24af654387 * sh(wpkh(xprv9s21ZrQH143K3QTDL4LXw2F7HEK3wJUD2nW2nRk4stbPy6cq3jPPqjiChkVvvNKmPGJxWUtg6LnF5kejMRNNU3TGtRBeJgk33yuGBxrMPHi/10/20/30/40/*h)) ** a9149a4d9901d6af519b2a23d4a2f51650fcba87ce7b87 ** a914bed59fc0024fae941d6e20a3b44a109ae740129287 ** a9148483aa1116eb9c05c482a72bada4b1db24af654387 * wsh(pkh(L4rK1yDtCWekvXuE6oXD9jCYfFNV2cWRpVuPLBcCU2z8TrisoyY1)) ** 0020338e023079b91c58571b20e602d7805fb808c22473cbc391a41b1bd3a192e75b * wsh(pkh(03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd)) ** 0020338e023079b91c58571b20e602d7805fb808c22473cbc391a41b1bd3a192e75b * wsh(pk(L4rK1yDtCWekvXuE6oXD9jCYfFNV2cWRpVuPLBcCU2z8TrisoyY1)) ** 00202e271faa2325c199d25d22e1ead982e45b64eeb4f31e73dbdf41bd4b5fec23fa * wsh(pk(03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd)) ** 00202e271faa2325c199d25d22e1ead982e45b64eeb4f31e73dbdf41bd4b5fec23fa * sh(wsh(pkh(L4rK1yDtCWekvXuE6oXD9jCYfFNV2cWRpVuPLBcCU2z8TrisoyY1))) ** a914b61b92e2ca21bac1e72a3ab859a742982bea960a87 * sh(wsh(pkh(03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd))) ** a914b61b92e2ca21bac1e72a3ab859a742982bea960a87 Invalid descriptors with descriptions * Uncompressed public key in wpkh(): wpkh(5KYZdUEo39z3FPrtuX2QbbwGnNP5zTd7yyr2SC1j299sBCnWjss) * Uncompressed public key in wpkh(): sh(wpkh(5KYZdUEo39z3FPrtuX2QbbwGnNP5zTd7yyr2SC1j299sBCnWjss)) * Uncompressed public key in wpkh(): wpkh(04a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd5b8dec5235a0fa8722476c7709c02559e3aa73aa03918ba2d492eea75abea235) * Uncompressed public key in wpkh(): sh(wpkh(04a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd5b8dec5235a0fa8722476c7709c02559e3aa73aa03918ba2d492eea75abea235)) * Uncompressed public keys under wsh(): wsh(pk(5KYZdUEo39z3FPrtuX2QbbwGnNP5zTd7yyr2SC1j299sBCnWjss)) * Uncompressed public keys under wsh(): wsh(pk(04a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd5b8dec5235a0fa8722476c7709c02559e3aa73aa03918ba2d492eea75abea235)) * wpkh() nested in wsh(): wsh(wpkh(03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd)) * wsh() nested in wsh(): wsh(wsh(pkh(03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd))) * wsh() nested in wsh(): sh(wsh(wsh(pkh(03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd)))) * Script in wpkh(): wpkh(wsh(pkh(03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd))) * Key in wsh(): wsh(03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd) ==Backwards Compatibility== wpkh(), and wsh() descriptors use the format and general operation specified in [[bip-0380.mediawiki|380]]. As these are a wholly new descriptors, they are not compatible with any implementation. However the scripts produced are standard scripts so existing software are likely to be familiar with them. ==Reference Implementation== wpkh(), and wsh() descriptors have been implemented in Bitcoin Core since version 0.17. ================================================ FILE: bip-0383.mediawiki ================================================
  BIP: 383
  Layer: Applications
  Title: Multisig Output Script Descriptors
  Authors: Pieter Wuille 
           Ava Chow 
  Status: Deployed
  Type: Informational
  Assigned: 2021-06-27
  License: BSD-2-Clause
  Requires: 380
==Abstract== This document specifies multi(), and sortedmulti() output script descriptors. Both functions take a threshold and one or more public keys and produce a multisig output script. multi() specifies the public keys in the output script in the order given in the descriptor while sortedmulti() sorts the public keys lexicographically when the output script is produced. ==Copyright== This BIP is licensed under the BSD 2-clause license. ==Motivation== The most common complex script used in Bitcoin is a threshold multisig. These expressions allow specifying multisig scripts as a descriptor. ==Specification== Two new script expressions are defined: multi(), and sortedmulti(). Both expressions produce the scripts of the same template and take the same arguments. They are written as multi(k,KEY_1,KEY_2,...,KEY_n). k is the threshold - the number of keys that must sign the input for the script to be valid. KEY_1,KEY_2,...,KEY_n are the key expressions for the multisig. k must be less than or equal to n. multi() and sortedmulti() expressions can be used as a top level expression, or inside of either a sh() or wsh() descriptor. Depending on the higher level descriptors, there may be restrictions on the type of public keys that can be included. Depending on the higher level descriptors, there are also restrictions on the number of keys that can be present, i.e. the maximum value of n. When used at the top level, there can only be at most 3 keys. When used inside of a sh() expression, there can only be most 15 compressed public keys (this is limited by the P2SH script limit). Otherwise the maximum number of keys is 20. The output script produced will be
k KEY_1 KEY_2 ... KEY_n n OP_CHECKMULTISIG
The values k and n must be minimally encoded integers. For values less than or equal to 16, they must be encoded using OP_0 through OP_16. For values greater than 16, they must be a push of the signed little endian encoded value without padding. ===sortedmulti()=== The only change for sortedmulti() is that the keys are sorted lexicographically prior to the creation of the output script. This sorting is on the keys that are to be put into the output script, i.e. after all extended keys are derived. ===Multiple Extended Keys=== When one or more the key expressions in a multi() or sortedmulti() expression are extended keys, the derived keys use the same child index. This changes the keys in lockstep and allows for output scripts to be indexed in the same way that the derived keys are indexed. ==Test Vectors== Valid descriptors followed by the scripts they produce. Descriptors involving derived child keys will have the 0th, 1st, and 2nd scripts listed. * multi(1,L4rK1yDtCWekvXuE6oXD9jCYfFNV2cWRpVuPLBcCU2z8TrisoyY1,5KYZdUEo39z3FPrtuX2QbbwGnNP5zTd7yyr2SC1j299sBCnWjss) ** 512103a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd4104a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd5b8dec5235a0fa8722476c7709c02559e3aa73aa03918ba2d492eea75abea23552ae * multi(1,03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd,04a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd5b8dec5235a0fa8722476c7709c02559e3aa73aa03918ba2d492eea75abea235) ** 512103a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd4104a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd5b8dec5235a0fa8722476c7709c02559e3aa73aa03918ba2d492eea75abea23552ae * sortedmulti(1,04a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd5b8dec5235a0fa8722476c7709c02559e3aa73aa03918ba2d492eea75abea235,03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd) ** 512103a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd4104a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd5b8dec5235a0fa8722476c7709c02559e3aa73aa03918ba2d492eea75abea23552ae * sh(multi(2,[00000000/111'/222]xprvA1RpRA33e1JQ7ifknakTFpgNXPmW2YvmhqLQYMmrj4xJXXWYpDPS3xz7iAxn8L39njGVyuoseXzU6rcxFLJ8HFsTjSyQbLYnMpCqE2VbFWc,xprv9uPDJpEQgRQfDcW7BkF7eTya6RPxXeJCqCJGHuCJ4GiRVLzkTXBAJMu2qaMWPrS7AANYqdq6vcBcBUdJCVVFceUvJFjaPdGZ2y9WACViL4L/0)) ** a91445a9a622a8b0a1269944be477640eedc447bbd8487 * sortedmulti(2,xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL/*,xpub68NZiKmJWnxxS6aaHmn81bvJeTESw724CRDs6HbuccFQN9Ku14VQrADWgqbhhTHBaohPX4CjNLf9fq9MYo6oDaPPLPxSb7gwQN3ih19Zm4Y/0/0/*) ** 5221025d5fc65ebb8d44a5274b53bac21ff8307fec2334a32df05553459f8b1f7fe1b62102fbd47cc8034098f0e6a94c6aeee8528abf0a2153a5d8e46d325b7284c046784652ae ** 52210264fd4d1f5dea8ded94c61e9641309349b62f27fbffe807291f664e286bfbe6472103f4ece6dfccfa37b211eb3d0af4d0c61dba9ef698622dc17eecdf764beeb005a652ae ** 5221022ccabda84c30bad578b13c89eb3b9544ce149787e5b538175b1d1ba259cbb83321024d902e1a2fc7a8755ab5b694c575fce742c48d9ff192e63df5193e4c7afe1f9c52ae * wsh(multi(2,xprv9s21ZrQH143K31xYSDQpPDxsXRTUcvj2iNHm5NUtrGiGG5e2DtALGdso3pGz6ssrdK4PFmM8NSpSBHNqPqm55Qn3LqFtT2emdEXVYsCzC2U/2147483647'/0,xprv9vHkqa6EV4sPZHYqZznhT2NPtPCjKuDKGY38FBWLvgaDx45zo9WQRUT3dKYnjwih2yJD9mkrocEZXo1ex8G81dwSM1fwqWpWkeS3v86pgKt/1/2/*,xprv9s21ZrQH143K3QTDL4LXw2F7HEK3wJUD2nW2nRk4stbPy6cq3jPPqjiChkVvvNKmPGJxWUtg6LnF5kejMRNNU3TGtRBeJgk33yuGBxrMPHi/10/20/30/40/*')) ** 0020b92623201f3bb7c3771d45b2ad1d0351ea8fbf8cfe0a0e570264e1075fa1948f ** 002036a08bbe4923af41cf4316817c93b8d37e2f635dd25cfff06bd50df6ae7ea203 ** 0020a96e7ab4607ca6b261bfe3245ffda9c746b28d3f59e83d34820ec0e2b36c139c * sh(wsh(multi(16,03669b8afcec803a0d323e9a17f3ea8e68e8abe5a278020a929adbec52421adbd0,0260b2003c386519fc9eadf2b5cf124dd8eea4c4e68d5e154050a9346ea98ce600,0362a74e399c39ed5593852a30147f2959b56bb827dfa3e60e464b02ccf87dc5e8,0261345b53de74a4d721ef877c255429961b7e43714171ac06168d7e08c542a8b8,02da72e8b46901a65d4374fe6315538d8f368557dda3a1dcf9ea903f3afe7314c8,0318c82dd0b53fd3a932d16e0ba9e278fcc937c582d5781be626ff16e201f72286,0297ccef1ef99f9d73dec9ad37476ddb232f1238aff877af19e72ba04493361009,02e502cfd5c3f972fe9a3e2a18827820638f96b6f347e54d63deb839011fd5765d,03e687710f0e3ebe81c1037074da939d409c0025f17eb86adb9427d28f0f7ae0e9,02c04d3a5274952acdbc76987f3184b346a483d43be40874624b29e3692c1df5af,02ed06e0f418b5b43a7ec01d1d7d27290fa15f75771cb69b642a51471c29c84acd,036d46073cbb9ffee90473f3da429abc8de7f8751199da44485682a989a4bebb24,02f5d1ff7c9029a80a4e36b9a5497027ef7f3e73384a4a94fbfe7c4e9164eec8bc,02e41deffd1b7cce11cde209a781adcffdabd1b91c0ba0375857a2bfd9302419f3,02d76625f7956a7fc505ab02556c23ee72d832f1bac391bcd2d3abce5710a13d06,0399eb0a5487515802dc14544cf10b3666623762fbed2ec38a3975716e2c29c232))) ** a9147fc63e13dc25e8a95a3cee3d9a714ac3afd96f1e87 * wsh(multi(20,KzoAz5CanayRKex3fSLQ2BwJpN7U52gZvxMyk78nDMHuqrUxuSJy,KwGNz6YCCQtYvFzMtrC6D3tKTKdBBboMrLTsjr2NYVBwapCkn7Mr,KxogYhiNfwxuswvXV66eFyKcCpm7dZ7TqHVqujHAVUjJxyivxQ9X,L2BUNduTSyZwZjwNHynQTF14mv2uz2NRq5n5sYWTb4FkkmqgEE9f,L1okJGHGn1kFjdXHKxXjwVVtmCMR2JA5QsbKCSpSb7ReQjezKeoD,KxDCNSST75HFPaW5QKpzHtAyaCQC7p9Vo3FYfi2u4dXD1vgMiboK,L5edQjFtnkcf5UWURn6UuuoFrabgDQUHdheKCziwN42aLwS3KizU,KzF8UWFcEC7BYTq8Go1xVimMkDmyNYVmXV5PV7RuDicvAocoPB8i,L3nHUboKG2w4VSJ5jYZ5CBM97oeK6YuKvfZxrefdShECcjEYKMWZ,KyjHo36dWkYhimKmVVmQTq3gERv3pnqA4xFCpvUgbGDJad7eS8WE,KwsfyHKRUTZPQtysN7M3tZ4GXTnuov5XRgjdF2XCG8faAPmFruRF,KzCUbGhN9LJhdeFfL9zQgTJMjqxdBKEekRGZX24hXdgCNCijkkap,KzgpMBwwsDLwkaC5UrmBgCYaBD2WgZ7PBoGYXR8KT7gCA9UTN5a3,KyBXTPy4T7YG4q9tcAM3LkvfRpD1ybHMvcJ2ehaWXaSqeGUxEdkP,KzJDe9iwJRPtKP2F2AoN6zBgzS7uiuAwhWCfGdNeYJ3PC1HNJ8M8,L1xbHrxynrqLKkoYc4qtoQPx6uy5qYXR5ZDYVYBSRmCV5piU3JG9,KzRedjSwMggebB3VufhbzpYJnvHfHe9kPJSjCU5QpJdAW3NSZxYS,Kyjtp5858xL7JfeV4PNRCKy2t6XvgqNNepArGY9F9F1SSPqNEMs3,L2D4RLHPiHBidkHS8ftx11jJk1hGFELvxh8LoxNQheaGT58dKenW,KyLPZdwY4td98bKkXqEXTEBX3vwEYTQo1yyLjX2jKXA63GBpmSjv)) ** 0020376bd8344b8b6ebe504ff85ef743eaa1aa9272178223bcb6887e9378efb341ac * sh(wsh(multi(20,KzoAz5CanayRKex3fSLQ2BwJpN7U52gZvxMyk78nDMHuqrUxuSJy,KwGNz6YCCQtYvFzMtrC6D3tKTKdBBboMrLTsjr2NYVBwapCkn7Mr,KxogYhiNfwxuswvXV66eFyKcCpm7dZ7TqHVqujHAVUjJxyivxQ9X,L2BUNduTSyZwZjwNHynQTF14mv2uz2NRq5n5sYWTb4FkkmqgEE9f,L1okJGHGn1kFjdXHKxXjwVVtmCMR2JA5QsbKCSpSb7ReQjezKeoD,KxDCNSST75HFPaW5QKpzHtAyaCQC7p9Vo3FYfi2u4dXD1vgMiboK,L5edQjFtnkcf5UWURn6UuuoFrabgDQUHdheKCziwN42aLwS3KizU,KzF8UWFcEC7BYTq8Go1xVimMkDmyNYVmXV5PV7RuDicvAocoPB8i,L3nHUboKG2w4VSJ5jYZ5CBM97oeK6YuKvfZxrefdShECcjEYKMWZ,KyjHo36dWkYhimKmVVmQTq3gERv3pnqA4xFCpvUgbGDJad7eS8WE,KwsfyHKRUTZPQtysN7M3tZ4GXTnuov5XRgjdF2XCG8faAPmFruRF,KzCUbGhN9LJhdeFfL9zQgTJMjqxdBKEekRGZX24hXdgCNCijkkap,KzgpMBwwsDLwkaC5UrmBgCYaBD2WgZ7PBoGYXR8KT7gCA9UTN5a3,KyBXTPy4T7YG4q9tcAM3LkvfRpD1ybHMvcJ2ehaWXaSqeGUxEdkP,KzJDe9iwJRPtKP2F2AoN6zBgzS7uiuAwhWCfGdNeYJ3PC1HNJ8M8,L1xbHrxynrqLKkoYc4qtoQPx6uy5qYXR5ZDYVYBSRmCV5piU3JG9,KzRedjSwMggebB3VufhbzpYJnvHfHe9kPJSjCU5QpJdAW3NSZxYS,Kyjtp5858xL7JfeV4PNRCKy2t6XvgqNNepArGY9F9F1SSPqNEMs3,L2D4RLHPiHBidkHS8ftx11jJk1hGFELvxh8LoxNQheaGT58dKenW,KyLPZdwY4td98bKkXqEXTEBX3vwEYTQo1yyLjX2jKXA63GBpmSjv))) ** a914c2c9c510e9d7f92fd6131e94803a8d34a8ef675e87 Invalid descriptors * More than 15 keys in P2SH multisig: sh(multi(16,03669b8afcec803a0d323e9a17f3ea8e68e8abe5a278020a929adbec52421adbd0,0260b2003c386519fc9eadf2b5cf124dd8eea4c4e68d5e154050a9346ea98ce600,0362a74e399c39ed5593852a30147f2959b56bb827dfa3e60e464b02ccf87dc5e8,0261345b53de74a4d721ef877c255429961b7e43714171ac06168d7e08c542a8b8,02da72e8b46901a65d4374fe6315538d8f368557dda3a1dcf9ea903f3afe7314c8,0318c82dd0b53fd3a932d16e0ba9e278fcc937c582d5781be626ff16e201f72286,0297ccef1ef99f9d73dec9ad37476ddb232f1238aff877af19e72ba04493361009,02e502cfd5c3f972fe9a3e2a18827820638f96b6f347e54d63deb839011fd5765d,03e687710f0e3ebe81c1037074da939d409c0025f17eb86adb9427d28f0f7ae0e9,02c04d3a5274952acdbc76987f3184b346a483d43be40874624b29e3692c1df5af,02ed06e0f418b5b43a7ec01d1d7d27290fa15f75771cb69b642a51471c29c84acd,036d46073cbb9ffee90473f3da429abc8de7f8751199da44485682a989a4bebb24,02f5d1ff7c9029a80a4e36b9a5497027ef7f3e73384a4a94fbfe7c4e9164eec8bc,02e41deffd1b7cce11cde209a781adcffdabd1b91c0ba0375857a2bfd9302419f3,02d76625f7956a7fc505ab02556c23ee72d832f1bac391bcd2d3abce5710a13d06,0399eb0a5487515802dc14544cf10b3666623762fbed2ec38a3975716e2c29c232)) * Invalid threshold: multi(a,03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd,04a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd5b8dec5235a0fa8722476c7709c02559e3aa73aa03918ba2d492eea75abea235) * Threshold of 0: multi(0,03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd,04a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd5b8dec5235a0fa8722476c7709c02559e3aa73aa03918ba2d492eea75abea235) * Threshold larger than keys: multi(3,L4rK1yDtCWekvXuE6oXD9jCYfFNV2cWRpVuPLBcCU2z8TrisoyY1,5KYZdUEo39z3FPrtuX2QbbwGnNP5zTd7yyr2SC1j299sBCnWjss) ==Backwards Compatibility== multi(), and sortedmulti() descriptors use the format and general operation specified in [[bip-0380.mediawiki|380]]. As these are a wholly new descriptors, they are not compatible with any implementation. However the scripts produced are standard scripts so existing software are likely to be familiar with them. ==Reference Implementation== multi(), and sortedmulti() descriptors have been implemented in Bitcoin Core since version 0.17. ================================================ FILE: bip-0384.mediawiki ================================================
  BIP: 384
  Layer: Applications
  Title: combo() Output Script Descriptors
  Authors: Pieter Wuille 
           Ava Chow 
  Status: Deployed
  Type: Informational
  Assigned: 2021-06-27
  License: BSD-2-Clause
  Requires: 380
==Abstract== This document specifies combo() output script descriptors. These take a key and produce P2PK, P2PKH, P2WPKH, and P2SH-P2WPKH output scripts if applicable to the key. ==Copyright== This BIP is licensed under the BSD 2-clause license. ==Motivation== In order to make the transition from traditional key based wallets to descriptor based wallets easier, it is useful to be able to take a key and produce the scripts which have traditionally been produced by wallet software. ==Specification== A new top level script expression is defined: combo(KEY). This expression can only be used as a top level expression. It takes a single key expression as an argument and produces either 2 or 4 output scripts, depending on the key. A combo() expression always produces a P2PK and P2PKH script, the same as putting the key in both a pk() and a pkh() expression. If the key is/has a compressed public key, then P2WPKH and P2SH-P2WPKH scripts are also produced, the same as putting the key in both a wpkh() and sh(wpkh()) expression. ==Test Vectors== Valid descriptors followed by the scripts they produce. Descriptors involving derived child keys will have the 0th, and 1st scripts in additional sub-bullets. * combo(L4rK1yDtCWekvXuE6oXD9jCYfFNV2cWRpVuPLBcCU2z8TrisoyY1) ** 2103a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bdac ** 76a9149a1c78a507689f6f54b847ad1cef1e614ee23f1e88ac ** 00149a1c78a507689f6f54b847ad1cef1e614ee23f1e ** a91484ab21b1b2fd065d4504ff693d832434b6108d7b87 * combo(04a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd5b8dec5235a0fa8722476c7709c02559e3aa73aa03918ba2d492eea75abea235) ** 4104a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd5b8dec5235a0fa8722476c7709c02559e3aa73aa03918ba2d492eea75abea235ac ** 76a914b5bd079c4d57cc7fc28ecf8213a6b791625b818388ac * combo([01234567]xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL) ** 2102d2b36900396c9282fa14628566582f206a5dd0bcc8d5e892611806cafb0301f0ac ** 76a91431a507b815593dfc51ffc7245ae7e5aee304246e88ac ** 001431a507b815593dfc51ffc7245ae7e5aee304246e ** a9142aafb926eb247cb18240a7f4c07983ad1f37922687 * combo(xprvA2JDeKCSNNZky6uBCviVfJSKyQ1mDYahRjijr5idH2WwLsEd4Hsb2Tyh8RfQMuPh7f7RtyzTtdrbdqqsunu5Mm3wDvUAKRHSC34sJ7in334/*) ** Child 0 *** 2102df12b7035bdac8e3bab862a3a83d06ea6b17b6753d52edecba9be46f5d09e076ac *** 76a914f90e3178ca25f2c808dc76624032d352fdbdfaf288ac *** 0014f90e3178ca25f2c808dc76624032d352fdbdfaf2 *** a91408f3ea8c68d4a7585bf9e8bda226723f70e445f087 ** Child 1 *** 21032869a233c9adff9a994e4966e5b821fd5bac066da6c3112488dc52383b4a98ecac *** 76a914a8409d1b6dfb1ed2a3e8aa5e0ef2ff26b15b75b788ac *** 0014a8409d1b6dfb1ed2a3e8aa5e0ef2ff26b15b75b7 *** a91473e39884cb71ae4e5ac9739e9225026c99763e6687 Invalid descriptors * combo() in sh : sh(combo(03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd)) * combo() in wsh : wsh(combo(03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd)) * Script in combo(): combo(pkh(03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd)) ==Backwards Compatibility== combo() descriptors use the format and general operation specified in [[bip-0380.mediawiki|380]]. As this is a wholly new descriptor, it is not compatible with any implementation. However the scripts produced are standard scripts so existing software are likely to be familiar with them. ==Reference Implementation== combo() descriptors have been implemented in Bitcoin Core since version 0.17. ================================================ FILE: bip-0385.mediawiki ================================================
  BIP: 385
  Layer: Applications
  Title: raw() and addr() Output Script Descriptors
  Authors: Pieter Wuille 
           Ava Chow 
  Status: Deployed
  Type: Informational
  Assigned: 2021-06-27
  License: BSD-2-Clause
  Requires: 380
==Abstract== This document specifies raw() and addr() output script descriptors. raw() encapsulates a raw script as a descriptor. addr() encapsulates an address as a descriptor. ==Copyright== This BIP is licensed under the BSD 2-clause license. ==Motivation== In order to make descriptors maximally compatible with scripts in use today, it is useful to be able to wrap any arbitrary output script or an address into a descriptor. ==Specification== Two new script expressions are defined: raw() and addr(). ===raw()=== The raw(HEX) expression can only be used as a top level descriptor. As the argument, it takes a hex string representing a Bitcoin script. The output script produced by this descriptor is the script represented by HEX. ===addr()=== The addr(ADDR) expression can only be used as a top level descriptor. It takes an address as its single argument. The output script produced by this descriptor is the output script produced by the address ADDR. ==Test Vectors== Valid descriptors followed by the scripts they produce. * raw(deadbeef) ** deadbeef * raw(512103a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd4104a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd5b8dec5235a0fa8722476c7709c02559e3aa73aa03918ba2d492eea75abea23552ae) ** 512103a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd4104a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd5b8dec5235a0fa8722476c7709c02559e3aa73aa03918ba2d492eea75abea23552ae * raw(a9149a4d9901d6af519b2a23d4a2f51650fcba87ce7b87) ** a9149a4d9901d6af519b2a23d4a2f51650fcba87ce7b87 * addr(3PUNyaW7M55oKWJ3kDukwk9bsKvryra15j) ** a914eeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeee87 Invalid descriptors * Non-hex script: raw(asdf) * Invalid address: addr(asdf) * raw nested in sh: sh(raw(deadbeef)) * raw nested in wsh: wsh(raw(deadbeef)) * addr nested in sh: sh(addr(3PUNyaW7M55oKWJ3kDukwk9bsKvryra15j)) * addr nested in wsh: wsh(addr(3PUNyaW7M55oKWJ3kDukwk9bsKvryra15j)) ==Backwards Compatibility== raw() and addr() descriptors use the format and general operation specified in [[bip-0380.mediawiki|380]]. As this is a wholly new descriptor, it is not compatible with any implementation. The reuse of existing Bitcoin addresses allows for this to be more easily implemented. ==Reference Implementation== raw() and addr() descriptors have been implemented in Bitcoin Core since version 0.17. ================================================ FILE: bip-0386.mediawiki ================================================
  BIP: 386
  Layer: Applications
  Title: tr() Output Script Descriptors
  Authors: Pieter Wuille 
           Ava Chow 
  Status: Deployed
  Type: Informational
  Assigned: 2021-06-27
  License: BSD-2-Clause
  Requires: 380
==Abstract== This document specifies tr() output script descriptors. tr() descriptors take a key and optionally a tree of scripts and produces a P2TR output script. ==Copyright== This BIP is licensed under the BSD 2-clause license. ==Motivation== Taproot added one additional standard output script format: P2TR. These expressions allow specifying those formats as a descriptor. ==Specification== A new script expression is defined: tr(). A new expression is defined: Tree Expressions ===Tree Expression=== A Tree Expression (denoted TREE) is an expression which represents a tree of scripts. The way the tree is represented in an output script is dependent on the higher level expressions. A Tree Expression is: * Any Script Expression that is allowed at the level this Tree Expression is in. * A pair of Tree Expressions consisting of: ** An open brace { ** A Tree Expression ** A comma , ** A Tree Expression ** A closing brace } ===tr()=== The tr(KEY) or tr(KEY, TREE) expression can only be used as a top level expression. All key expressions under any tr() expression must create x-only public keys. tr(KEY) takes a single key expression as an argument and produces a P2TR output script which does not have a script path. Each key produced by the key expression is used as the internal key of a P2TR output as specified by [[bip-0341.mediawiki#cite_ref-22-0|BIP 341]]. Specifically, "If the spending conditions do not require a script path, the output key should commit to an unspendable script path instead of having no script path. This can be achieved by computing the output key point as ''Q = P + int(hashTapTweak(bytes(P)))G''."
internal_key:       lift_x(KEY)
32_byte_output_key: internal_key + int(HashTapTweak(bytes(internal_key)))G
scriptPubKey:       OP_1 <32_byte_output_key>
tr(KEY, TREE) takes a key expression as the first argument, and a tree expression as the second argument and produces a P2TR output script which has a script path. The keys produced by the first key expression are used as the internal key as specified by [[bip-0341.mediawiki#Constructing_and_spending_Taproot_outputs|BIP 341]]. The Tree expression becomes the Taproot script tree as described in BIP 341. A merkle root is computed from this tree and combined with the internal key to create the Taproot output key.
internal_key:       lift_x(KEY)
merkle_root:        HashTapBranch(TREE)
32_byte_output_key: internal_key + int(HashTapTweak(bytes(internal_key) || merkle_root))G
scriptPubKey:       OP_1 <32_byte_output_key>
===Modified Key Expression=== Key Expressions within a tr() expression must only create x-only public keys. Uncompressed public keys are not allowed, but compressed public keys would be implicitly converted to x-only public keys. The keys derived from extended keys must be serialized as x-only public keys. An additional key expression is defined only for use within a tr() descriptor: * A 64 hex character string representing an x-only public key ==Test Vectors== Valid descriptors followed by the scripts they produce. Descriptors involving derived child keys will have the 0th, 1st, and 2nd scripts listed. * tr(a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd) ** 512077aab6e066f8a7419c5ab714c12c67d25007ed55a43cadcacb4d7a970a093f11 * tr(L4rK1yDtCWekvXuE6oXD9jCYfFNV2cWRpVuPLBcCU2z8TrisoyY1) ** 512077aab6e066f8a7419c5ab714c12c67d25007ed55a43cadcacb4d7a970a093f11 * tr(xprvA1RpRA33e1JQ7ifknakTFpgNXPmW2YvmhqLQYMmrj4xJXXWYpDPS3xz7iAxn8L39njGVyuoseXzU6rcxFLJ8HFsTjSyQbLYnMpCqE2VbFWc/0/*,pk(xprvA1RpRA33e1JQ7ifknakTFpgNXPmW2YvmhqLQYMmrj4xJXXWYpDPS3xz7iAxn8L39njGVyuoseXzU6rcxFLJ8HFsTjSyQbLYnMpCqE2VbFWc/1/*)) ** 512078bc707124daa551b65af74de2ec128b7525e10f374dc67b64e00ce0ab8b3e12 ** 512001f0a02a17808c20134b78faab80ef93ffba82261ccef0a2314f5d62b6438f11 ** 512021024954fcec88237a9386fce80ef2ced5f1e91b422b26c59ccfc174c8d1ad25 * tr(a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd,pk(669b8afcec803a0d323e9a17f3ea8e68e8abe5a278020a929adbec52421adbd0)) ** 512017cf18db381d836d8923b1bdb246cfcd818da1a9f0e6e7907f187f0b2f937754 * tr(a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd,{pk(xprvA2JDeKCSNNZky6uBCviVfJSKyQ1mDYahRjijr5idH2WwLsEd4Hsb2Tyh8RfQMuPh7f7RtyzTtdrbdqqsunu5Mm3wDvUAKRHSC34sJ7in334/0),{{pk(xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL),pk(02df12b7035bdac8e3bab862a3a83d06ea6b17b6753d52edecba9be46f5d09e076)},pk(L4rK1yDtCWekvXuE6oXD9jCYfFNV2cWRpVuPLBcCU2z8TrisoyY1)}}) ** 512071fff39599a7b78bc02623cbe814efebf1a404f5d8ad34ea80f213bd8943f574 Invalid Descriptors * Uncompressed private key: tr(5KYZdUEo39z3FPrtuX2QbbwGnNP5zTd7yyr2SC1j299sBCnWjss) * Uncompressed public key: tr(04a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd5b8dec5235a0fa8722476c7709c02559e3aa73aa03918ba2d492eea75abea235) * tr() nested in wsh: wsh(tr(a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd)) * tr() nested in sh: sh(tr(a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd)) * pkh() nested in tr: tr(a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd, pkh(L4rK1yDtCWekvXuE6oXD9jCYfFNV2cWRpVuPLBcCU2z8TrisoyY1)) ==Backwards Compatibility== tr() descriptors use the format and general operation specified in [[bip-0380.mediawiki|380]]. As these are a set of wholly new descriptors, they are not compatible with any implementation. However the scripts produced are standard scripts so existing software are likely to be familiar with them. Tree Expressions are largely incompatible with existing script expressions due to the restrictions in those expressions. As of 2021-06-27, the only allowed script expression that can be used in a tree expression is pk(). However there will be future BIPs that specify script expressions that can be used in tree expressions. ==Reference Implementation== tr() descriptors have been implemented in Bitcoin Core since version 22.0. ================================================ FILE: bip-0387.mediawiki ================================================
  BIP: 387
  Layer: Applications
  Title: Tapscript Multisig Output Script Descriptors
  Authors: Pieter Wuille 
           Ava Chow 
  Status: Deployed
  Type: Informational
  Assigned: 2024-04-17
  License: BSD-2-Clause
  Requires: 380
==Abstract== This document specifies multi_a() and sortedmulti_a() output script descriptors. Like BIP 383's multi() and sortedmulti(), both functions take a threshold and one or more public keys and produce a multisig script. The primary distinction is that multi_a() and sortedmulti_a() only produce tapscripts and are only allowed in a tapscript context. ==Copyright== This BIP is licensed under the BSD 2-clause license. ==Motivation== The most common complex script used in Bitcoin is a threshold multisig. These expressions allow specifying multisig scripts as a descriptor. ==Specification== Two new script expressions are defined: multi_a() and sortedmulti_a(). Both expressions produce the scripts of the same template and take the same arguments. They are written as multi_a(k,KEY_1,KEY_2,...,KEY_n). k is the threshold - the number of keys that must sign the input for the script to be valid. KEY_1,KEY_2,...,KEY_n are the key expressions for the multisig. k must be less than or equal to n. multi_a() and sortedmulti_a() expressions can only be used inside of a tr() descriptor. The maximum number of keys is 999. The output script produced also depends on the value of k. If k is less than or equal to 16:
KEY_1 OP_CHECKSIG KEY_2 OP_CHECKSIGADD ... KEY_n OP_CHECKSIGADD OP_k OP_NUMEQUAL
if k is greater than 16:
KEY_1 OP_CHECKSIG KEY_2 OP_CHECKSIGADD ... KEY_n OP_CHECKSIGADD k OP_NUMEQUAL
===sortedmulti_a()=== The only change for sortedmulti_a() is that the x-only public keys are sorted lexicographically prior to the creation of the output script. This sorting is on the keys that are to be put into the output script, i.e. after all extended keys are derived. ===Multiple Extended Keys
=== When one or more of the key expressions in a multi_a() or sortedmulti_a() expression are extended keys, the derived keys use the same child index. This changes the keys in lockstep and allows for output scripts to be indexed in the same way that the derived keys are indexed. ==Test Vectors== Valid descriptors followed by the scripts they produce. Descriptors involving derived child keys will have the 0th, 1st, and 2nd scripts listed. * tr(L4rK1yDtCWekvXuE6oXD9jCYfFNV2cWRpVuPLBcCU2z8TrisoyY1,multi_a(1,KzoAz5CanayRKex3fSLQ2BwJpN7U52gZvxMyk78nDMHuqrUxuSJy)) ** 5120eb5bd3894327d75093891cc3a62506df7d58ec137fcd104cdd285d67816074f3 * tr(a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd,multi_a(1,669b8afcec803a0d323e9a17f3ea8e68e8abe5a278020a929adbec52421adbd0)) ** 5120eb5bd3894327d75093891cc3a62506df7d58ec137fcd104cdd285d67816074f3 * tr(50929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac0,multi_a(2,[00000000/111'/222]xprvA1RpRA33e1JQ7ifknakTFpgNXPmW2YvmhqLQYMmrj4xJXXWYpDPS3xz7iAxn8L39njGVyuoseXzU6rcxFLJ8HFsTjSyQbLYnMpCqE2VbFWc,xprv9uPDJpEQgRQfDcW7BkF7eTya6RPxXeJCqCJGHuCJ4GiRVLzkTXBAJMu2qaMWPrS7AANYqdq6vcBcBUdJCVVFceUvJFjaPdGZ2y9WACViL4L/0)) ** 51202eea93581594a43c0c8423b70dc112e5651df63984d108d4fc8ccd3b63b4eafa * tr(50929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac0,sortedmulti_a(2,[00000000/111'/222]xprvA1RpRA33e1JQ7ifknakTFpgNXPmW2YvmhqLQYMmrj4xJXXWYpDPS3xz7iAxn8L39njGVyuoseXzU6rcxFLJ8HFsTjSyQbLYnMpCqE2VbFWc,xprv9uPDJpEQgRQfDcW7BkF7eTya6RPxXeJCqCJGHuCJ4GiRVLzkTXBAJMu2qaMWPrS7AANYqdq6vcBcBUdJCVVFceUvJFjaPdGZ2y9WACViL4L/0)) ** 512016fa6a6ba7e98c54b5bf43b3144912b78a61b60b02f6a74172b8dcb35b12bc30 * tr(50929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac0,sortedmulti_a(2,xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL/*,xpub68NZiKmJWnxxS6aaHmn81bvJeTESw724CRDs6HbuccFQN9Ku14VQrADWgqbhhTHBaohPX4CjNLf9fq9MYo6oDaPPLPxSb7gwQN3ih19Zm4Y/0/0/*)) ** 5120abd47468515223f58a1a18edfde709a7a2aab2b696d59ecf8c34f0ba274ef772 ** 5120fe62e7ed20705bd1d3678e072bc999acb014f07795fa02cb8f25a7aa787e8cbd ** 51201311093750f459039adaa2a5ed23b0f7a8ae2c2ffb07c5390ea37e2fb1050b41 * tr(50929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac0,multi_a(2,xprv9s21ZrQH143K31xYSDQpPDxsXRTUcvj2iNHm5NUtrGiGG5e2DtALGdso3pGz6ssrdK4PFmM8NSpSBHNqPqm55Qn3LqFtT2emdEXVYsCzC2U/2147483647'/0,xprv9vHkqa6EV4sPZHYqZznhT2NPtPCjKuDKGY38FBWLvgaDx45zo9WQRUT3dKYnjwih2yJD9mkrocEZXo1ex8G81dwSM1fwqWpWkeS3v86pgKt/1/2/*,xprv9s21ZrQH143K3QTDL4LXw2F7HEK3wJUD2nW2nRk4stbPy6cq3jPPqjiChkVvvNKmPGJxWUtg6LnF5kejMRNNU3TGtRBeJgk33yuGBxrMPHi/10/20/30/40/*')) ** 5120e4c8f2b0a7d3a688ac131cb03248c0d4b0a59bbd4f37211c848cfbd22a981192 ** 5120827faedaa21e52fca2ac83b53afd1ab7d4d1e6ce67ff42b19f2723d48b5a19ab ** 5120647495ed09de61a3a324704f9203c130d655bf3141f9b748df8f7be7e9af55a4 Invalid descriptors * Unsupported top level: multi_a(1,03669b8afcec803a0d323e9a17f3ea8e68e8abe5a278020a929adbec52421adbd0) * Unsupported sh() context: sh(multi_a(1,03669b8afcec803a0d323e9a17f3ea8e68e8abe5a278020a929adbec52421adbd0)) * Unsupported wsh() context: wsh(multi_a(1,03669b8afcec803a0d323e9a17f3ea8e68e8abe5a278020a929adbec52421adbd0)) * Invalid threshold: tr(50929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac0,multi_a(a,03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd)) * Threshold of 0: tr(50929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac0,multi_a(0,03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd)) * Uncompressed pubkey: tr(50929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac0,multi_a(1,04a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd5b8dec5235a0fa8722476c7709c02559e3aa73aa03918ba2d492eea75abea235)) * Threshold larger than keys: tr(50929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac0,multi_a(3,L4rK1yDtCWekvXuE6oXD9jCYfFNV2cWRpVuPLBcCU2z8TrisoyY1,5KYZdUEo39z3FPrtuX2QbbwGnNP5zTd7yyr2SC1j299sBCnWjss)) ==Backwards Compatibility== multi_a() and sortedmulti_a() descriptors use the format and general operation specified in [[bip-0380.mediawiki|380]]. As these are wholly new descriptors, they are not compatible with any implementation. However, the scripts produced are standard scripts, so existing software are likely to be familiar with them. ==Reference Implementation== multi_a() and sortedmulti_a() descriptors were implemented in Bitcoin Core in https://github.com/bitcoin/bitcoin/pull/24043 and have been available since version 24.0. ================================================ FILE: bip-0388/wallet_policies.py ================================================ #!/usr/bin/env python3 from typing import Iterable, List, Mapping, Tuple, Generator def find_all(text: str, pattern: str, start: int = 0) -> Generator[int, None, None]: """Generates all the positions of `pattern` as a substring of `text`, starting from index at least `start`.""" while True: start = text.find(pattern, start) if start == -1: return yield start start += len(pattern) def find_first(text: str, start_pos: int, patterns: Iterable[str]) -> int: """Returns the position of the first occurrence of any of the elements in `patterns` as a substring of `text`, or -1 if none of the patterns is found.""" matches = (text.find(x, start_pos) for x in patterns) return min((x for x in matches if x != -1), default=-1) def find_key_end_position(desc: str, start_pos: int) -> int: """Assuming that `start_pos` is the beginning of a KEY expression (and not musig), finds the position of the end of the key expression, excluding (if present) the final derivation steps after an xpub. This is the information that goes into an entry of the vector of key information of the wallet policy.""" has_orig_info = True if desc[start_pos] == '[' else False if has_orig_info: closing_bracket_pos = desc.find("]", start_pos) if closing_bracket_pos == -1: raise Exception("Invalid descriptor: could not find closing ']'") key_pos_start = closing_bracket_pos + 1 else: key_pos_start = start_pos # find the earliest occurrence of ",", a ")" or a "/" (it must find at least 1) end_pos = find_first(desc, key_pos_start, [",", ")", "/"]) if end_pos == -1: raise Exception( "Invalid descriptor: cannot find the end of key expression") return end_pos class WalletPolicy(object): """Simple class to represent wallet policies. This is a toy implementation that does not parse the descriptor template. A more robust implementation would build the abstract syntax tree of the template and of the descriptor, allowing one to detect errors, and manipulate it semantically instead of relying on string manipulation.""" def __init__(self, descriptor_template: str, keys_info: List[str]): self.descriptor_template = descriptor_template self.keys_info = keys_info def to_descriptor(self) -> str: """Converts a wallet policy into the descriptor (with the / syntax, if present).""" desc = self.descriptor_template # replace each "/**" with "/<0;1>/*" desc = desc.replace("/**", "/<0;1>/*") # process all the @N expressions in decreasing order. This guarantees that string replacements # works as expected (as any prefix expression is processed after). for i in reversed(range(len(self.keys_info))): desc = desc.replace(f"@{i}", self.keys_info[i]) # there should not be any remaining "@" expressions if desc.find("@") != -1: raise Exception("Invalid descriptor template: contains invalid key index") return desc @classmethod def from_descriptor(cls, descriptor: str) -> 'WalletPolicy': """Converts a "reasonable" descriptor (with the / syntax) into the corresponding wallet policy.""" # list of pairs of integers, where the tuple (m,n) with m < n means a key expression starts at # m (inclusive) and at n (exclusive) key_expressions: List[Tuple[int, int]] = [] key_with_orig_pos_start = None def parse_key_expressions(only_first=False, handle_musig=False): # Starting at the position in `key_with_orig_pos_start`, parses a number of key expressions, and updates # the `key_expressions` array accordingly. # If `only_first` is `True`, it stops after parsing a single key expression. # If `handle_musig` is `True`, and a key expression is a `musig` operator, it recursively parses # the keys in the musig expression. `musig` inside `musig` is not allowed. nonlocal key_with_orig_pos_start if key_with_orig_pos_start is None: raise Exception("Unexpected error") while True: if handle_musig and descriptor[key_with_orig_pos_start:].startswith("musig"): closing_parenthesis_pos = find_first( descriptor, key_with_orig_pos_start, [")"]) if closing_parenthesis_pos == -1: raise Exception( "Invalid descriptor: musig without closing parenthesis") key_with_orig_pos_start = key_with_orig_pos_start + \ len("musig(") parse_key_expressions( only_first=False, handle_musig=False) key_pos_end = closing_parenthesis_pos + 1 else: key_pos_end = find_key_end_position( descriptor, key_with_orig_pos_start) key_expressions.append( (key_with_orig_pos_start, key_pos_end)) if descriptor[key_pos_end] == '/': # find the actual end (comma or closing parenthesis) key_pos_end = find_first( descriptor, key_pos_end, [",", ")"]) if key_pos_end == -1: raise Exception( "Invalid descriptor: unterminated key expression") if descriptor[key_pos_end] == ',': # There is another key expression, repeat from after the comma key_with_orig_pos_start = key_pos_end + 1 else: break if only_first: break # operators for which the KEY is the first argument operators_key_first = ["pk", "pkh", "pk_h", "pk_k", "tr"] # operators for which the KEY is everything except the first argument operators_key_all_but_first = [ "multi", "sortedmulti", "multi_a", "sortedmulti_a"] for op in operators_key_first + operators_key_all_but_first: for op_pos_start in find_all(descriptor, op + "("): # ignore if not a whole word (otherwise "sortedmulti" would be found inside "multi") if op_pos_start > 0 and 'a' <= descriptor[op_pos_start - 1] <= 'z': continue if op in operators_key_all_but_first: # skip the first argument (we know it's not a KEY expression, so it does not have a comma) first_comma_pos = descriptor.find(",", op_pos_start) if first_comma_pos == -1: raise Exception( "Invalid descriptor: multi, sortedmulti, multi_a and sortedmulti_a must have at least two arguments") key_with_orig_pos_start = 1 + first_comma_pos else: # other operators, the first argument is already a KEY expression key_with_orig_pos_start = op_pos_start + len(op) + 1 only_first = op in operators_key_first parse_key_expressions( only_first=only_first, handle_musig=True) result: List[str] = [] keys: List[str] = [] keys_to_idx: Mapping[str, int] = {} prev_end = 0 for start, end in sorted(key_expressions): result.append(descriptor[prev_end:start]) key = descriptor[start:end] if key not in keys_to_idx: idx = len(keys) keys.append(key) keys_to_idx[key] = idx else: idx = keys_to_idx[key] result.append(f"@{idx}") prev_end = end result.append(descriptor[prev_end:]) return cls("".join(result), keys) if __name__ == "__main__": descriptors = [ "pkh([d34db33f/44'/0'/0']xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL/**)", "wsh(multi(1,xpub661MyMwAqRbcFW31YEwpkMuc5THy2PSt5bDMsktWQcFF8syAmRUapSCGu8ED9W6oDMSgv6Zz8idoc4a6mr8BDzTJY47LJhkJ8UB7WEGuduB/**,xpub69H7F5d8KSRgmmdJg2KhpAK8SR3DjMwAdkxj3ZuxV27CprR9LgpeyGmXUbC6wb7ERfvrnKZjXoUmmDznezpbZb7ap6r1D3tgFxHmwMkQTPH/**))", "tr([12345678/44'/0'/0']xpub6BVZ6JrGsWsUbpP74S8rnz13hVFDtYtKyuTTEYPNSF6GFpDFpL1YXWg3BpwpUWAnsZZ7Qe3XKz7GL3BEx3RQVq61cxqSkjceq25S1xFKFVa,{pk(xpub6AGdromjXf5yf3m7ndaCoR9Ac3UjwTvQ7QQkZoyoh2vfGE9i1AwB2vCbvjTpBL1KRERUsGszg63SVNXsHZU3CiykQqtZPrdXKMdaG2vs6uu),pk(xpub6AnhdkteWC4kPQvkY3QQXGmDCMfmFoYzEQ7FwRFa4BQ1a22k4VL4BD3Jdcog2Sf2KzBscXXAdPRMgjCBDeq6bAryqnMaWX2FaVUGPxWMLDh)})", "tr(xpub6AEWqA1MNRzBBXenkug4NtNguDKTNcXoKQj8fU9VQyid38yikruFRffjoDm9UEaHGEJ6jQxjYdWWZRxR7Xy5ePrQNjohXJuNzkRNSiiBUcE,sortedmulti_a(2,[11223344/44'/0'/0']xpub6AyJhEKxcPaPnYNuA7VBeUQ24v6mEzzPSX5AJm3TSyg1Zsti7rnGKy1Hg6JAdXKF4QUmFZbby9p97AjBNm2VFCEec2ip5C9JntyxosmCeMW,xpub6AQVHBgieCHpGo4GhpGAo4v9v7hfr2Kr4D8ZQJqJwbEyZwtW3pWYSLRQyrNYbTzpoq6XpFtaKZGnEGUMtiydCgqsJDAZNqs9L5QDNKqUBsV))", "tr([11111111/44'/0'/0']xpub6CLZSUDtcUhJVDoPSY8pSRKi4W1RSSLBgwZ2AYmwTH9Yv5tPVFHZxJBUQ27QLLwHej6kfo9DQQbwaHmpXsQq59CjtsE2gNLHmojwgMrsQNe/**,{and_v(v:pk([22222222/44'/0'/0']xpub6CiztfGsUxmpwkWe6gvz8d5VHyFLDoiPpeUfWmQ2vWAhQL3Z1hhEc6PE4irFs4bzjS7dCB4yyinaubrCpFJq4bcKGCD4jjqTxaWiKAJ7mvJ/**),older(52596)),multi_a(2,[33333333/44'/0'/0']xpub6DTZd6od7is2wxXndmE7zaUifzFPwVKshVSGEZedfTJtUjfLyhy4hgCW15hvxRpGaDmtiFoJKaCEaSRfXrQBuYRx18zwquy46dwBsJnsrz2/**,[44444444/44'/0'/0']xpub6BnK4wFbPeLZM4VNjoUA4yLCru6kCT3bhDJNBhbzHLGp1fmgK6muz27h4drixJZeHG8vSS5U5EYyE3gE8ozG94iNg3NDYE8M5YafvhzhMR9/**)})", "tr(musig([33333333/44'/0'/0']xpub6DTZd6od7is2wxXndmE7zaUifzFPwVKshVSGEZedfTJtUjfLyhy4hgCW15hvxRpGaDmtiFoJKaCEaSRfXrQBuYRx18zwquy46dwBsJnsrz2,[44444444/44'/0'/0']xpub6BnK4wFbPeLZM4VNjoUA4yLCru6kCT3bhDJNBhbzHLGp1fmgK6muz27h4drixJZeHG8vSS5U5EYyE3gE8ozG94iNg3NDYE8M5YafvhzhMR9)/**,{and_v(v:pk([22222222/44'/0'/0']xpub6CiztfGsUxmpwkWe6gvz8d5VHyFLDoiPpeUfWmQ2vWAhQL3Z1hhEc6PE4irFs4bzjS7dCB4yyinaubrCpFJq4bcKGCD4jjqTxaWiKAJ7mvJ/**),older(52596)),pk([11111111/44'/0'/0']xpub6CLZSUDtcUhJVDoPSY8pSRKi4W1RSSLBgwZ2AYmwTH9Yv5tPVFHZxJBUQ27QLLwHej6kfo9DQQbwaHmpXsQq59CjtsE2gNLHmojwgMrsQNe/**)})", ] for desc in descriptors: # Demoes the conversion from a "sane" descriptor to a wallet policy print(f"Descriptor:\n{desc}") wp = WalletPolicy.from_descriptor(desc) print(f"Policy descriptor template:\n{wp.descriptor_template}") print(f"Keys:\n{wp.keys_info}") print("======================================================\n") # Converting back to descriptors also works, as long as we take care of /** assert wp.to_descriptor().replace("/<0;1>/*", "/**") == desc ================================================ FILE: bip-0388.mediawiki ================================================
  BIP: 388
  Layer: Applications
  Title: Wallet Policies for Descriptor Wallets
  Authors: Salvatore Ingala 
  Status: Complete
  Type: Specification
  Assigned: 2022-11-16
  License: BSD-2-Clause
  Discussion: 2022-05-10: https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2022-May/020423.html
== Abstract == Software wallets and hardware signing devices typically partition funds into separate "accounts". When signing or visualizing a transaction, aggregate flows of funds of all accounts affected by the transaction may (and should) be displayed to the user. Wallet policies build on top of output script descriptors to represent such accounts in a compact, reviewable way. An account encompasses a logical group of receive and change addresses, and each wallet policy represents all descriptors necessary to describe an account in its entirety. We simplify the language to suit devices with limited memory, where even keeping the entire descriptor in memory could be a major hurdle, by reducing the generality of descriptors to just the essential features and by separating the extended pubkeys and other key information from the descriptor. This results in a more compact representation and simplifies the inspection of the policy by the user. The compilation of wallet policies to the corresponding descriptor is trivial, and the reverse process is easy for supported descriptors, because the language is kept similar to that of output script descriptors. == Copyright == This BIP is licensed under the BSD 2-clause license. == Motivation == ''[[bip-0380.mediawiki|Output Script Descriptors]]'' were introduced in Bitcoin Core as a way to represent collections of output scripts. It is a general and flexible language, designed to catch all the possible use-cases of bitcoin wallets (that is, if you know the script and you have the necessary keys, it will be possible to sign transactions with any descriptor-based software wallet). Unfortunately, descriptors are not a perfect match for the typical usage of hardware signing devices (often also called ''hardware wallets''). Most of them have some of the following limitations when compared to a general-purpose machine running Bitcoin Core: * they are embedded devices with limited RAM and computational power; * they cannot import additional private keys (that is, they can only sign with keys derived from a single seed via [[bip-0032.mediawiki|BIP-32]]); * they have limited storage, or they might not have persistent storage at all (''stateless design''). Moreover, other limitations like the limited size of the screen might affect what design choices are available in practice. Therefore, minimizing the amount of information shown on-screen is important for a good user experience. The ability for the user to completely validate on-screen the kind of script used (and each of the involved keys) is crucial for secure usage, as the machine that is interacting with the hardware signer (and running the software wallet) is considered untrusted. A more native, compact representation of the wallet receive and change addresses might also benefit the UX of software wallets when they use descriptors (possibly with miniscript) for representing complex locking conditions. We remark that wallet policies are not related to the ''policy'' language, a higher level language that can be compiled to [[bip-0379.md|miniscript]]. === Security, privacy and UX concerns for hardware signing devices === The usage of complex scripts presents challenges in terms of both security and user experience for a hardware signing device. ==== Security issues ==== Hardware signing devices strive to guarantee that no action can be performed without the user’s consent as long as the user correctly verifies the information that is shown on the device’s screen before approving. This must hold even in scenarios where the attacker has full control of the machine that is connected to the signing device, and can execute arbitrary requests, or tamper with the legitimate user's requests. Therefore, it is not at all trivial to allow complex scripts, especially if they contain keys that belong to third parties. The hardware signing device must guarantee that the user knows precisely what "policy" is being used to spend the funds, and that any "unspent" funds (if any) that is sent to a change address will be protected by the same policy. This makes it impossible for an attacker to surreptitiously modify the policy, therefore stealing or burning the user's funds. ==== Avoiding key reuse ==== Reusing public keys within a script is a source of malleability when using miniscript policies, which has potential security implications. Reusing keys across different UTXOs harms user privacy by allowing external parties to link these UTXOs to the same entity once they are spent. By constraining the derivation path patterns to have a uniform structure, wallet policies prevent key reuse among the same or different UTXOs of the same account. It is strongly recommended to avoid key reuse across accounts. Distinct public keys per account can be guaranteed by using distinct hardened derivation paths. This specification does not mandate hardened derivation in order to maintain compatibility with existing deployments that do not adhere to this recommendation. It is out of scope for this document to guarantee that users do not reuse extended public keys among different wallet accounts. This is still very important, but the responsibility is left to the users and their software wallet. ==== UX issues ==== Miniscript (and taproot trees) allow substantially more complex spending policies. It is a challenge to ensure that the user can practically verify such spending policies on the screen. We set two fundamental design goals: * Minimize the amount of information that is shown on screen - so that the user can actually validate it. * Minimize the number of times the user has to validate such information. Designing a secure protocol for the coordination of a descriptor wallet among distant parties is also a challenging problem that is out of the scope of this document. See [[bip-0129.mediawiki|BIP-129 (Bitcoin Secure Multisig Setup)]] for an approach designed for multisig wallets. Regardless of the approach, the ability for the user to carefully verify all the details of the spending policies using the hardware signer's screen is a prerequisite for security in adversarial environments. === Policy registration as a solution === A solution to address the security concerns, and part of the UX concerns, is to have a registration flow for the wallet policy in the hardware signing device. The ''wallet policy'' must contain enough information to generate all the relevant addresses/scripts, and for the hardware signing device to identify the keys that it controls and that are needed to spend the funds sent to those addresses. Before a new policy is used for the first time, the user will register a wallet policy into the hardware device. While the details of the process are out of scope in this document, the flow should be something similar to the following: # The software wallet initiates a ''wallet policy registration'' on the hardware signing device; the information should include the wallet policy, but also a unique ''name'' that identifies the policy. # The device shows the wallet policy to the user using the secure screen. # After inspecting the policy and comparing it with a trusted source (for example a printed backup), the user approves the policy. # If stateful, the hardware signing device persists the policy in its permanent memory; if stateless, it returns a "proof of registration". The '''proof of registration''' will allow the hardware signer to verify that a certain policy was indeed previously approved by the user, and is therefore safe to use without repeating the expensive user verification procedure. The details of how to create a proof of registration are out of scope for this document; using a Message Authentication Code on a hash committing to the wallet policy, its name and any additional metadata is an effective solution if correctly executed. Once a policy is registered, the hardware signing device can perform the typical operations securely: * generating receive and change addresses; * showing addresses on the secure screen; * sign transactions spending from a wallet, while correctly identifying change addresses and computing the transaction fees. Before any of the actions mentioned above, the hardware signing device will retrieve the policy from its permanent storage if stateful; if stateless it will validate the proof of registration before using the wallet policy provided by the client. Once the previously registered policy is correctly identified and approved by the user (for example by showing its name), and as long as the policy registration was executed securely, hardware signing devices can provide a user experience similar to the usual one for single-signature transactions. === Avoiding blowup in descriptor size === While reusing a pubkey in different branches of a miniscript is explicitly forbidden by miniscript (as it has certain negative security implications), it is still reasonable to reuse the same xpub in multiple places, albeit with different final steps of derivation (so that the actual pubkeys that are used in the script are indeed different). In fact, there are many reasonable spending policies with a quadratic size in the number of participants. For example, using Taproot, a 3-of-5 threshold wallet could use: * a key path with a 5-of-5 [[bip-0327.mediawiki|MuSig2]] aggregated key * a script tree with 11 leaves: ** 10 different scripts using a 3-of-3 MuSig2 aggregated key, plus ** a final leaf with a fallback 3-of-5 multisig using multi_a (in case interactive signing is not available). With each xpub being 118 bytes long, the repetition of xpubs makes the descriptor become extremely large. Replacing the common part of the key with a short key placeholder and organizing all the key expressions in a separate list helps to keep the size of the wallet policy small, which is crucial to allow human inspection during the registration flow. == Specification == This section formally defines wallet policies, and how they relate to output script descriptors. === Formal definition === A ''wallet policy'' is composed of a ''wallet descriptor template'', together with a vector of ''key information items''. ==== Wallet descriptor template ==== A ''wallet descriptor template'' is a SCRIPT expression. SCRIPT expressions: * sh(SCRIPT) (top level only): P2SH embed the argument. * wsh(SCRIPT) (top level or inside sh only): P2WSH embed the argument. * pkh(KEY) (not inside tr): P2PKH output for the given public key. * wpkh(KEY) (top level or inside sh only): P2WPKH output for the given compressed pubkey. * multi(k,KEY_1,KEY_2,...,KEY_n) (inside sh or wsh only): ''k''-of-''n'' multisig script. * sortedmulti(k,KEY_1,KEY_2,...,KEY_n) (inside sh or wsh only): ''k''-of-''n'' multisig script with keys sorted lexicographically in the resulting script. * tr(KEY) or tr(KEY,TREE) (top level only): P2TR output with the specified key as internal key, and optionally a tree of script paths. * any valid miniscript template (inside wsh or tr only). See [[bip-0379.md|BIP-379]] for a precise specification of all the valid miniscript SCRIPT expressions. TREE expressions: * any SCRIPT expression * An open brace {, a TREE expression, a comma ,, a TREE expression, and a closing brace } KEY expressions consist of * a KP expression * ''always'' followed by either: ** the string /**, or ** a string of the form //*, for two distinct decimal numbers NUM representing unhardened derivations, or ** any of the additional, implementation-specific valid derivation path patterns (see [[#optional-derivation-paths|Optional derivation paths]] below). KP expressions (key placeholders) consist of either: * a KI (key index) expression, or * (only inside tr): musig(KI_1,KI_2,...,KI_n) A KI (key index) expression consists of: * a single character @ * followed by a non-negative decimal number, with no leading zeros (except for @0) The /** in the placeholder template represents commonly used paths for receive/change addresses, and is equivalent to /<0;1>/*. Note that while [[bip-0389.mediawiki|BIP-389]] allows multipath / expressions with an arbitrary number of options, this specification restricts it to exactly 2 choices (with the typical meaning of receive/change addresses). SCRIPT, TREE and KEY expressions map directly to the corresponding concepts defined in [[bip-0380.mediawiki|BIP-380]] for output script descriptors. Each KEY expression always corresponds to a precise public key in the final bitcoin Script. Therefore, all the derivation steps in the BIP-32 hierarchy are included in a KEY expression. Each KP (key placeholder) expression, on the other hand, maps to the root of all the corresponding public keys for all the possible UTXOs that belong to the account represented in the wallet policy. Therefore, no derivation steps are allowed in a KP expression. A KI (key index) @i for some number ''i'' represents the ''i''-th key in the vector of key information items (which must be of size at least ''i + 1'', or the wallet policy is invalid). Note: while descriptor templates for miniscript are not formally defined in this version of the document (pending standardization), it is straightforward to adapt this approach by adding additional SCRIPT expressions. ==== Key information vector ==== Each element of the key origin information vector is a KEY_INFO expression, containing an extended public key, and (optionally) its key origin. * Optionally, key origin information, consisting of: ** An open bracket [ ** Exactly 8 hex characters for the fingerprint of the master key from which this key is derived from (see [[bip-0032.mediawiki|BIP-32]] for details) ** Followed by zero or more /NUM' or /NUM path elements to indicate hardened or unhardened derivation steps between the fingerprint and the xpub that follows ** A closing bracket ] * Followed by the actual key, which is a serialized extended public key (as defined in [[bip-0032.mediawiki|BIP-32]]). ==== Additional rules ==== A wallet policy must have at least one key placeholder and the corresponding key. The public keys obtained by deserializing elements of the key information vector must be pairwise distinct'''Why must public keys be distinct?''' Reusing pubkeys could be insecure in the context of wallet policies containing [https://bitcoin.sipa.be/miniscript/ miniscript]. Avoiding repeated public keys altogether avoids the problem at the source.. If two KEY are KP//* and KP//* for the same key placeholder KP, then the sets {M, N} and {P, Q} must be disjoint. Two musig key placeholders are the same if they have exactly the same set of key indexes (regardless of the order). Repeated KI expressions are not allowed inside a musig placeholder. The key information vector should be ordered so that placeholder @i never appears for the first time before an occurrence of @j for some j < i; for example, the first placeholder is always @0, the next one is @1, etc. === Descriptor derivation === From a wallet descriptor template (and the associated vector of key information items), one can therefore obtain the corresponding multipath descriptor by: * replacing each key placeholder with the corresponding key origin information; * replacing every /** with /<0;1>/*. For example, the wallet descriptor pkh(@0/**) with key information ["[d34db33f/44'/0'/0']xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL"] produces the following multipath descriptor: pkh([d34db33f/44'/0'/0']xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL/<0;1>/*) === Implementation guidelines === It is acceptable to implement only a subset of the possible wallet policies defined by this standard. It is recommended that any limitations are clearly documented. Implementations can add additional metadata that is stored together with the wallet policy for the purpose of wallet policy registration and later usage. Metadata can be vendor-specific and is out of the scope of this document. Any implementation in a software wallet that allows wallet policies not matching any of the specifications in [[bip-0044.mediawiki|BIP-44]], [[bip-0049.mediawiki|BIP-49]], [[bip-0084.mediawiki|BIP-84]], [[bip-0086.mediawiki|BIP-86]] (especially if involving external cosigners) should put great care into a process for backing up the wallet policy that represents the account. In fact, unlike standard single-signature scenarios, the seed alone is no longer enough to discover wallet policies with existing funds, and the loss of the backup is likely to lead to permanent loss of funds. Unlike the seed, leaking such backups only affects the privacy of the user, but it does not allow the attacker to steal funds. === Optional derivation paths === In order to allow supporting legacy derivation schemes (for example, using simply /* instead of the more common //* scheme most software wallets use today), or other schemes that are not covered in this document, implementations might choose to permit additional derivation patterns for the key placeholder (KP) expressions. However, care needs to be taken in view of the following considerations: * Allowing derivation schemes with a different length or cardinality in the same wallet policy would make it difficult to guarantee that there are no repeated pubkeys for every possible address generated by the policy. For example, @0/<0;1>/* and @1/* would generate the same pubkeys if the second public key in the key information vector is one of the first two unhardened children of the first public key. This could cause malleability with potential security implications (for example, in policies containing miniscript). * Allowing naked pubkeys with no /* suffix (for example a descriptor template like wsh(multi(2,@0,@1/<0;1>/*))) would cause a pubkey to be repeated in every output generated from the policy, which would result in a total loss of privacy. == Examples == In the examples in this section, the vector of key information items is omitted. See the test vectors below for complete examples. Common single-signature account patterns: * pkh(@0/**) (legacy). * wpkh(@0/**) (native segwit). * sh(wpkh(@0/**)) (nested segwit). * tr(@0/**) (taproot single-signature account). Common multisig schemes: * wsh(multi(2,@0/**,@1/**)) - SegWit 2-of-2 multisig, keys in order. * sh(sortedmulti(2,@0/**,@1/**,@2/**)) - Legacy 2-of-3 multisig, sorted keys. * tr(musig(@0,@1)/**) - MuSig2 2-of-2 in the taproot keypath Some miniscript policies in wsh: * wsh(and_v(v:pk(@0/**),or_d(pk(@1/**),older(12960)))) - Trust-minimized second factor, degrading to a single signature after about 90 days. * wsh(thresh(3,pk(@0/**),s:pk(@1/**),s:pk(@2/**),sln:older(12960))) - A 3-of-3 wallet that becomes a 2-of-3 if coins are not spent for about 90 days. * wsh(or_d(pk(@0/**),and_v(v:multi(2,@1/**,@2/**,@3/**),older(65535)))) - A singlesig wallet with automatic inheritance to a timelocked 2-of-3 multisig of family members. == Test Vectors == === Valid policies === [[bip-0044.mediawiki|BIP-44]], first account Descriptor template: pkh(@0/**) Keys info: ["[6738736c/44'/0'/0']xpub6Br37sWxruYfT8ASpCjVHKGwgdnYFEn98DwiN76i2oyY6fgH1LAPmmDcF46xjxJr22gw4jmVjTE2E3URMnRPEPYyo1zoPSUba563ESMXCeb"] Descriptor: pkh([6738736c/44'/0'/0']xpub6Br37sWxruYfT8ASpCjVHKGwgdnYFEn98DwiN76i2oyY6fgH1LAPmmDcF46xjxJr22gw4jmVjTE2E3URMnRPEPYyo1zoPSUba563ESMXCeb/<0;1>/*)
[[bip-0049.mediawiki|BIP-49]], second account Descriptor template: sh(wpkh(@0/**)) Keys info: ["[6738736c/49'/0'/1']xpub6Bex1CHWGXNNwGVKHLqNC7kcV348FxkCxpZXyCWp1k27kin8sRPayjZUKDjyQeZzGUdyeAj2emoW5zStFFUAHRgd5w8iVVbLgZ7PmjAKAm9"] Descriptor: sh(wpkh([6738736c/49'/0'/1']xpub6Bex1CHWGXNNwGVKHLqNC7kcV348FxkCxpZXyCWp1k27kin8sRPayjZUKDjyQeZzGUdyeAj2emoW5zStFFUAHRgd5w8iVVbLgZ7PmjAKAm9/<0;1>/*))
[[bip-0084.mediawiki|BIP-84]], third account Descriptor template: wpkh(@0/**) Keys info: ["[6738736c/84'/0'/2']xpub6CRQzb8u9dmMcq5XAwwRn9gcoYCjndJkhKgD11WKzbVGd932UmrExWFxCAvRnDN3ez6ZujLmMvmLBaSWdfWVn75L83Qxu1qSX4fJNrJg2Gt"] Descriptor: wpkh([6738736c/84'/0'/2']xpub6CRQzb8u9dmMcq5XAwwRn9gcoYCjndJkhKgD11WKzbVGd932UmrExWFxCAvRnDN3ez6ZujLmMvmLBaSWdfWVn75L83Qxu1qSX4fJNrJg2Gt/<0;1>/*)
[[bip-0086.mediawiki|BIP-86]], first account Descriptor template: tr(@0/**) Keys info: ["[6738736c/86'/0'/0']xpub6CryUDWPS28eR2cDyojB8G354izmx294BdjeSvH469Ty3o2E6Tq5VjBJCn8rWBgesvTJnyXNAJ3QpLFGuNwqFXNt3gn612raffLWfdHNkYL"] Descriptor: tr([6738736c/86'/0'/0']xpub6CryUDWPS28eR2cDyojB8G354izmx294BdjeSvH469Ty3o2E6Tq5VjBJCn8rWBgesvTJnyXNAJ3QpLFGuNwqFXNt3gn612raffLWfdHNkYL/<0;1>/*)
[[bip-0048.mediawiki|BIP-48]] P2WSH multisig Descriptor template: wsh(sortedmulti(2,@0/**,@1/**)) Keys info: ["[6738736c/48'/0'/0'/2']xpub6FC1fXFP1GXLX5TKtcjHGT4q89SDRehkQLtbKJ2PzWcvbBHtyDsJPLtpLtkGqYNYZdVVAjRQ5kug9CsapegmmeRutpP7PW4u4wVF9JfkDhw", "[b2b1f0cf/48'/0'/0'/2']xpub6EWhjpPa6FqrcaPBuGBZRJVjzGJ1ZsMygRF26RwN932Vfkn1gyCiTbECVitBjRCkexEvetLdiqzTcYimmzYxyR1BZ79KNevgt61PDcukmC7"] Descriptor: wsh(sortedmulti(2,[6738736c/48'/0'/0'/2']xpub6FC1fXFP1GXLX5TKtcjHGT4q89SDRehkQLtbKJ2PzWcvbBHtyDsJPLtpLtkGqYNYZdVVAjRQ5kug9CsapegmmeRutpP7PW4u4wVF9JfkDhw/<0;1>/*,[b2b1f0cf/48'/0'/0'/2']xpub6EWhjpPa6FqrcaPBuGBZRJVjzGJ1ZsMygRF26RwN932Vfkn1gyCiTbECVitBjRCkexEvetLdiqzTcYimmzYxyR1BZ79KNevgt61PDcukmC7/<0;1>/*))
Miniscript: A 3-of-3 that becomes a 2-of-3 after 90 days Descriptor template: wsh(thresh(3,pk(@0/**),s:pk(@1/**),s:pk(@2/**),sln:older(12960))) Keys info: ["[6738736c/48'/0'/0'/100']xpub6FC1fXFP1GXQpyRFfSE1vzzySqs3Vg63bzimYLeqtNUYbzA87kMNTcuy9ubr7MmavGRjW2FRYHP4WGKjwutbf1ghgkUW9H7e3ceaPLRcVwa", "[b2b1f0cf/44'/0'/0'/100']xpub6EYajCJHe2CK53RLVXrN14uWoEttZgrRSaRztujsXg7yRhGtHmLBt9ot9Pd5ugfwWEu6eWyJYKSshyvZFKDXiNbBcoK42KRZbxwjRQpm5Js", "[a666a867/44'/0'/0'/100']xpub6Dgsze3ujLi1EiHoCtHFMS9VLS1UheVqxrHGfP7sBJ2DBfChEUHV4MDwmxAXR2ayeytpwm3zJEU3H3pjCR6q6U5sP2p2qzAD71x9z5QShK2"] Descriptor: wsh(thresh(3,pk([6738736c/48'/0'/0'/100']xpub6FC1fXFP1GXQpyRFfSE1vzzySqs3Vg63bzimYLeqtNUYbzA87kMNTcuy9ubr7MmavGRjW2FRYHP4WGKjwutbf1ghgkUW9H7e3ceaPLRcVwa/<0;1>/*),s:pk([b2b1f0cf/44'/0'/0'/100']xpub6EYajCJHe2CK53RLVXrN14uWoEttZgrRSaRztujsXg7yRhGtHmLBt9ot9Pd5ugfwWEu6eWyJYKSshyvZFKDXiNbBcoK42KRZbxwjRQpm5Js/<0;1>/*),s:pk([a666a867/44'/0'/0'/100']xpub6Dgsze3ujLi1EiHoCtHFMS9VLS1UheVqxrHGfP7sBJ2DBfChEUHV4MDwmxAXR2ayeytpwm3zJEU3H3pjCR6q6U5sP2p2qzAD71x9z5QShK2/<0;1>/*),sln:older(12960)))
Miniscript: A singlesig wallet with automatic inheritance to a timelocked 2-of-3 multisig Descriptor template: wsh(or_d(pk(@0/**),and_v(v:multi(2,@1/**,@2/**,@3/**),older(65535)))) Keys info: ["[6738736c/48'/0'/0'/100']xpub6FC1fXFP1GXQpyRFfSE1vzzySqs3Vg63bzimYLeqtNUYbzA87kMNTcuy9ubr7MmavGRjW2FRYHP4WGKjwutbf1ghgkUW9H7e3ceaPLRcVwa", "[b2b1f0cf/44'/0'/0'/100']xpub6EYajCJHe2CK53RLVXrN14uWoEttZgrRSaRztujsXg7yRhGtHmLBt9ot9Pd5ugfwWEu6eWyJYKSshyvZFKDXiNbBcoK42KRZbxwjRQpm5Js", "[a666a867/44'/0'/0'/100']xpub6Dgsze3ujLi1EiHoCtHFMS9VLS1UheVqxrHGfP7sBJ2DBfChEUHV4MDwmxAXR2ayeytpwm3zJEU3H3pjCR6q6U5sP2p2qzAD71x9z5QShK2", "[bb641298/44'/0'/0'/100']xpub6Dz8PHFmXkYkykQ83ySkruky567XtJb9N69uXScJZqweYiQn6FyieajdiyjCvWzRZ2GoLHMRE1cwDfuJZ6461YvNRGVBJNnLA35cZrQKSRJ"] Descriptor: wsh(or_d(pk([6738736c/48'/0'/0'/100']xpub6FC1fXFP1GXQpyRFfSE1vzzySqs3Vg63bzimYLeqtNUYbzA87kMNTcuy9ubr7MmavGRjW2FRYHP4WGKjwutbf1ghgkUW9H7e3ceaPLRcVwa/<0;1>/*),and_v(v:multi(2,[b2b1f0cf/44'/0'/0'/100']xpub6EYajCJHe2CK53RLVXrN14uWoEttZgrRSaRztujsXg7yRhGtHmLBt9ot9Pd5ugfwWEu6eWyJYKSshyvZFKDXiNbBcoK42KRZbxwjRQpm5Js/<0;1>/*,[a666a867/44'/0'/0'/100']xpub6Dgsze3ujLi1EiHoCtHFMS9VLS1UheVqxrHGfP7sBJ2DBfChEUHV4MDwmxAXR2ayeytpwm3zJEU3H3pjCR6q6U5sP2p2qzAD71x9z5QShK2/<0;1>/*,[bb641298/44'/0'/0'/100']xpub6Dz8PHFmXkYkykQ83ySkruky567XtJb9N69uXScJZqweYiQn6FyieajdiyjCvWzRZ2GoLHMRE1cwDfuJZ6461YvNRGVBJNnLA35cZrQKSRJ/<0;1>/*),older(65535))))
Taproot wallet policy with sortedmulti_a and a miniscript leaf Descriptor template: tr(@0/**,{sortedmulti_a(1,@0/<2;3>/*,@1/**),or_b(pk(@2/**),s:pk(@3/**))}) Keys info: ["[6738736c/48'/0'/0'/100']xpub6FC1fXFP1GXQpyRFfSE1vzzySqs3Vg63bzimYLeqtNUYbzA87kMNTcuy9ubr7MmavGRjW2FRYHP4WGKjwutbf1ghgkUW9H7e3ceaPLRcVwa", "xpub6Fc2TRaCWNgfT49nRGG2G78d1dPnjhW66gEXi7oYZML7qEFN8e21b2DLDipTZZnfV6V7ivrMkvh4VbnHY2ChHTS9qM3XVLJiAgcfagYQk6K", "xpub6GxHB9kRdFfTqYka8tgtX9Gh3Td3A9XS8uakUGVcJ9NGZ1uLrGZrRVr67DjpMNCHprZmVmceFTY4X4wWfksy8nVwPiNvzJ5pjLxzPtpnfEM", "xpub6GjFUVVYewLj5no5uoNKCWuyWhQ1rKGvV8DgXBG9Uc6DvAKxt2dhrj1EZFrTNB5qxAoBkVW3wF8uCS3q1ri9fueAa6y7heFTcf27Q4gyeh6"] Descriptor: tr([6738736c/48'/0'/0'/100']xpub6FC1fXFP1GXQpyRFfSE1vzzySqs3Vg63bzimYLeqtNUYbzA87kMNTcuy9ubr7MmavGRjW2FRYHP4WGKjwutbf1ghgkUW9H7e3ceaPLRcVwa/<0;1>/*,{sortedmulti_a(1,[6738736c/48'/0'/0'/100']xpub6FC1fXFP1GXQpyRFfSE1vzzySqs3Vg63bzimYLeqtNUYbzA87kMNTcuy9ubr7MmavGRjW2FRYHP4WGKjwutbf1ghgkUW9H7e3ceaPLRcVwa/<2;3>/*,xpub6Fc2TRaCWNgfT49nRGG2G78d1dPnjhW66gEXi7oYZML7qEFN8e21b2DLDipTZZnfV6V7ivrMkvh4VbnHY2ChHTS9qM3XVLJiAgcfagYQk6K/<0;1>/*),or_b(pk(xpub6GxHB9kRdFfTqYka8tgtX9Gh3Td3A9XS8uakUGVcJ9NGZ1uLrGZrRVr67DjpMNCHprZmVmceFTY4X4wWfksy8nVwPiNvzJ5pjLxzPtpnfEM/<0;1>/*),s:pk(xpub6GjFUVVYewLj5no5uoNKCWuyWhQ1rKGvV8DgXBG9Uc6DvAKxt2dhrj1EZFrTNB5qxAoBkVW3wF8uCS3q1ri9fueAa6y7heFTcf27Q4gyeh6/<0;1>/*))})
Taproot MuSig2 3-of-3 in the key path, with three 2-of-2 MuSig2 recovery paths after 90 days in the script paths Descriptor template: tr(musig(@0,@1,@2)/**,{and_v(v:pk(musig(@0,@1)/**),older(12960)),{and_v(v:pk(musig(@0,@2)/**),older(12960)),and_v(v:pk(musig(@1,@2)/**),older(12960))}}) Keys info: ["[6738736c/48'/0'/0'/100']xpub6FC1fXFP1GXQpyRFfSE1vzzySqs3Vg63bzimYLeqtNUYbzA87kMNTcuy9ubr7MmavGRjW2FRYHP4WGKjwutbf1ghgkUW9H7e3ceaPLRcVwa", "[b2b1f0cf/44'/0'/0'/100']xpub6EYajCJHe2CK53RLVXrN14uWoEttZgrRSaRztujsXg7yRhGtHmLBt9ot9Pd5ugfwWEu6eWyJYKSshyvZFKDXiNbBcoK42KRZbxwjRQpm5Js", "[a666a867/44'/0'/0'/100']xpub6Dgsze3ujLi1EiHoCtHFMS9VLS1UheVqxrHGfP7sBJ2DBfChEUHV4MDwmxAXR2ayeytpwm3zJEU3H3pjCR6q6U5sP2p2qzAD71x9z5QShK2"] Descriptor: tr(musig([6738736c/48'/0'/0'/100']xpub6FC1fXFP1GXQpyRFfSE1vzzySqs3Vg63bzimYLeqtNUYbzA87kMNTcuy9ubr7MmavGRjW2FRYHP4WGKjwutbf1ghgkUW9H7e3ceaPLRcVwa,[b2b1f0cf/44'/0'/0'/100']xpub6EYajCJHe2CK53RLVXrN14uWoEttZgrRSaRztujsXg7yRhGtHmLBt9ot9Pd5ugfwWEu6eWyJYKSshyvZFKDXiNbBcoK42KRZbxwjRQpm5Js,[a666a867/44'/0'/0'/100']xpub6Dgsze3ujLi1EiHoCtHFMS9VLS1UheVqxrHGfP7sBJ2DBfChEUHV4MDwmxAXR2ayeytpwm3zJEU3H3pjCR6q6U5sP2p2qzAD71x9z5QShK2)/<0;1>/*,{and_v(v:pk(musig([6738736c/48'/0'/0'/100']xpub6FC1fXFP1GXQpyRFfSE1vzzySqs3Vg63bzimYLeqtNUYbzA87kMNTcuy9ubr7MmavGRjW2FRYHP4WGKjwutbf1ghgkUW9H7e3ceaPLRcVwa,[b2b1f0cf/44'/0'/0'/100']xpub6EYajCJHe2CK53RLVXrN14uWoEttZgrRSaRztujsXg7yRhGtHmLBt9ot9Pd5ugfwWEu6eWyJYKSshyvZFKDXiNbBcoK42KRZbxwjRQpm5Js)/<0;1>/*),older(12960)),{and_v(v:pk(musig([6738736c/48'/0'/0'/100']xpub6FC1fXFP1GXQpyRFfSE1vzzySqs3Vg63bzimYLeqtNUYbzA87kMNTcuy9ubr7MmavGRjW2FRYHP4WGKjwutbf1ghgkUW9H7e3ceaPLRcVwa,[a666a867/44'/0'/0'/100']xpub6Dgsze3ujLi1EiHoCtHFMS9VLS1UheVqxrHGfP7sBJ2DBfChEUHV4MDwmxAXR2ayeytpwm3zJEU3H3pjCR6q6U5sP2p2qzAD71x9z5QShK2)/<0;1>/*),older(12960)),and_v(v:pk(musig([b2b1f0cf/44'/0'/0'/100']xpub6EYajCJHe2CK53RLVXrN14uWoEttZgrRSaRztujsXg7yRhGtHmLBt9ot9Pd5ugfwWEu6eWyJYKSshyvZFKDXiNbBcoK42KRZbxwjRQpm5Js,[a666a867/44'/0'/0'/100']xpub6Dgsze3ujLi1EiHoCtHFMS9VLS1UheVqxrHGfP7sBJ2DBfChEUHV4MDwmxAXR2ayeytpwm3zJEU3H3pjCR6q6U5sP2p2qzAD71x9z5QShK2)/<0;1>/*),older(12960))}}) === Invalid policies === The following descriptor templates are invalid: * pkh(@0): Key placeholder with no path following it * pkh(@0/0/**): Key placeholder with an explicit path present * sh(multi(1,@1/**,@0/**)): Key placeholders out of order * sh(multi(1,@0/**,@2/**)): Skipped key placeholder @1 * sh(multi(1,@0/**,@0/**)): Repeated keys with the same path expression * sh(multi(1,@0/<0;1>/*,@0/<1;2>/*)): Non-disjoint multipath expressions (@0/1/* appears twice) * sh(multi(1,@0/**,xpub6AHA9hZDN11k2ijHMeS5QqHx2KP9aMBRhTDqANMnwVtdyw2TDYRmF8PjpvwUFcL1Et8Hj59S3gTSMcUQ5gAqTz3Wd8EsMTmF3DChhqPQBnU/<0;1>/*)): Expression with a non-KP key present * pkh(@0/<0;1;2>/*): Allowed cardinality > 2 * tr(musig(@0/**,@1/**)): Derivation before aggregation is not allowed in wallet policies (despite being allowed in [[bip-0390.mediawiki|BIP-390]]) Remark: some of the examples of invalid descriptor templates may be valid via optional extensions. == Backwards Compatibility == The @ character used for key placeholders is not part of the syntax of output script descriptors, therefore any valid descriptor with at least one KEY expression is not a valid descriptor template. Vice versa, any descriptor template with at least one key placeholder is not a valid output script descriptor. Adoption of wallet policies in software and hardware wallets is opt-in. Conversion from wallet policies to the corresponding descriptors is programmatically extremely easy, and conversion from descriptors to wallet policies (when respecting the required patterns) can be automated. See the reference implementation below for some examples of conversion. Software wallets are recommended to allow exporting plain descriptors for the purposes of interoperability with software not using wallet policies. == Reference Implementation == Wallet policies are implemented in * the [https://github.com/LedgerHQ/app-bitcoin-new Ledger bitcoin application] since version 2.1.0; * the [https://github.com/digitalbitbox/bitbox02-firmware BitBox02 firmware] since version v9.15.0; * [https://github.com/Blockstream/Jade Blockstream Jade] since version v1.0.24, via [https://github.com/ElementsProject/libwally-core libwally-core] v1.0.0. * [https://github.com/btcpayserver/btcpayserver BTCPay Server] from version [https://github.com/btcpayserver/btcpayserver/pull/6684 v2.1.1]. (Currently only a limited subset of singlesig and multisig policies) * [https://github.com/MetacoSA/NBitcoin/ NBitcoin] through Miniscript.Parse. For development and testing purposes, we provide a [[bip-0388/wallet_policies.py|Python 3.7 reference implementation]] of simple classes to handle wallet policies, and the conversion to/from output script descriptors. The reference implementation is for demonstration purposes only and not to be used in production environments. == Change Log == * '''1.1.0''' (2024-11): ** Added support for musig key placeholders in descriptor templates. * '''1.0.0''' (2024-05): ** Initial version. == Footnotes == == Acknowledgments == The authors would like to thank the people who provided feedback in the bitcoin-dev list, and in person. ================================================ FILE: bip-0389.mediawiki ================================================
  BIP: 389
  Layer: Applications
  Title: Multipath Descriptor Key Expressions
  Authors: Ava Chow 
  Status: Draft
  Type: Informational
  Assigned: 2022-07-26
  License: BSD-2-Clause
  Requires: 380
==Abstract== This document specifies a modification to Key Expressions of Descriptors that are described in BIP 380. This modification allows Key Expressions to indicate BIP 32 derivation path steps that can have multiple values. ==Copyright== This BIP is licensed under the BSD 2-clause license. ==Motivation== Descriptors can describe the scripts that are used in a wallet, but wallets often require at least two descriptors for all of the scripts that they watch for. Wallets typically have one descriptor for producing receiving addresses, and the other for change addresses. These descriptors are often extremely similar - they produce the same types of scripts, derive keys from the same master key, and use derivation paths that are almost identical. The only differences are in the derivation path where one of the steps will be different between the descriptors. Thus it is useful to have a notation to represent both descriptors as a single descriptor where one of the derivation steps is a pair of values. ==Specification== For extended keys and their derivations paths in a Key Expression, BIP 380 states: * xpub encoded extended public key or xprv encoded extended private key (as defined in BIP 32) ** Followed by zero or more /NUM or /NUMh path elements indicating BIP 32 derivation steps to be taken after the given extended key. ** Optionally followed by a single /* or /*h final step to denote all direct unhardened or hardened children. This is modified to state: * xpub encoded extended public key or xprv encoded extended private key (as defined in BIP 32) ** Followed by zero or more /NUM (may be followed by h, H, or ' to indicate a hardened step) path elements indicating BIP 32 derivation steps to be taken after the given extended key. ** Followed by zero or one / (each NUM may be followed by h, H, or ' to indicate a hardened step) path element indicating a tuple of BIP 32 derivation steps to be taken after the given extended key. *** Followed by zero or more ;NUM (may be followed by h, H, or ' to indicate a hardened step) additional tuple values of BIP 32 derivation steps *** Followed by a single >/ ** Followed by zero or more /NUM (may be followed by h, H, or ' to indicate a hardened step) path elements indicating BIP 32 derivation steps to be taken after the given extended key. ** Optionally followed by a single /* (may be followed by h, H, or ' to indicate a hardened step) final step to denote all direct unhardened or hardened children. When a / is encountered, parsers should account for a presence of multiple descriptors where the first descriptor uses the first NUM, and a second descriptor uses the second NUM, and so on, until each NUM is accounted for in the production of public keys, scripts, and addresses, as well as descriptor import and export operations. Descriptors that contain multiple Key Expressions that each have a / must have tuples of exactly the same length so that they are derived in lockstep in the same way that /* paths in multiple Key expressions are handled. Duplicate NUMs within a tuple are not allowed. The common use case for this is to represent descriptors for producing receiving and change addresses. When interpreting for this use case, wallets should use the first descriptor for producing receiving addresses, and the second descriptor for producing change addresses. For this use case, the element will commonly be the value /<0;1> Note that only one / specifier is allowed in a Key Expression. ==Test Vectors== Valid multipath descriptors followed by the descriptors they expand into as sub-bullets * pk(xpub68NZiKmJWnxxS6aaHmn81bvJeTESw724CRDs6HbuccFQN9Ku14VQrADWgqbhhTHBaohPX4CjNLf9fq9MYo6oDaPPLPxSb7gwQN3ih19Zm4Y/<0;1>) ** pk(xpub68NZiKmJWnxxS6aaHmn81bvJeTESw724CRDs6HbuccFQN9Ku14VQrADWgqbhhTHBaohPX4CjNLf9fq9MYo6oDaPPLPxSb7gwQN3ih19Zm4Y/0) ** pk(xpub68NZiKmJWnxxS6aaHmn81bvJeTESw724CRDs6HbuccFQN9Ku14VQrADWgqbhhTHBaohPX4CjNLf9fq9MYo6oDaPPLPxSb7gwQN3ih19Zm4Y/1) * pkh(xprv9s21ZrQH143K31xYSDQpPDxsXRTUcvj2iNHm5NUtrGiGG5e2DtALGdso3pGz6ssrdK4PFmM8NSpSBHNqPqm55Qn3LqFtT2emdEXVYsCzC2U/<2147483647h;0>/0) ** pkh(xprv9s21ZrQH143K31xYSDQpPDxsXRTUcvj2iNHm5NUtrGiGG5e2DtALGdso3pGz6ssrdK4PFmM8NSpSBHNqPqm55Qn3LqFtT2emdEXVYsCzC2U/2147483647h/0) ** pkh(xprv9s21ZrQH143K31xYSDQpPDxsXRTUcvj2iNHm5NUtrGiGG5e2DtALGdso3pGz6ssrdK4PFmM8NSpSBHNqPqm55Qn3LqFtT2emdEXVYsCzC2U/0/0) * wpkh([ffffffff/13h]xpub69H7F5d8KSRgmmdJg2KhpAK8SR3DjMwAdkxj3ZuxV27CprR9LgpeyGmXUbC6wb7ERfvrnKZjXoUmmDznezpbZb7ap6r1D3tgFxHmwMkQTPH/<1;3>/2/* ** wpkh([ffffffff/13h]xpub69H7F5d8KSRgmmdJg2KhpAK8SR3DjMwAdkxj3ZuxV27CprR9LgpeyGmXUbC6wb7ERfvrnKZjXoUmmDznezpbZb7ap6r1D3tgFxHmwMkQTPH/1/2/*) ** wpkh([ffffffff/13h]xpub69H7F5d8KSRgmmdJg2KhpAK8SR3DjMwAdkxj3ZuxV27CprR9LgpeyGmXUbC6wb7ERfvrnKZjXoUmmDznezpbZb7ap6r1D3tgFxHmwMkQTPH/3/2/*) * multi(2,xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL/<1;2>/*,xpub68NZiKmJWnxxS6aaHmn81bvJeTESw724CRDs6HbuccFQN9Ku14VQrADWgqbhhTHBaohPX4CjNLf9fq9MYo6oDaPPLPxSb7gwQN3ih19Zm4Y/<3;4>/0/*) ** multi(2,xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL/1/*,xpub68NZiKmJWnxxS6aaHmn81bvJeTESw724CRDs6HbuccFQN9Ku14VQrADWgqbhhTHBaohPX4CjNLf9fq9MYo6oDaPPLPxSb7gwQN3ih19Zm4Y/3/0/*) ** multi(2,xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL/2/*,xpub68NZiKmJWnxxS6aaHmn81bvJeTESw724CRDs6HbuccFQN9Ku14VQrADWgqbhhTHBaohPX4CjNLf9fq9MYo6oDaPPLPxSb7gwQN3ih19Zm4Y/4/0/*) * pkh(xpub661MyMwAqRbcFW31YEwpkMuc5THy2PSt5bDMsktWQcFF8syAmRUapSCGu8ED9W6oDMSgv6Zz8idoc4a6mr8BDzTJY47LJhkJ8UB7WEGuduB/<0;1;2>) ** pkh(xpub661MyMwAqRbcFW31YEwpkMuc5THy2PSt5bDMsktWQcFF8syAmRUapSCGu8ED9W6oDMSgv6Zz8idoc4a6mr8BDzTJY47LJhkJ8UB7WEGuduB/0) ** pkh(xpub661MyMwAqRbcFW31YEwpkMuc5THy2PSt5bDMsktWQcFF8syAmRUapSCGu8ED9W6oDMSgv6Zz8idoc4a6mr8BDzTJY47LJhkJ8UB7WEGuduB/1) ** pkh(xpub661MyMwAqRbcFW31YEwpkMuc5THy2PSt5bDMsktWQcFF8syAmRUapSCGu8ED9W6oDMSgv6Zz8idoc4a6mr8BDzTJY47LJhkJ8UB7WEGuduB/2) * sh(multi(2,xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL/<1;2;3>/0/*,xpub68NZiKmJWnxxS6aaHmn81bvJeTESw724CRDs6HbuccFQN9Ku14VQrADWgqbhhTHBaohPX4CjNLf9fq9MYo6oDaPPLPxSb7gwQN3ih19Zm4Y/0/*,xpub661MyMwAqRbcGDZQUKLqmWodYLcoBQnQH33yYkkF3jjxeLvY8qr2wWGEWkiKFaaQfJCoi3HeEq3Dc5DptfbCyjD38fNhSqtKc1UHaP4ba3t/0/0/<3;4;5>/*)) ** sh(multi(2,xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL/1/0/*,xpub68NZiKmJWnxxS6aaHmn81bvJeTESw724CRDs6HbuccFQN9Ku14VQrADWgqbhhTHBaohPX4CjNLf9fq9MYo6oDaPPLPxSb7gwQN3ih19Zm4Y/0/*,xpub661MyMwAqRbcGDZQUKLqmWodYLcoBQnQH33yYkkF3jjxeLvY8qr2wWGEWkiKFaaQfJCoi3HeEq3Dc5DptfbCyjD38fNhSqtKc1UHaP4ba3t/0/0/3/*)) ** sh(multi(2,xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL/2/0/*,xpub68NZiKmJWnxxS6aaHmn81bvJeTESw724CRDs6HbuccFQN9Ku14VQrADWgqbhhTHBaohPX4CjNLf9fq9MYo6oDaPPLPxSb7gwQN3ih19Zm4Y/0/*,xpub661MyMwAqRbcGDZQUKLqmWodYLcoBQnQH33yYkkF3jjxeLvY8qr2wWGEWkiKFaaQfJCoi3HeEq3Dc5DptfbCyjD38fNhSqtKc1UHaP4ba3t/0/0/4/*)) ** sh(multi(2,xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL/3/0/*,xpub68NZiKmJWnxxS6aaHmn81bvJeTESw724CRDs6HbuccFQN9Ku14VQrADWgqbhhTHBaohPX4CjNLf9fq9MYo6oDaPPLPxSb7gwQN3ih19Zm4Y/0/*,xpub661MyMwAqRbcGDZQUKLqmWodYLcoBQnQH33yYkkF3jjxeLvY8qr2wWGEWkiKFaaQfJCoi3HeEq3Dc5DptfbCyjD38fNhSqtKc1UHaP4ba3t/0/0/5/*)) Invalid descriptors * Multiple multipath specifiers: pkh(xprv9s21ZrQH143K31xYSDQpPDxsXRTUcvj2iNHm5NUtrGiGG5e2DtALGdso3pGz6ssrdK4PFmM8NSpSBHNqPqm55Qn3LqFtT2emdEXVYsCzC2U/<0;1>/<2;3>) * Multipath specifier in origin: pkh([deadbeef/<0;1>]xpub661MyMwAqRbcFW31YEwpkMuc5THy2PSt5bDMsktWQcFF8syAmRUapSCGu8ED9W6oDMSgv6Zz8idoc4a6mr8BDzTJY47LJhkJ8UB7WEGuduB/0) * Multipath specifiers of mismatched lengths: tr(xpub661MyMwAqRbcF3yVrV2KyYetLMYA5mCbv4BhrKwUrFE9LZM6JRR1AEt8Jq4V4C8LwtTke6YEEdCZqgXp85YRk2j74EfJKhe3QybQ9kcUjs4/<6;7;8;9>/*,{pk(xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL/<1;2;3>/0/*),pk(xpub661MyMwAqRbcGDZQUKLqmWodYLcoBQnQH33yYkkF3jjxeLvY8qr2wWGEWkiKFaaQfJCoi3HeEq3Dc5DptfbCyjD38fNhSqtKc1UHaP4ba3t/0/0/<3;4;5>/*)}) * Multipath specifiers of mismatched lengths: sh(multi(2,xprvA1RpRA33e1JQ7ifknakTFpgNXPmW2YvmhqLQYMmrj4xJXXWYpDPS3xz7iAxn8L39njGVyuoseXzU6rcxFLJ8HFsTjSyQbLYnMpCqE2VbFWc/<1;2;3>/0/*,xprv9uPDJpEQgRQfDcW7BkF7eTya6RPxXeJCqCJGHuCJ4GiRVLzkTXBAJMu2qaMWPrS7AANYqdq6vcBcBUdJCVVFceUvJFjaPdGZ2y9WACViL4L/0/*,xprv9s21ZrQH143K3jUwNHoqQNrtzJnJmx4Yup8NkNLdVQCymYbPbJXnPhwkfTfxZfptcs3rLAPUXS39oDLgrNKQGwbGsEmJJ8BU3RzQuvShEG4/0/0/<3;4>/*)) * Empty multipath specifier: wpkh(xpub661MyMwAqRbcFW31YEwpkMuc5THy2PSt5bDMsktWQcFF8syAmRUapSCGu8ED9W6oDMSgv6Zz8idoc4a6mr8BDzTJY47LJhkJ8UB7WEGuduB/<>/*) * Missing multipath start: wpkh(xpub661MyMwAqRbcFW31YEwpkMuc5THy2PSt5bDMsktWQcFF8syAmRUapSCGu8ED9W6oDMSgv6Zz8idoc4a6mr8BDzTJY47LJhkJ8UB7WEGuduB/0>/*) * Missing multipath end: wpkh(xpub661MyMwAqRbcFW31YEwpkMuc5THy2PSt5bDMsktWQcFF8syAmRUapSCGu8ED9W6oDMSgv6Zz8idoc4a6mr8BDzTJY47LJhkJ8UB7WEGuduB/<0/*) * Missing index in multipath specifier: wpkh(xpub661MyMwAqRbcFW31YEwpkMuc5THy2PSt5bDMsktWQcFF8syAmRUapSCGu8ED9W6oDMSgv6Zz8idoc4a6mr8BDzTJY47LJhkJ8UB7WEGuduB/<0;>/*) ==Backwards Compatibility== This is an addition to the Key Expressions defined in BIP 380. Key Expressions using the format described in BIP 380 are compatible with this modification and parsers that implement this will still be able to parse such descriptors. However as this is an addition to Key Expressions, older parsers will not be able to understand such descriptors. This modification to Key Expressions uses two new characters: < and ;. These are part of the descriptor character set and so are covered by the checksum algorithm. As these are previously unused characters, old parsers will not accidentally mistake them for indicating something else. This proposal is in contrast to similar proposals such as BIP 88 which allow for multiple derivation indexes in a single element. This limitation exists in order to reduce the number of descriptors that are expanded, avoid confusion about how to expand the descriptor, and avoid having expanded descriptors that users are not expecting. ==Reference Implementation== https://github.com/bitcoin/bitcoin/pull/22838 ================================================ FILE: bip-0390.mediawiki ================================================
  BIP: 390
  Layer: Applications
  Title: musig() Descriptor Key Expression
  Authors: Ava Chow 
  Status: Draft
  Type: Informational
  Assigned: 2024-06-04
  License: CC0-1.0
  Version: 0.2.0
  Requires: 380, 328
==Abstract== This document specifies a musig() key expression for output script descriptors. musig() expressions take multiple keys and produce an aggregate public key using [[bip-0327.mediawiki|BIP-327]]. ==Copyright== This BIP is licensed under the Creative Commons CC0 1.0 Universal license. ==Motivation== [[bip-0327.mediawiki|BIP-327]] introduces the MuSig2 Multi-Signature scheme. It is useful to have a way for keys to be used in a MuSig2 aggregate key to be expressed in descriptors so that wallets can more easily use MuSig2. ==Specification== A new key expression is defined: musig(). In the following sections, the term KEY refers to key expressions as defined in [[bip-0380.mediawiki|BIP-380]] and [[bip-0389.mediawiki|BIP-389]]. ===musig(KEY, KEY, ..., KEY)=== The musig(KEY, KEY, ..., KEY) expression can only be used inside of a tr(), rawtr() or sp() expression as a key expression. It additionally cannot be nested within another musig() expression. Participant public keys may be repeated. The aggregate public key is produced by using the KeyAgg algorithm on all KEYs specified in the expression after performing all specified derivation. As with script expressions, KEY can contain child derivation specified by /*. A new aggregate public key will be computed for each child index. Keys must be sorted with the KeySort algorithm after all derivation and prior to aggregation'''Why must the keys be sorted prior to aggregation?''' Although the descriptor's written form sets an order for the keys that could be used for aggregation, the order should not matter as MuSig2 philosophically operates over a set of keys, with the order merely being an implementation detail in aggregation itself. Requiring sorting of keys prior to aggregation enforces this philosophy as keys can be written in the descriptor in any order with the end result still being the same. Furthermore, this aids with recovery where the descriptor was not backed up as users will not need to also have backed up, or guess, the correct order of keys.. ===musig(KEY, KEY, ..., KEY)/NUM/.../*=== musig(KEY, KEY, ..., KEY)/NUM/.../* expressions are also allowed if no KEY expression contains child derivation as specified by /* or multipath as specified with /, in addition to the same usage restrictions as in the previous section. The KEY expressions additionally must be xpubs or derived from xpubs. The aggregate public key is first computed as described above, with the keys also being sorted after all derivation and prior to aggregation. Then further [[bip-0032.mediawiki|BIP-32]] derivation will be performed on the aggregate public key as described in [[bip-0328.mediawiki|BIP-328]]. The /NUM/.../* following the musig() specifies the derivation path to be used when deriving from the aggregate public key. /* is also optional. As there is no aggregate private key, only unhardened derivation from the aggregate public key is allowed. Thus these derivation steps cannot contain /NUMh or /NUM' nor can child derivation be specified as /*h, or /*'. ==Test Vectors== Valid descriptors containing followed by the scripts they produce. Descriptors involving derived child keys will have the 0th, 1st, and 2nd scripts listed. * rawtr(musig(KwDiBf89QgGbjEhKnhXJuH7LrciVrZi3qYjgd9M7rFU74sHUHy8S,03dff1d77f2a671c5f36183726db2341be58feae1da2deced843240f7b502ba659,023590a94e768f8e1815c2f24b4d80a8e3149316c3518ce7b7ad338368d038ca66)) ** 5120789d937bade6673538f3e28d8368dda4d0512f94da44cf477a505716d26a1575 * tr(musig(02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9,03dff1d77f2a671c5f36183726db2341be58feae1da2deced843240f7b502ba659,023590a94e768f8e1815c2f24b4d80a8e3149316c3518ce7b7ad338368d038ca66)) ** 512079e6c3e628c9bfbce91de6b7fb28e2aec7713d377cf260ab599dcbc40e542312 * rawtr(musig(xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL,xpub68NZiKmJWnxxS6aaHmn81bvJeTESw724CRDs6HbuccFQN9Ku14VQrADWgqbhhTHBaohPX4CjNLf9fq9MYo6oDaPPLPxSb7gwQN3ih19Zm4Y)/0/*) ** 51209508c08832f3bb9d5e8baf8cb5cfa3669902e2f2da19acea63ff47b93faa9bfc ** 51205ca1102663025a83dd9b5dbc214762c5a6309af00d48167d2d6483808525a298 ** 51207dbed1b89c338df6a1ae137f133a19cae6e03d481196ee6f1a5c7d1aeb56b166 * tr(musig(xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL,xpub68NZiKmJWnxxS6aaHmn81bvJeTESw724CRDs6HbuccFQN9Ku14VQrADWgqbhhTHBaohPX4CjNLf9fq9MYo6oDaPPLPxSb7gwQN3ih19Zm4Y)/0/*,pk(f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9)) ** 51201d377b637b5c73f670f5c8a96a2c0bb0d1a682a1fca6aba91fe673501a189782 ** 51208950c83b117a6c208d5205ffefcf75b187b32512eb7f0d8577db8d9102833036 ** 5120a49a477c61df73691b77fcd563a80a15ea67bb9c75470310ce5c0f25918db60d * tr(f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9,pk(musig(xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL,xpub68NZiKmJWnxxS6aaHmn81bvJeTESw724CRDs6HbuccFQN9Ku14VQrADWgqbhhTHBaohPX4CjNLf9fq9MYo6oDaPPLPxSb7gwQN3ih19Zm4Y)/0/*)) ** 512068983d461174afc90c26f3b2821d8a9ced9534586a756763b68371a404635cc8 ** 5120368e2d864115181bdc8bb5dc8684be8d0760d5c33315570d71a21afce4afd43e ** 512097a1e6270b33ad85744677418bae5f59ea9136027223bc6e282c47c167b471d5 * tr(musig(xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL/1,xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL/1)/2) ** 5120a17ceacd6422bd5ffd9f165807b254b7d68ad39f179cc4f11545a6835227e97c Invalid descriptors * musig() is not allowed in top-level pk(): pk(musig(02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9,03dff1d77f2a671c5f36183726db2341be58feae1da2deced843240f7b502ba659,023590a94e768f8e1815c2f24b4d80a8e3149316c3518ce7b7ad338368d038ca66)) * musig() is not allowed in top-level pkh(): pkh(musig(02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9,03dff1d77f2a671c5f36183726db2341be58feae1da2deced843240f7b502ba659,023590a94e768f8e1815c2f24b4d80a8e3149316c3518ce7b7ad338368d038ca66)) * musig() is not allowed in wpkh(): wpkh(musig(02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9,03dff1d77f2a671c5f36183726db2341be58feae1da2deced843240f7b502ba659,023590a94e768f8e1815c2f24b4d80a8e3149316c3518ce7b7ad338368d038ca66)) * musig() is not allowed in combo(): combo(musig(02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9,03dff1d77f2a671c5f36183726db2341be58feae1da2deced843240f7b502ba659,023590a94e768f8e1815c2f24b4d80a8e3149316c3518ce7b7ad338368d038ca66)) * musig() is not allowed in sh(wpkh()): sh(wpkh(musig(02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9,03dff1d77f2a671c5f36183726db2341be58feae1da2deced843240f7b502ba659,023590a94e768f8e1815c2f24b4d80a8e3149316c3518ce7b7ad338368d038ca66))) * musig() is not allowed in sh(wsh()): sh(wsh(pk(musig(02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9,03dff1d77f2a671c5f36183726db2341be58feae1da2deced843240f7b502ba659,023590a94e768f8e1815c2f24b4d80a8e3149316c3518ce7b7ad338368d038ca66)))) * musig() is not allowed in wsh(): wsh(musig(02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9,03dff1d77f2a671c5f36183726db2341be58feae1da2deced843240f7b502ba659,023590a94e768f8e1815c2f24b4d80a8e3149316c3518ce7b7ad338368d038ca66)) * musig() is not allowed in sh(): sh(musig(02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9,03dff1d77f2a671c5f36183726db2341be58feae1da2deced843240f7b502ba659,023590a94e768f8e1815c2f24b4d80a8e3149316c3518ce7b7ad338368d038ca66)) * Ranged musig() requires all participants to be xpubs: tr(musig(02f9308a019258c31049344f85f89d5229b531c845836f99b08601f113bce036f9,03dff1d77f2a671c5f36183726db2341be58feae1da2deced843240f7b502ba659,023590a94e768f8e1815c2f24b4d80a8e3149316c3518ce7b7ad338368d038ca66)/0/0) * Cannot have ranged participants if musig() is also ranged: tr(musig(xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL/*,xpub68NZiKmJWnxxS6aaHmn81bvJeTESw724CRDs6HbuccFQN9Ku14VQrADWgqbhhTHBaohPX4CjNLf9fq9MYo6oDaPPLPxSb7gwQN3ih19Zm4Y)/0/*) * Cannot have multipath participants if musig() is also multipath: tr(musig(xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL/<0;1>,xpub68NZiKmJWnxxS6aaHmn81bvJeTESw724CRDs6HbuccFQN9Ku14VQrADWgqbhhTHBaohPX4CjNLf9fq9MYo6oDaPPLPxSb7gwQN3ih19Zm4Y)/<2;3>) * musig() cannot have hardened derivation steps: tr(musig(xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL,xpub68NZiKmJWnxxS6aaHmn81bvJeTESw724CRDs6HbuccFQN9Ku14VQrADWgqbhhTHBaohPX4CjNLf9fq9MYo6oDaPPLPxSb7gwQN3ih19Zm4Y)/0h/*) * musig() cannot have hardened child derivation: tr(musig(xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL,xpub68NZiKmJWnxxS6aaHmn81bvJeTESw724CRDs6HbuccFQN9Ku14VQrADWgqbhhTHBaohPX4CjNLf9fq9MYo6oDaPPLPxSb7gwQN3ih19Zm4Y)/0/*h) * musig() cannot have participants with child derivation when musig() has derivation steps: tr(musig(xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL/*,xpub68NZiKmJWnxxS6aaHmn81bvJeTESw724CRDs6HbuccFQN9Ku14VQrADWgqbhhTHBaohPX4CjNLf9fq9MYo6oDaPPLPxSb7gwQN3ih19Zm4Y/*)/1/2 ==Backwards Compatibility== musig() expressions use the format and general operation specified in [[bip-0380.mediawiki|BIP-380]]. As these are a set of wholly new expressions, they are not compatible with any implementation. However the keys are produced using a standard process so existing software are likely to be familiar with them. ==Rationale== ==Reference Implementation== The reference implementation is available in Bitcoin Core [[https://github.com/bitcoin/bitcoin/pull/31244|PR #31244]]. ==Changelog== * __0.2.0__ (2026-03-04) - Allow musig() inside sp() expressions. * __0.1.0__ (2025-12-08) - Allow musig() inside rawtr() expressions. ==Acknowledgements== Thanks to Pieter Wuille, Andrew Poelstra, Sanket Kanjalkar, Salvatore Ingala, and all others who participated in discussions on this topic. ================================================ FILE: bip-0392.mediawiki ================================================
  BIP: 392
  Layer: Applications
  Title: Silent Payment Output Script Descriptors
  Authors: Craig Raw 
  Status: Draft
  Type: Specification
  Assigned: 2026-02-06
  License: BSD-2-Clause
  Discussion: https://groups.google.com/g/bitcoindev/c/bP6ktUyCOJI
  Requires: 341, 350, 352, 380
==Abstract== This document specifies sp() output script descriptors for silent payments. sp() descriptors take silent payment key material and describe P2TR outputs when combined with sender input public keys as defined in BIP352. ==Copyright== This BIP is licensed under the BSD 2-clause license. ==Motivation== BIP352 defines silent payments, a protocol for static payment addresses without on-chain linkability. This descriptor provides a standardized way to represent silent payment outputs within the output descriptor framework, enabling wallet interoperability and backup/recovery using existing descriptor-based infrastructure. ==Specification== A new top level script expression is defined: sp(). ===Key Expressions=== Two new key expression types are defined for use with sp() descriptors: ====spscan==== The spscan key expression encodes the scan private key and spend public key. It is a [https://github.com/bitcoin/bips/blob/master/bip-0350.mediawiki Bech32m] encoding of: * The human-readable part "spscan" for mainnet, "tspscan" for testnets * The data-part values: ** The character "q", to represent silent payments version 0 ** The payload: ser256(bscan) || serP(Bspend) ====spspend==== The spspend key expression encodes both the scan and spend private keys. It is a [https://github.com/bitcoin/bips/blob/master/bip-0350.mediawiki Bech32m] encoding of: * The human-readable part "spspend" for mainnet, "tspspend" for testnets * The data-part values: ** The character "q", to represent silent payments version 0 ** The payload: ser256(bscan) || ser256(bspend) Note: The serialization of ser256(p) and serP(P) follows the definition in BIP352. ===sp()=== The sp(KEY) or sp(KEY,KEY) expression can only be used as a top level descriptor. sp(KEY) takes a single key expression as an argument, which must be either an spscan or spspend encoded key, optionally with key origin information. If included, the key origin information specifies the fingerprint and derivation path to the depth from which the scan and spend keys are derived using the child paths recommended in BIP352 (1h/0 for scan, 0h/0 for spend). sp(KEY,KEY) takes two key expressions. The first key expression represents the scan key and must be a single private key (e.g. a WIF compressed private key or xprv extended private key). The second key expression represents the spend key and may be any key expression as defined in BIP380 or other key expression BIPs (e.g. musig() as defined in BIP390) that represents a single key, public or private. Note however that uncompressed keys are not allowed under any sp() expression, as BIP352 only permits compressed public keys. When combined with sender input public keys, the descriptor produces P2TR output scripts describing silent payments made to wallets represented by the key expression(s). The output scripts produced are BIP341 taproot outputs as specified in BIP352. ==Examples== Valid descriptors: * sp(spscan1q...) - Using spscan encoded key (watch-only) * sp([deadbeef/352h/0h/0h]spscan1q...) - With key origin * sp(spspend1q...) - Using spspend encoded key (full wallet) * sp(L4rK1yDtCWekvXuE6oXD9jCYfFNV2cWRpVuPLBcCU2z8TrisoyY1,0260b2003c386519fc9eadf2b5cf124dd8eea4c4e68d5e154050a9346ea98ce600) - WIF scan key with compressed public spend key (watch-only) * sp([deadbeef/352h/0h/0h]xprv.../0h,xpub.../0h) - Extended private scan key with extended public spend key (watch-only) * sp([deadbeef/352h/0h/0h]xprv.../0h,xprv.../0h) - Extended private keys for both scan and spend (full wallet) * sp(L4rK1yDtCWekvXuE6oXD9jCYfFNV2cWRpVuPLBcCU2z8TrisoyY1,musig(03dff1d77f2a671c5f36183726db2341be58feae1da2deced843240f7b502ba659,023590a94e768f8e1815c2f24b4d80a8e3149316c3518ce7b7ad338368d038ca66)) - WIF scan key with MuSig2 aggregate spend key (watch-only) Invalid descriptors: * sp() requires at least one key expression * sp(xpub...) single argument form requires spscan or spspend encoded key * sp(xpub...,xpub...) two argument form requires private scan key (e.g. WIF or xprv) * sp(spscan1q...,spscan1q...) two argument form requires single key expressions * sp(5KYZdUEo39z3FPrtuX2QbbwGnNP5zTd7yyr2SC1j299sBCnWjss,0260b2003c386519fc9eadf2b5cf124dd8eea4c4e68d5e154050a9346ea98ce600) uncompressed private key * sh(sp(spscan1q...)) sp() is top level only * wsh(sp(spscan1q...)) sp() is top level only ==Usage Notes== For watch-only wallets, use spscan encoding or the two argument form with a public spend key. For full wallets that can both scan and spend, use spspend encoding or the two argument form with a private spend key. When using the two argument form, the scan key must be private (e.g. WIF or xprv) since scanning requires the private scan key. ==Backwards Compatibility== sp() descriptors use the format and general operation specified in BIP380. As this is a wholly new descriptor, it is not compatible with any prior implementation. The scripts produced are BIP341 taproot outputs, making them indistinguishable from other taproot outputs on-chain. ==Reference Implementation== TBD ==Test Vectors== TBD ================================================ FILE: bip-0431.mediawiki ================================================
  BIP: 431
  Layer: Applications
  Title: Topology Restrictions for Pinning
  Authors: Gloria Zhao 
  Status: Draft
  Type: Informational
  Assigned: 2024-01-10
  License: BSD-3-Clause
  Discussion: 2022-01-27: https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2022-January/019817.html [bitcoin-dev] discussion
              2022-01-27: https://gist.github.com/glozow/25d9662c52453bd08b4b4b1d3783b9ff gist discussion
              2022-09-23: https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2022-September/020937.html [bitcoin-dev] proposal
              2024-01-02: https://delvingbitcoin.org/t/v3-transaction-policy-for-anti-pinning/340 Delving Bitcoin post
              2024-01-16: https://delvingbitcoin.org/t/lightning-transactions-with-v3-and-ephemeral-anchors/418 Delving Bitcoin post
==Abstract== This document describes pinning problems that can arise from limitations in mempool policy. It also describes a type of policy with adjusted topology limits which, combined with other policy rules, helps minimize the potential pinning problems. These restrictions simplify the assessment of incentive compatibility of accepting or replacing such transactions, thus helping ensure any replacements are more profitable for the node. Within the context of nodes that implement this policy, fee-bumping is more reliable for users. ==Motivation== Mempools typically accept and relay transactions that spend outputs from other unconfirmed transactions, but restrict package sizes through ancestor and descendant limits https://github.com/bitcoin/bitcoin/blob/632a2bb731804dffe52bd4cbd90bfee352d25ede/doc/policy/mempool-limits.md to limit the computational complexity of mempool operations and mitigate Denial of Service attacks. Users may also create unconfirmed transactions that conflict with -- or are "double spends" of -- each other by spending the same input(s) in both. Instead of always keeping the first-seen transaction, many mempools also have some kind of Replace by Fee (RBF) policy [https://github.com/bitcoin/bitcoin/blob/632a2bb731804dffe52bd4cbd90bfee352d25ede/doc/policy/mempool-replacements.md Bitcoin Core's RBF policy] at the time of writing. It is slightly different from what is described in BIP 125. to keep the more incentive compatible transaction, i.e. one that would earn a miner more fees. Users utilize these rules when they create higher feerate double-spends (replacements) to expedite confirmation of their transactions. However, these policies make imperfect trade-offs between incentive compatibility and DoS-resistance. For example, malicious actors may sometimes exploit limitations to prevent incentive-compatible transactions from being accepted or fee-bumped (''pinning''). Pinning is consequential to contracting protocols in which untrusted parties construct and sign time-sensitive transactions to be broadcast on-chain later Posts about pinning in LN and LN-Symmetry: * [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2022-May/020458.html "Bringing a nuke to a knife fight: Transaction introspection to stop RBF pinning"] * [https://lists.linuxfoundation.org/pipermail/lightning-dev/2020-April/002639.html "RBF Pinning with Counterparties and Competing Interest"] * [https://lists.linuxfoundation.org/pipermail/lightning-dev/2020-June/002758.html "Pinning : The Good, The Bad, The Ugly"] * [https://github.com/t-bast/lightning-docs/blob/master/pinning-attacks.md "Pinning Attacks"] * [https://gist.github.com/instagibbs/60264606e181451e977e439a49f69fe1 "Eltoo Pinning"] . When the funds available to be redeemed by each party depend on a transaction confirming within a specific time window, a malicious party may be able to steal money if the honest party cannot get their transaction confirmed. As such, the ability to fee-bump a transaction to entice miners to include it in their blocks is crucial to the security of the protocol. ===RBF pinning through absolute fees=== Imagine that counterparties Alice and Mallory have transactions (or packages) A and B, respectively, which conflict with each other. Alice broadcasts A and Mallory broadcasts B. RBF rules require the replacement transaction pay a higher absolute fee than the aggregate fees paid by all original transactions ([https://github.com/bitcoin/bitcoin/blob/master/doc/policy/mempool-replacements.md#current-replace-by-fee-policy "Rule 3"]). This means Mallory may increase the fees required to replace B beyond what Alice was planning to pay for A's fees. 1. Adding transaction(s) that descend from B and pay a low feerate (too low to fee-bump B through CPFP)Example: https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2023-December/022216.html. 2. Adding a high-fee descendant of B that also spends from another large, low-feerate mempool transaction (where the fee of the descendant is too low to fee-bump both B and its other parent through CPFP)Example: https://github.com/bitcoin/bitcoin/pull/25038#issuecomment-1320295394. ===RBF pinning through number of conflicts=== RBF rules require that no replacement trigger the removal of more than 100 transactions ([https://github.com/bitcoin/bitcoin/blob/master/doc/policy/mempool-replacements.md#current-replace-by-fee-policy "Rule 5"]). This number includes the descendants of the conflicted mempool transactions. Mallory can make it more difficult to replace transactions by attaching lots of descendants to them. For example, if Alice wants to batch-replace 5 transactions but each has 21 descendants, her replacement will be rejected regardless of its fees. ===RBF incentive compatibility requirements=== There is currently no effective rule to enforce that a replacement transaction would be more incentive compatible to keep in the mempool. It is difficult to quantify the incentive compatibility of a set of transactions, especially in comparison with another set of transactionshttps://delvingbitcoin.org/t/mempool-incentive-compatibility/553, but the requirement of a feerate increase ([https://github.com/bitcoin/bitcoin/blob/master/doc/policy/mempool-replacements.md#current-replace-by-fee-policy "Rule 6"]) is far too simplistic. For example, a user could create a replacement transaction that pays more fees and is higher feerate, but has a low feerate ancestor and would confirm slower than the original transaction. As a result, all transactions signed with SIGHASH_ANYONECANPAY are vulnerable to being replaced by a transaction that will confirm later than the originalhttps://github.com/bitcoin/bitcoin/pull/23121#pullrequestreview-766271585. ===Child fees don't count towards RBF rules=== A transaction must meet all fee-related requirements (Rules 3, 4, 6) alone; its child's fees cannot be used. A ''Package RBF'' policy would allow a transaction's child to be used for its RBF requirements. In LN Penalty, conflicting commitment transactions signed with the same fees cannot replace each other, even if accompanied by a fee-bumping child. This limitation necessitates the presence of two anchor outputs, allowing both parties to fee-bump either commitment transaction that enters their mempool. ===Package limit pinning and replacing CPFP Carve Out=== Mempool policies limit the number and total virtual size of an unconfirmed transaction's descendants. A fee-bumping child of an unconfirmed transaction (CPFP) may be rejected for exceeding the descendant limit. When a transaction has multiple outputs owned by different parties, a malicious party can prevent the other(s) from CPFPing their transaction by attaching enough descendants to monopolize the descendant limit (''package limit pinning''). LN commitment transactions rely on CPFP carve out [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2018-November/016518.html "CPFP Carve-Out for Fee-Prediction Issues in Contracting Applications (eg Lightning)"] to avoid package limit pinning. There are weaknesses with this approach of using 2 anchors and CPFP Carve Out. This proposal helps address a few of them (see Related Work for how other weaknesses are addressed): * Cluster Mempool necessitates the removal of CPFP Carve Out https://delvingbitcoin.org/t/an-overview-of-the-cluster-mempool-proposal/393#the-cpfp-carveout-rule-can-no-longer-be-supported-12. * CPFP Carve Out only allows ''one more'' child to be added to the transaction. This means it cannot guarantee the ability to CPFP for more than 2 parties of a shared transaction. ==Topologically Restricted Until Confirmation== This section describes one approach for opt-in policy rules that can realistically be deployed today and is useful to today's applications. It is based on the idea that most limitations stem from existing ancestor/descendant package limits being too permissive for the majority of use cases. The scope of the policy's anti-pinning benefits is limited to the individual node's mempool, and the degree to which a user's transaction is safe from pinning depends how much of the network has adopted this policy. Similarly, there are multiple approaches to creating a policy to minimize pinning, more may become available over time (see Related Work section), and the details of this approach can be tweaked if conditions change. For example, if loosening one of the topology restrictions enables a new use case while still providing acceptable pinning bounds, it can be changed. ===Specification=== Senders can signal that they want a transaction to be Topologically Restricted Until Confirmation (TRUC). Specifically, set nVersion=3. A node that implements this policy would apply their existing standardness and policy rules, along with the following set of rules, to TRUC transactions: 1. A TRUC transaction signals replaceability, even if it does not signal BIP125 replaceability. 2. Any TRUC transaction's unconfirmed ancestors must all be TRUC. Any descendant of an unconfirmed TRUC transaction must also be TRUC. Rationale: * Requiring packages to be all-or-none TRUC makes it possible to enforce the topology limits. For example, the TRUC descendant limit would not be very meaningful if it could be bypassed by creating a non-TRUC child. * Combined with Rule 1, this requirement creates "inherited signaling" when descendants of unconfirmed transactions are created. Checking whether a transaction signals replaceability this way does not require mempool traversal, and does not change based on what transactions are mined. Note: A TRUC transaction can spend outputs from ''confirmed'' non-TRUC transactions. A non-TRUC transaction can spend outputs from ''confirmed'' TRUC transactions. 3. An unconfirmed TRUC transaction cannot have more than 1 unconfirmed ancestor. An unconfirmed TRUC transaction cannot have more than 1 unconfirmed descendant. CPFP Carve Out is not granted to TRUC transactions. Rationale: * The larger the descendant limit, the more transactions may need to be replaced. See #1 in Rule 3 Pinning section above. This also makes pinning using Rule 5 more difficult, since a directly conflicting transaction has fewer possible descendants. * These two limits (ancestor count 2, descendant count 2) effectively create a cluster limit using the existing ancestor and descendant limits. Increasing them to 3 would imply an infinite cluster count limit. * This 1-parent-1-child topology makes it possible to use ancestor score (minimum of ancestor feerate and individual feerate) as a measure of incentive compatibility.
Q: Why not allow multiple parents to enable batched fee-bumping?
To mitigate pinning through absolute fees, we need to prevent a child of an unconfirmed TRUC transaction from bringing in more unconfirmed ancestors. See #2 in "RBF pinning through absolute fees" section above.
Q: Why not allow another child?
Allowing another child disables the ability to use ancestor score to measure incentive compatibility. Imagine the original transaction, A, has a child B and co-parent C (i.e. B spends from A and C). C also has another child, D. B is one of the original transactions and thus its ancestor feerate must be lower than the package's feerate. However, this may be an underestimation because D can bump C without B's help. This is resolved if TRUC transactions can only have TRUC ancestors, as then C cannot have another child.
Q: Why allow any descendants at all?
At least 1 descendant is required to allow CPFP of the presigned transaction. Without package RBF, multiple anchor outputs would be required to allow each counterparty to fee-bump any presigned transaction. With package RBF, since the presigned transactions can replace each other, 1 anchor output is sufficient.
4. A TRUC transaction cannot have a sigop-adjusted virtual size larger than 10,000 vB. Rationale: Limit the amount of virtual bytes (and thus fees) that may need to be replaced, while leaving a comfortable amount of space for payments, HTLCs, or other uses of the transaction. Generally, having a smaller maximum size helps to better define bounds for algorithms and memory usage, and the existing limit of 100,000 vB seems much larger than necessary. 5. A TRUC transaction that has an unconfirmed TRUC ancestor cannot have a sigop-adjusted virtual size larger than 1000 vB. Rationale: Limit the amount of virtual bytes (and thus fees) that may need to be replaced, while leaving a comfortable amount of space for inputs to fund the transaction.
Q: Why not bigger?
The larger the descendant size limit, the more vbytes may need to be replaced. With default limits, if the child is e.g. 100,000 vB, that might be an additional 100,000 sats (at 1 sat/vbyte) or more, depending on the feerate. Restricting all children to 1000 vB reduces the upper bound of the additional fees by a factor of 100.
This rule is also easily tacked on to existing logic for policy and wallets. A maximum size standard transaction (100 kvB) can have up to 1000 vB of descendants to be within the default descendant limit (101 kvB).
Q: Why not smaller?
The smaller this limit, the fewer UTXOs a child may use to fund this fee-bump. For example, only allowing the TRUC child to have 2 inputs would require wallets to maintain a pool of high-value confirmed UTXOs. However, as the fee-bumping child only needs to fund fees (as opposed to payments), just a few UTXOs should suffice. With a limit of 1000 vB and usage of taproot outputs, the child can have 15 inputs and 2 outputs (calculated using [https://bitcoinops.org/en/tools/calc-size/ this tool]).
6. An individual TRUC transaction is permitted to be below the mempool min relay feerate, assuming it is considered within a package that meets the mempool's feerate requirements. Rationale: This allows contracting protocols to create presigned transactions with 0 fees and fee-bump them using CPFP at broadcast time. ====Implementation==== * https://github.com/bitcoin/bitcoin/pull/28948 * https://github.com/bitcoin/bitcoin/pull/29873 * https://github.com/bitcoin/bitcoin/pull/29496 ====Related Work==== This 1-parent-1-child (aka cluster size 2) topology restriction makes the transactions much easier to reason about, which enables additional features like feerate diagram comparisons [https://github.com/bitcoin/bitcoin/pull/29242 this PR] implements feerate diagram creation and comparison for sets of transactions in which the maximum cluster size is 2, e.g. all TRUC transactions. , package RBF [https://github.com/bitcoin/bitcoin/pull/28984 this PR] implements package RBF, enforcing incentive compatibility by comparing the feerate diagrams of the mempool before and after replacement. The feerate diagrams are easy to build when the relevant clusters are of size 2 and below, so package RBF is restricted to those scenarios. As TRUC transactions always have this property, package RBF is enabled for TRUC transactions. , and sibling eviction [https://github.com/bitcoin/bitcoin/pull/29306 This PR] implements sibling eviction for TRUC transactions: if a new transaction would exceed a transaction's descendant limit, it considers evicting the existing descendant using replacement rules. Sibling eviction is feasible for TRUC transactions because there is no difficulty in identifying which descendant to evict (there can only be 1). . The [https://github.com/bitcoin/bips/pull/1524 Ephemeral Anchors] proposal builds on top of this one to add more features. It changes the anchor script to be anyone can spend, allowing anybody to add fees and reducing the onchain footprint and fee costs. It also allows anchor outputs to have 0 value, eliminating the need to deduct value from the input amount in order to create anchors. The [https://delvingbitcoin.org/t/an-overview-of-the-cluster-mempool-proposal/393/7 Cluster Mempool] proposal makes fundamental changes to mempool structure and policy rules, enabling the accurate assessment of the incentive compatibility of accepting or removing a transaction, among other things. Notably, Cluster Mempool introduces a limit to all transactions' cluster size to make incentive compatibility calculations feasible. This cluster limit is similar to TRUC limits in that it bounds computation to enable improved policies, but is applied to all transactions (not just ones that opt in) and is much less restrictive than TRUC limits. Cluster Mempool provides a more holistic solution to some of the problems listed (such as adding an incentive compatibility requirement to RBF and safely enabling package RBF for more complex topologies). However, it does not help resolve all problems (such as RBF Pinning through absolute fees and number of conflicts). Also, since Cluster Mempool is incompatible with CPFP Carve Outhttps://delvingbitcoin.org/t/an-overview-of-the-cluster-mempool-proposal/393#the-cpfp-carveout-rule-can-no-longer-be-supported-12, TRUC with sibling eviction and package RBF provide an alternative solution to applications that rely on it. Building on top of Cluster Mempool, there are also various ideas for extending TRUC transactions and creating another anti-pinning policy https://delvingbitcoin.org/t/v3-and-some-possible-futures/523/3. [https://bitcoinops.org/en/topics/package-relay Package Relay] includes changes in p2p protocol, transaction relay logic, and mempool policy to enable nodes to accept and relay packages of transactions. Much of this proposal's utility relies on the existence of package relay for 1-parent-1-child packages (the topology TRUC supports). ====Backward Compatibility==== Transactions with nVersion=3 were previously nonstandard. There are no known conflicts with previous usage. ====Intended Usage==== Generally, users with no interest in spending unconfirmed outputs from a transaction can make them TRUC transactions for more robust RBF abilities. This proposal allows for a different solution to fee-bumping in LN, in which commitment transactions are signed with 0 fees and include a single anchor that can later be used to add fees at broadcast time Proposals for changes to LN commitment transaction format using TRUC and a single anchor: * [https://delvingbitcoin.org/t/lightning-transactions-with-v3-and-ephemeral-anchors/418 "Lightning transactions with v3 and ephemeral anchors"] * [https://github.com/instagibbs/bolts/commits/zero_fee_commitment bolts proposal branch] * See "Intended usage for LN" section in [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2022-September/020937.html "New transaction policies (nVersion=3) for contracting protocols"] . A similar fee-bumping model can also be used in other contracting protocols Examples of non-LN protocols that have shown interest in, designed, or built fee-bumping using TRUC: * A LN-Symmetry implementation using TRUC and ephemeral anchors: [https://delvingbitcoin.org/t/ln-symmetry-project-recap/359 LN-Symmetry Project Recap] [https://github.com/instagibbs/lightning/tree/eltoo_support branch] * See "Managing Fees Safely" mentioning ephemeral anchors in [https://jameso.be/vaults.pdf "Vaults and Covenants"] . ==Alternatives== Various alternatives for RBF Proposals and discussions dedicated to improving RBF: * [https://gist.github.com/glozow/25d9662c52453bd08b4b4b1d3783b9ff "RBF Improvements"] * [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2022-January/019817.html "Improving RBF Policy"] * [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2019-June/016998.html "[PROPOSAL] Emergency RBF (BIP 125)"] and new fee-bumping mechanisms
Proposals and discussions dedicated to improving or creating new fee-bumping mechanisms: * [https://github.com/lightning/bolts/pull/1036 "Add option to sign commitments at various feerates"] * [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2021-July/019243.html "A Stroll through Fee-Bumping Techniques : Input-Based vs Child-Pay-For-Parent"] * [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2020-September/018168.html "A Replacement for RBF and CPFP: Non-Destructive TXID Dependencies for Fee Sponsoring"] * [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2022-February/019879.html "Thoughts on fee bumping"]
have been proposed across multiple discussion threads. Most alternatives do not conflict with TRUC, and some work in conjunction with this proposal - see Related Work. A few popular ideas that were not incorporated into this work are summarized here. ===Alternatives: add static incentive compatibility rule in RBF policy=== Add incentive compatibility requirement to RBF policy using some existing score or static calculation Examples of incentive compatibility score proposals and suggestions: * [https://github.com/bitcoin/bitcoin/pull/23121 "check ancestor feerate in RBF, remove BIP125 Rule2"] * [https://github.com/bitcoin/bitcoin/pull/26451 "Enforce incentive compatibility for all RBF replacements"] * https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2022-January/019841.html * https://gist.github.com/glozow/25d9662c52453bd08b4b4b1d3783b9ff?permalink_comment_id=4081349#gistcomment-4081349 . As the incentive compatibility "score" of a transaction must be dynamically calculated given the structure of mempools today, there is no satisfactory solution. A full calculation is too computationally expensive. Static values can overestimate or underestimate, leading to more pinning problems Four examples of static calculations and an example in which they are all inaccurate: https://gist.github.com/glozow/25d9662c52453bd08b4b4b1d3783b9ff#mining-score-of-a-mempool-transaction. The ability to calculate incentive compatibility scores efficiently is a primary feature and motivation for both TRUC transactions and Cluster Mempool. ===Alternatives: replace by feerate=== "Instead of using Rule 3 and/or 4 (requiring an increase in absolute fees), allow replacements with a higher feerate." One variation of this proposal is to apply this rule in certain exceptional scenarios or when the replacement would confirm "soon" Examples of Replace by Feerate proposals and suggestions: * [https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2019-June/016998.html "[PROPOSAL] Emergency RBF (BIP 125)"] * [https://gist.github.com/glozow/25d9662c52453bd08b4b4b1d3783b9ff#fees-in-next-block-and-feerate-for-the-rest-of-the-mempool] * [https://petertodd.org/2024/one-shot-replace-by-fee-rate "One-Shot Replace-by-Fee-Rate"] . The primary problem with these proposals is the potential for free relay and DDoS attacks. Removing Rule 3 and 4 in general would allow free relay Examples of free relay with the removal of Rule 3 and/or 4:
Consider a rule where the fee can be decreased (remove Rule 3 and 4) but the feerate must double. In this scenario, a 100 kvB transaction can be replaced by a 100 vB transaction paying 200 sats. That's 200 sats to relay 100,200 vB of transaction data, which is less than 0.002 sat/vB. It becomes quite cheap to replace large portions of the mempool, decreasing both its average feerate and total absolute fees.
Consider a rule where the fee can stay the same (keep Rule 3 but drop Rule 4) but the feerate must double. The attacker can start out with 100 kvB transaction, paying 1 sat/vB. A user can reduce its size over and over again, doubling the feerate each time until it gets too small, and end up paying 100 ksat for 100 kvB(1 + 1/2 + 1/4 + ... + log2(mintxsize)) -> approaches 200 kvB. This means the attacker pays a rate of 0.5 sat/vB to relay transactions, which is below our "free relay" threshold of 1 sat/vB.
. Another issue is the complexity of defining and implementing a "would confirm soon" or "is in the top N portion of the mempool." These proposals require an efficient way to assess the incentive compatibility score of a transaction and where it ranks amongst the other mempool transactions. This isn't feasible without something like cluster mempool (also see the "add static incentive compatibility rule in RBF policy" section above) Concerns about Replace by Feerate proposals * https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2019-June/017020.html * https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2019-June/017002.html * https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2022-February/019879.html * https://gist.github.com/glozow/25d9662c52453bd08b4b4b1d3783b9ff?permalink_comment_id=4044451#gistcomment-4044451 . ===Alternatives: implement rate-limiting without fee rules=== "Since Rule 3 and 4 (requiring an increase in absolute fees) are for rate-limiting, replace them with a mempool-wide or per-peer rate limits on replacements by outpoint and/or bandwidth Examples of general rate-limiting proposals and suggestions: * https://gist.github.com/glozow/25d9662c52453bd08b4b4b1d3783b9ff?permalink_comment_id=4081349#gistcomment-4081349 * https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2022-January/019820.html * https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2019-June/017024.html
Related proposal for changing the amount of bandwidth that replacement transactions use: * https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2022-January/019820.html
." A problem with any global rate limit is that, in the absence of reputation or identities, the limit could be exhausted by an attacker, thus restricting replacements for honest users. For example, an outpoint-based rate limit could be exhausted by one dishonest participant of a shared transaction, preventing the other participants from making any replacements. There are also other concerns about implementation complexity, free relay issues, and other unresolved edge cases Concerns * https://gist.github.com/glozow/25d9662c52453bd08b4b4b1d3783b9ff?permalink_comment_id=4081559#gistcomment-4081559 * https://lists.linuxfoundation.org/pipermail/bitcoin-dev/2022-February/019921.html * https://docs.google.com/document/d/1LpYF17HdbXPGHKSl3WYdxG4XTJBNJKSn-c2UJ2yphhE/edit?usp=sharing . ==Acknowledgements== Thank you to everyone who contributed to this proposal and document, including Jon Atack, Matt Corallo, Suhas Daftuar, Mark Erhardt, Antoine Poinsot, Antoine Riard, Gregory Sanders, and Bastien Teinturier. ==References and Rationale== ================================================ FILE: bip-0433.mediawiki ================================================
  BIP: 433
  Layer: Applications
  Title: Pay to Anchor (P2A)
  Authors: Gregory Sanders 
  Status: Draft
  Type: Informational
  Assigned: 2025-12-08
  License: BSD-3-Clause
  Discussion: 2024-06-27: https://github.com/bitcoin/bitcoin/pull/30352 Github PR
              2024-10-10: https://bitcoinops.org/en/bitcoin-core-28-wallet-integration-guide/ wallet integration guide
==Abstract== This document describes a new standard output script called Pay to Anchor (P2A) and prescribes making spending of this output type standard. This output is "keyless" meaning no signature or witness data at all are required to spend this output typea. ==Motivation== The "anchor" output type is a commonly used pattern in Bitcoin layer 2 systems such as Lightning Network and beyond. This pattern allows transactions which are presigned far in advance to leave a "hook" for CPFP fee bumping later, when prevailing feerates for block inclusion are better known. When the wallet user is unconcerned by *who* is able to bump the transaction fees as long as someone does, this output type may confer a couple of advantages: 1. Using an output type with minimal output and spending input footprint saves fees 2. Keyless operation aids in interoperability of services like watchtowers as there is no privileged key material required for bumping with the drawback that selection of this output type could result in griefing if anti-pinning measures are not taken. If unsure, use in conjunction with [https://github.com/bitcoin/bips/blob/master/bip-0431.mediawiki TRUC transactions]. ===Specification=== A P2A output is defined as one with the scriptPubKey OP_1 <0x4e73>Native segwit outputs are composed of a witness version and a witness program. A witness program must be at least two bytes long and the specific bytes cannot be zeros. The two bytes for the P2A witness program are chosen to spell "fees" in bech32m encoding. corresponding to the addresses bc1pfeessrawgf on Bitcoin mainnet, on public testnets, and bcrt1pfeesnyr2tx on regtest. P2A inputs are considered standard by Bitcoin Core for spending if no witness data is attached. This avoids meaningless witness padding. Consensus meaning is unchanged. ====Implementation==== * https://github.com/bitcoin/bitcoin/pull/30352 ====Related Work==== There are a number of related but separate historical concepts: [https://github.com/bitcoin/bitcoin/pull/30239 Ephemeral Dust]: Relay policies allowing a single dust output as long as it is spent in a transaction package. As an implementation detail, dust threshold for P2A is set at 240 satoshis by default, other dust levels remain unchanged, and the dust-having transaction must be zero fee. Any output script type may have down to 0-value outputs. [https://bitcoinops.org/en/topics/ephemeral-anchors/ Ephemeral Anchors]: Historically the union of P2A output type and ephemeral dust. Keyed anchors along with ephemeral dust are also an accepted pattern and as such they remain separate concepts. [https://github.com/bitcoin/bips/blob/master/bip-0431.mediawiki TRUC transactions]: TRUC transactions bound the topology including child transaction size, which aids in anti-pinning for the P2A output, as anyone can attach a child transaction including an oversized, low feerate one. There is no ineherent dependency on this concept and P2A. ====Backward Compatibility==== Creation of P2A outputs has been considered standard since the deployment of Segwit softfork on the network. Transactions with P2A inputs were previously nonstandard, reserved as an upgrade hook. There are no known conflicts with previous usage. ==Acknowledgements== Thanks to collaborators who helped focus the historical ideas into deployed ones: Suhas Daftuar, Gloria Zhao, Pieter Wuille, Jeremy Rubin, and Bastien Teinturier. ==References and Rationale== ================================================ FILE: bip-0434.md ================================================ ``` BIP: 434 Layer: Peer Services Title: Peer Feature Negotiation Authors: Anthony Towns Status: Draft Type: Specification Assigned: 2026-01-14 License: BSD-2-Clause Discussion: 2025-12-19: https://gnusha.org/pi/bitcoindev/aUUXLgEUCgGb122o@erisian.com.au/T/#u 2020-08-21: https://gnusha.org/pi/bitcoindev/20200821023647.7eat4goqqrtaqnna@erisian.com.au/ Version: 0.1.0 ``` ## Abstract This BIP defines a peer-to-peer (P2P) message that can be used for announcements and negotiation related to support of new peer-to-peer features. ## Motivation Historically, new peer-to-peer protocol changes have been tied to bumping the protocol version, so that nodes know to only attempt feature negotiation with peers that support the feature. Coordinating the protocol version across implementations, when different clients may have different priorities for features to implement, is an unnecessary burden in the upgrade process for P2P features that do not require universal support. And at a more philosophical level, having the P2P protocol be [permissionlessly extensible][permless-extensible], with no coordination required between implementations or developers, seems ideal for a decentralized system. Many earlier P2P protocol upgrades were implemented as new messages sent after a peer connection is set up (ie, after receipt of a `verack` message by both sides). See [BIP 130 (sendheaders)][BIP130], [BIP 133 (feefilter)][BIP133], and [BIP 152 (compact blocks)][BIP152] for some examples. However, for some P2P upgrades, it is helpful to perform feature negotiation prior to a connection being fully established (ie, prior to the `verack` being received by both sides). [BIP 155 (addrv2)][BIP155] and [BIP 339 (wtxid-relay)][BIP339] are examples of this approach, which involves sending and receiving a single new message (`sendaddrv2` and `wtxidrelay` respectively), in between `version` and `verack` to indicate support of the new feature. In all these cases, sending new messages on the network raises the question of what non-implementing software will do with such messages. The common behavior observed on the network was for software to ignore unknown messages received from a peer, so these proposals posed minimal risk of potential network partitioning. In fact, supporting protocol extensibility in this manner was given as an explicit reason to ignore unknown messages in Bitcoin's [first release][0.1-extensibility]. However, if nodes respond to unknown messages by disconnecting, then the network might partition in the future as incompatible software is deployed. And in fact, some clients on the network have historically discouraged or disallowed unknown messages, both between `version` and `verack` (eg, Bitcoin Core discouraged such messages between [PR#9720][PR#9720] and [PR#19723][PR#19723], and btcd disallowed such messages until [PR#1812][btcd#1812], but see also discussion in [#1661][btcd#1661]), as well as after `verack`. To maximise compatibility with such clients, most of these BIPs require that peers bump the protocol version: * [BIP 130][BIP130] requires version 70012 or higher, * [BIP 133][BIP133] requires version 70013 or higher, * [BIP 152][BIP152] recommends version 70014/70015 or higher, and * [BIP 339][BIP339] requires version 70016 or higher. And while [BIP 155][BIP155] does not specify a minimum protocol version, implementations have [added][PR#20564] a de facto requirement of version 70016 or higher. In this BIP, we propose codifying and generalising the mechanism used by [BIP 339][BIP339] for future P2P upgrades, by adding a single new feature negotiation message that can be reused for advertising arbitrary new features, and requiring that implementing software ignore unknown features that might be advertised. This allows future upgrades to negotiate new features by exchanging messages prior to exchanging `verack` messages, without concerns of being unnecessarily disconnected by a peer which doesn't understand the messages, and without needing to coordinate updating the protocol version. ## Specification The key words "MUST", "MUST NOT", "REQUIRED", "SHOULD", "SHOULD NOT", "RECOMMENDED", "MAY", and "OPTIONAL" in this document are to be interpreted as described in RFC 2119. For the purposes of this section, `CompactSize` refers to the variable-length integer encoding used across the existing P2P protocol to encode array lengths, among other things, in 1, 3, 5 or 9 bytes. Only `CompactSize` encodings which are minimally-encoded (ie the shortest length possible) are used by this specification. Nodes implementing this BIP: * MUST advertise a protocol version number `>= 70017`, * MUST NOT send `feature` messages to peers that advertise a protocol version number `< 70017`, * MUST accept `feature` messages received after the `version` message and before the `verack` message, and * MUST NOT send `feature` messages after sending the `verack` message. In addition, nodes implementing this BIP: * SHOULD ignore unknown messages received after the `version` message and before the `verack` message, * MAY ignore `feature` messages sent after `verack`, and * MAY disconnect peers who send `feature` messages after `verack`. Feature specifications based on this BIP: * MUST forbid sending messages it introduces after `verack` to a peer that has not indicated support for the feature via a `feature` message. ### `feature` message The payload of the `feature` message contains exactly the following data: | Type | Name | Description | | ----------- | ------------- | ----------- | | string | `featureid` | Unique identifier for the feature | | byte-vector | `featuredata` | Feature-specific configuration data | The `featureid` is encoded in the usual way, that is, as a `CompactSize` specifying the string length, followed by that many bytes. The string length MUST be between 4 and 80, inclusive. The string SHOULD include only printable ASCII characters (ie, each byte should have a value between 32 and 126, inclusive). Likewise, `featuredata` is encoded as a `CompactSize` specifying the byte-vector size, followed by that many bytes. How these bytes are interpreted is part of the feature's specification. The byte-vector size MUST NOT be more than 512 bytes. Note that the `featuredata` field is not optional, so if no data is required, an empty vector should be provided, ie serialized as `CompactSize` of 0. Nodes implementing this BIP MUST ignore `feature` messages specifying a `featureid` they do not support, so long as the payload conforms to the requirements above. Nodes implementing this BIP MAY disconnect peers that send `feature` messages where the `feature` message's payload cannot be correctly parsed (including having missing or additional data), even if they do not recognise the `featureid`. The `featureid` MUST be a globally unique identifier for the feature. For features published as a BIP, the `featureid` SHOULD be the assigned BIP number, eg "BIP434", or be based on the BIP number (eg, "BIP434v2" where the "v2" suffix covers versioning, or "BIP434.3" where the ".3" suffix covers part 3 of the BIP). For experimental features that do not (yet) have a BIP number assigned, some other unique identifier MUST be chosen, such as a URL to the repository where development is taking place, or the sha256 digest of some longer reference. #### `feature` message 1-byte identifier Nodes implementing both this BIP and [BIP 324 (v2 P2P encrypted transport)][BIP324] MUST treat a message with a 1-byte `message_type` equal to `37` that is received prior to `verack` as the `feature` message. ### Feature negotiation It is RECOMMENDED that feature negotiation be designed and implemented as follows: * all `feature` messages and the `verack` message should be sent immediately on receipt of the peer's `version` message * any negotiation calculations should be performed immediately on receipt of the peer's `verack` message This structure is fairly easy to implement, and avoids introducing any significant latency that might result from more interactive negotiation methods. Feature specifications defining a `featureid` MAY make use of the following approaches: #### Feature advertisement: 1. Send a `feature` message advertising the `featureid` unconditionally 2. Accept messages related to the feature unconditionally 3. Only send messages defined by the feature if the peer sent a valid `feature` message for the `featureid`. This approach is appropriate for many simple features that define new messages, particularly where an implementation might only implement sending or receiving a message, but not both, eg [BIP 35 (mempool)][BIP35]. #### Feature coordination: 1. Send a `feature` message advertising the `featureid` unconditionally 2. Check if the peer sends the same `feature` message (or a compatible one), and enable the feature for this peer if so. 3. Only send/accept messages or encode data items according to the feature's specification if the feature is enabled for this peer. This approach is appropriate for upgrades to data encoding in P2P messages, eg [BIP 339 (wtxidrelay)][BIP339] or [BIP 155 (addrv2)][BIP155]. #### Feature versioning: 1. Send `feature` messages for multiple incompatible features, eg `BIP434v3`, `BIP434v2`, `BIP434v1`, ordered from most preferred to least. 2. Track the corresponding `feature` messages from your peer. 3. If you were the listening peer, enable your highest preference feature that your peer also supports. 4. If you were the initiating peer, enable the first feature that your peer announced, that you also support. 5. For example if the listening peer sends `BIP434v3`, `BIP434v2`, `BIP434v1`, and the initiating peer sends `BIP434v1`, `BIP434v2`, then the listening peer should select `BIP434v2` when `verack` is received, and the initiating peer should select `BIP434v2` as soon as `feature BIP434v2` is received. 6. Conversely, if the initiating peer sends `BIP434v3`, `BIP434v2`, `BIP434v1`, and the listening peer sends `BIP434v1`, `BIP434v2`, then the listening peer should select `BIP434v1` when `verack` is received, and the initiating peer should select `BIP434v1` as soon as `feature BIP434v1` is received. 7. In most cases, implementations should simply advertise incompatible features in order from most recent to oldest, on the basis that the only reason to make incompatible updates is because there are significant improvements. Exceptions to that may occur when two incompatible features are both receiving active development, or when an implementation has only partially implemented the latest spec, and the older spec is better supported (and thus should be listed first, as the preferred protocol to adopt). This approach may be appropriate when making substantial changes to a deployed protocol and backwards compatibility is desirable on a short-term basis, or when there is disagreement amongst implementations or users as to which approach is most desirable. ## Considerations The advantage this approach has over bumping the protocol version number when introducing new P2P messages or data structures, is that no coordination is required (that is, there is no longer a question whether version "n+1" belongs to Alice's new feature, or Bob's new feature), and there is no implication that supporting each new feature means all prior features are also supported. The advantage this approach has over defining new messages for each feature is that the `featureid` can be much longer (at up to 80 bytes) than a message type id (which are limited to 12 bytes). With a [BIP 324][BIP324] one-byte `message_type`, the overhead compared to that approach is also kept small. This approach is largely equivalent to adding a [payload to the `verack` message][verack-payload] (eg, a vector of `featureid`, `featuredata` pairs). It was chosen because: * it retains compatibility with any implementations that expect `verack` to have no payload; * it allows peers to process each feature request individually, rather than having to first load the configuration information for all features into memory at once (in order to validate the message's checksum), and then deal with each feature's configuration; * limiting the maximum message payload size you accept (eg to 4MB) does not limit the number of features you can accept; and * we have experience with negotiating features with individual messages, but no experience with doing so via `verack` payload. A mild disadvantage compared to using a `verack` payload is that this approach allows the possibility of interactive feature negotiation prior to `verack`. However interactive feature negotiation is always possible simply by having the initiating peer disconnect and reconnect after discovering the listening peer's supported features. This specification attempts to maximise compatibility with implementations that prefer to fully validate each message received: * `feature` messages, even for unknown features, must always be fully parseable into a `featureid` and `featuredata` * Ignoring unknown messages prior to `verack` is only a recommendation, not a requirement, so compliant implementations may disconnect on an unknown message that cannot be validated. * Sending unknown messages after `verack` is explicitly forbidden, in so far as that is possible. ## Backward compatibility Clients specifying a version number prior to `70017` remain fully compatible with this change. Clients specifying a version number of `70017` or higher that do not implement this BIP remain fully compatible provided they do not disconnect peers upon receiving unexpected messages received between `version` and `verack`. ## Acknowledgements Much of the logic here, and much of the text in the motivation section, is based on Suhas Daftuar's 2020 post on [Generalizing feature negotiation][suhas-draft]. ## Copyright This BIP is licensed under the 2-clause BSD license. [BIP130]: https://github.com/bitcoin/bips/blob/master/bip-0130.mediawiki [BIP133]: https://github.com/bitcoin/bips/blob/master/bip-0133.mediawiki [BIP152]: https://github.com/bitcoin/bips/blob/master/bip-0152.mediawiki [BIP155]: https://github.com/bitcoin/bips/blob/master/bip-0155.mediawiki [BIP339]: https://github.com/bitcoin/bips/blob/master/bip-0339.mediawiki [BIP35]: https://github.com/bitcoin/bips/blob/master/bip-0035.mediawiki [BIP324]: https://github.com/bitcoin/bips/blob/master/bip-0324.mediawiki [verack-payload]: https://gnusha.org/pi/bitcoindev/B514142F-382B-4D49-B68D-0115ECBD1D79@voskuil.org/ [PR#20564]: https://github.com/bitcoin/bitcoin/pull/20564 [PR#9720]: https://github.com/bitcoin/bitcoin/pull/9720 [PR#19723]: https://github.com/bitcoin/bitcoin/pull/19723 [btcd#1812]: https://github.com/btcsuite/btcd/pull/1812 [btcd#1661]: https://github.com/btcsuite/btcd/issues/1661 [permless-extensible]: https://github.com/bitcoin/bitcoin/pull/20564#issuecomment-738456560 [0.1-extensibility]: https://github.com/benjiqq/bitcoinArchive/blob/master/bitcoin0.1/src/main.cpp#L2035-L2039 [suhas-draft]: https://gnusha.org/pi/bitcoindev/CAFp6fsE=HPFUMFhyuZkroBO_QJ-dUWNJqCPg9=fMJ3Jqnu1hnw@mail.gmail.com/ ================================================ FILE: bip-0442.md ================================================ ``` BIP: 442 Layer: Consensus (soft fork) Title: OP_PAIRCOMMIT Authors: moonsettler Brandon Black Status: Draft Type: Specification Assigned: 2024-12-09 License: BSD-3-Clause Discussion: https://delvingbitcoin.org/t/op-paircommit-as-a-candidate-for-addition-to-lnhance/1216 https://groups.google.com/g/bitcoindev/c/si6ZNIkVfOw/m/29VY_YRrCgAJ ``` ## Abstract This BIP proposes a new tapscript opcode, `OP_PAIRCOMMIT`, which enables efficient and secure commitment to pairs of stack elements using a tagged hash construction. This opcode provides limited vector commitment functionality, facilitating more expressive contracts and improved data availability in Bitcoin scripts. ## Summary For taproot script spends with leaf version *0xc0* (see [BIP-342]), `OP_PAIRCOMMIT` replaces `OP_SUCCESS205` (*0xcd*). When executed, `OP_PAIRCOMMIT` pops the top two stack elements, computes a *PairCommit* tagged SHA256 hash over their compact size and data, and pushes the resulting 32-byte hash onto the stack. ## Specification Notation follows [BIP-340], including the tagged hash notation: *hashtag(x) = SHA256(SHA256(tag) || SHA256(tag) || x)* Stack operation: - If fewer than 2 elements are present, script execution fails. - Let the stack be *[..., x1, x2]* (top is rightmost). - Compute: `pc` = *hashPairCommit(compact_size(len(x1)) || x1 || compact_size(len(x2)) || x2)*[^1] - Pop `x2` and `x1` from the stack. - Push `pc` onto the stack. [^1]: The number of SHA256 blocks is minimized in typical use cases. The tag can be precomputed as a SHA256 mid-state, requiring only two hash cycles for two 32-byte items, or one for two smaller items. ## Motivation Bitcoin scripts often commit to single data items (e.g., hash/time locks, P2PKH), but lack native support for committing to multiple items together. `OP_PAIRCOMMIT` enables Merklized commitments, allowing contracts to commit to trees of elements with a single hash. This supports use cases such as hash lock contracts where any pre-image in a Merkle tree can unlock a spend. Combined with `OP_CHECKSIGFROMSTACK`, signing commitments to multiple items enables complex delegation (e.g., delegating to `key1` after time `t1` and `key2` after time `t2`). Previously, such delegation required key laddering[^2], which is more costly in validation. `OP_PAIRCOMMIT` enforces relationships between items efficiently. [^2]: Key laddering involves a sequence of keys signing tuples of items and keys, which is costly in bytes and sigops. See [key laddering post] for details. ## Examples ### Committing to more than 2 elements `OP_PAIRCOMMIT` can commit to a vector of stack elements securely and efficiently. ```perl # Commit to three elements: a, b, c # pc-hash = PC(a, PC(b, c)) # Witness: OP_PAIRCOMMIT # , PC(b, c) OP_PAIRCOMMIT # PC(a, PC(b, c)) # PC(a, PC(b, c)), OP_EQUALVERIFY # # ... ``` ### Use in Lightning Symmetry Lightning Symmetry contracts require data availability for contested closes. [^3] By forcing parties to include settlement transaction hashes in the witness, later updates can reconstruct scripts of intermediate states while only keeping the latest state. [^3]: The required data is a full CTV hash of the settlement transaction when there are open HTLCs, or merely the difference in balance between the channel partners in other cases. Whether the latter optimization would be used is an implementation detail not further discussed here. ```perl # S: 500000000 # internal-key: BIP-327 aggregate key of channel participants # state-n-hash: { nLockTime(S+n), out(contract, amount(A)+amount(B)) } # settlement-n-hash: { nSequence(2w), out(A, amount(A)), out(B, amount(B)) } # state-n-recovery-data: { settlement-n-hash or state-n-balance } ``` #### Example channel script (pseudo-code) ```perl # Witness: OP_CHECKTEMPLATEVERIFY # , , OP_PAIRCOMMIT # , PC(state-n-recovery-data, state-n-hash) OP_INTERNALKEY # , PC(state-n-recovery-data, state-n-hash), OP_CHECKSIGFROMSTACK # <1> # <1>, OP_CHECKLOCKTIMEVERIFY # <1>, OP_DROP # <1> ``` #### Channel update script (pseudo-code) for m > n ```perl OP_IF # Witness: OP_CHECKTEMPLATEVERIFY # , , OP_PAIRCOMMIT # , PC(state-m-recovery-data, state-m-hash) OP_INTERNALKEY # , PC(state-m-recovery-data, state-m-hash), OP_CHECKSIGFROMSTACK # <1> # <1>, OP_CHECKLOCKTIMEVERIFY # <1>, OP_DROP # <1> OP_ELSE # Empty witness stack # OP_CHECKTEMPLATEVERIFY # OP_0NOTEQUAL # <1> OP_ENDIF ``` These constructions ensure both parties sign the same pair hash, requiring inclusion of both update and settlement hashes in the witness. [^4] [^5] [^4]: `state-n-hash` commits to a specific `nLockTime` value for the transaction through `OP_CHECKTEMPLATEVERIFY`; `OP_CHECKLOCKTIMEVERIFY` ensures that the state progression can only go forward (the transaction needs to have greater `nLockTime` value than the intermediate state [^5]: `OP_0NOTEQUAL` can be omitted (any non-zero value left on the stack would be accepted by the script interpreter). ### In MATT The Merklize All The Things ([MATT]) framework uses `OP_CAT` to combine items for commitments. `OP_PAIRCOMMIT` provides a more ergonomic and secure alternative[^6]. [^6]: Naive use of `OP_CAT` is vulnerable to byte shifting attacks. E.g. *0x0102 || 0x03* equals *0x01 || 0x0203*. Mitigation requires length checking or hashing. ## Alternative approaches Alternative approaches considered and rejected: - `OP_CAT`[^6][^9] - SHA256 streaming opcodes[^9] - Merkle operation opcodes - 'Kitty' CAT: `OP_CAT` with size limits - `OP_CHECKTEMPLATEVERIFY` committing to the taproot annex[^7] - `OP_CHECKSIGFROMSTACK` on n elements - `OP_VECTORCOMMIT`: generalized for n > 2 elements - ReKey/Laddering[^2] - `OP_RETURN`[^8] [^7]: Committing to the taproot annex allows one additional item, but it is not accessible to script. [^8]: `OP_RETURN` can commit to additional data, but is costly and not accessible to script. [^9]: `OP_PAIRCOMMIT` enables useful scripts without the risks of `OP_CAT` (see [CAT-tricks-I], [CAT-tricks-II]). ## Reference Implementation ### Code ```c++ case OP_PAIRCOMMIT: { // OP_PAIRCOMMIT is only available in Tapscript // ... // x1 x2 -- hash if (stack.size() < 2) { return set_error(serror, SCRIPT_ERR_INVALID_STACK_OPERATION); } const valtype& vch1 = stacktop(-2); const valtype& vch2 = stacktop(-1); uint256 hash = PairCommitHash(vch1, vch2); stack.pop_back(); stack.pop_back(); stack.emplace_back(hash.begin(), hash.end()); break; } ``` ```c++ const HashWriter HASHER_PAIRCOMMIT{TaggedHash("PairCommit")}; uint256 PairCommitHash(const std::vector& x1, const std::vector& x2) { return (HashWriter{HASHER_PAIRCOMMIT} << x1 << x2).GetSHA256(); } ``` ### Pull Request https://github.com/lnhance/bitcoin/pull/6/files ## Rationale ### Cost comparison of Lightning Symmetry constructions | Method | Channel Script | Update Script | Update Witness1 | Force Close2 | Contest | Settlement Mechanism | |:----------------------|---------------:|--------------:|---------------------------:|------------------------:|--------:|:--------------------:| | APO-Annex | 8 WU | 113 WU | 100 WU | 1221 WU | 627 WU| SigOp | | APO-Return | 8 WU | 113 WU | 66 WU | 1359 WU | 765 WU| SigOp | | CTV+CSFS | 43 WU | 81 WU | 98 WU | 1394 WU | 765 WU| HashEq | | CTV+CSFS+IKEY | 10 WU | 48 WU | 98 WU | 1328 WU | 732 WU| HashEq | | CTV+CSFS+IKEY+PC | 11 WU | 49 WU | 131 WU | 1191 WU | 594 WU| HashEq | | THIKCS-Annex | 10 WU | 49 WU | 98 WU | 1160 WU | 563 WU| HashEq | | THIKCS-Return | 10 WU | 49 WU | 66 WU | 1329 WU | 733 WU| HashEq | 1 *Witness is the same weight for both Force Close and Contest in LN-Symmetry* \ 2 *Total cost of unilateral close transactions* \ 3 *THIKCS is short for TEMPLATEHASH+IKEY+CSFS* ### Proving general computation using trees `OP_PAIRCOMMIT` enables Merkle tree commitments, which can represent functions where inputs and corresponding outputs are the leaves. Taproot trees can be 128 levels deep, therefore including up to 2128 possible leaf scripts that can represent complex functions. This is already over the practical computational limits to enumerate and Merklize. ## Backward Compatibility Constraining `OP_SUCCESS` opcodes allows deployment as a backwards-compatible soft fork. Reliance on `OP_SUCCESS205` behavior will be invalidated by `OP_PAIRCOMMIT`. ## Deployment TBD ## Credits Jeremy Rubin, Salvatore Ingala, Anthony Towns, Ademan555, Psifour ## Copyright This document is licensed under the 3-clause BSD license. ## References 1. LNhance bitcoin repository: [lnhance] 2. Lightning Symmetry: [eltoo] 3. OP_CAT: [BIP-347], [BIN-2024-0001] 4. OP_CHECKTEMPLATEVERIFY: [BIP-119] 5. OP_CHECKSIGFROMSTACK: [BIP-348], [BIN-2024-0003] 6. OP_CHECKCONTRACTVERIFY: [BIP-443] 7. OP_INTERNALKEY: [BIP-349], [BIN-2024-0004] 8. OP_TEMPLATEHASH: [BIP-446] 9. Tagged hash: [BIP-340] 10. MuSig2: [BIP-327] [lnhance]: https://github.com/lnhance/bitcoin [eltoo]: https://github.com/instagibbs/bolts/blob/eltoo_draft/XX-eltoo-transactions.md [CAT-tricks-I]: https://medium.com/blockstream/cat-and-schnorr-tricks-i-faf1b59bd298 [CAT-tricks-II]: https://medium.com/blockstream/cat-and-schnorr-tricks-ii-2f6ede3d7bb5 [MATT]: https://merkle.fun [Lightning Symmetry write-up]: https://delvingbitcoin.org/t/ln-symmetry-project-recap/359 [key laddering post]: https://rubin.io/bitcoin/2024/12/02/csfs-ctv-rekey-symmetry/ [//]: # (BIPs referenced) [BIP-119]: https://github.com/bitcoin/bips/tree/master/bip-0119.mediawiki [BIP-327]: https://github.com/bitcoin/bips/blob/master/bip-0327.mediawiki [BIP-340]: https://github.com/bitcoin/bips/blob/master/bip-0340.mediawiki [BIP-341]: https://github.com/bitcoin/bips/blob/master/bip-0341.mediawiki [BIP-342]: https://github.com/bitcoin/bips/blob/master/bip-0342.mediawiki [BIP-347]: https://github.com/bitcoin/bips/blob/master/bip-0347.mediawiki [BIP-348]: https://github.com/bitcoin/bips/blob/master/bip-0348.md [BIP-349]: https://github.com/bitcoin/bips/blob/master/bip-0349.md [BIP-443]: https://github.com/bitcoin/bips/blob/master/bip-0443.mediawiki [BIP-446]: https://github.com/instagibbs/bips/blob/bip_op_templatehash/bip-0446.md [BIN-2024-0001]: https://github.com/bitcoin-inquisition/binana/blob/master/2024/BIN-2024-0001.md [BIN-2024-0003]: https://github.com/bitcoin-inquisition/binana/blob/master/2024/BIN-2024-0003.md [BIN-2024-0004]: https://github.com/bitcoin-inquisition/binana/blob/master/2024/BIN-2024-0004.md [//]: # (Internal links) [optimal]: #cost-comparison-of-ln-symmetry-constructions ================================================ FILE: bip-0443.mediawiki ================================================
  BIP: 443
  Layer: Consensus (soft fork)
  Title: OP_CHECKCONTRACTVERIFY
  Authors: Salvatore Ingala 
  Status: Draft
  Type: Specification
  Assigned: 2025-05-08
  License: BSD-3-Clause
  Discussion: 2022-11-08: https://gnusha.org/pi/bitcoindev/CAMhCMoH9uZPeAE_2tWH6rf0RndqV+ypjbNzazpFwFnLUpPsZ7g@mail.gmail.com
              2023-07-30: https://gnusha.org/pi/bitcoindev/CAMhCMoFYF+9NL1sqKfn=ma3C_mfQv7mj2fqbqO5WXVwd6vyhLw@mail.gmail.com
== Abstract == This BIP proposes to add consensus support for a new tapscript opcode that enables a new type of output restrictions: OP_CHECKCONTRACTVERIFY (OP_CCV). This opcode enables users to create UTXOs that carry a dynamic commitment to a piece of data. The commitment can be validated during the execution of the script, allowing introspection to the committed data. Moreover, a script can constrain the internal public key and taptree of one or more outputs, and possibly the committed data. In conjunction with an opcode for ''vector commitments''''Vector commitments'' are cryptographic primitives that allow to commit to a vector of values via a single short value. Hashing and concatenation trivially allow to commit to an entire vector, and later reveal all of its elements. Merkle trees are among the simplest efficient vector commitments, allowing to reveal individual elements with logarithmically-sized proofs., this allows to create and compose arbitrary state machines that define the possible future outcomes of a UTXO. The validity of a state transition depends on the conditions that can be expressed in the program (scripts in the taptree). === Copyright === This document is licensed under the 3-clause BSD license. === Motivation === The ability to constrain the future of coins beyond what is possible with presigned transactions is at the core of numerous attempts to improve bitcoin. Some of the proposed applications include: * UTXO sharing schemes like Ark, CoinPools, Timeout Trees, etc. use various types of output restrictions in order to enable multiple parties to share the control of a UTXO, while ensuring that each participant controls their own balance. * OP_VAULT[[bip-0345.mediawiki|BIP-345]] is a proposed opcode to implement a 2-step withdrawal process, enabling on-chain reactive security. * OP_CHECKTEMPLATEVERIFY[[bip-0119.mediawiki|BIP-119]] is a long-proposed opcode to constrain a transaction to a ''template'' with a fixed set of outputs. * Sidechains and rollups could be implemented via a UTXO encumbered with a recursive covenant, updating the sidechain state root every time it is spent. Constructions like BitVMhttps://bitvm.org/ try to side-step the lack of a primitive allowing UTXOs to carry state with a clever use of Lamport Signatures, and optimistic execution of smart contracts. This comes with an extremely high cost in term of complexity, interactivity, and (potentially) in block size occupation, for some of the possible execution paths. Moreover, the design of fully trustless bridges remains elusive. Rather than providing a construct optimized for a specific application, this BIP aims to provide a fundamental building block that is widely applicable, and common to many constructions. == Design == OP_CHECKCONTRACTVERIFY is an implementation of a new primitive that could be called ''state-carrying UTXOs''. It allows to embed a commitment to a piece of data in a UTXO, and to validate it during the execution of the script, and ''carry'' a (possibly dynamically computed) piece of data to the new UTXOs that are produced. We consider the ''program'' of a P2TR UTXO to be composed of an x-only public key (that we call the ''naked key''), and a Merkle tree of scripts. If there is no data committed in the UTXO, then the naked key is the internal key as defined in BIP-341. If the UTXO carries a commitment to a 32-byte hash (the ''data''), the naked key is tweaked with a hash of the data. The resulting key is the taproot internal key per BIP-341. This allows to embed a commitment to the data that can be validated during the script execution, while staying fully compatible with taproot. Notably: * the committed data does not make the UTXO any larger; * the keypath spend is still available to any party that possesses the private key of the naked key, as long as they have knowledge of the embedded data (or at least the data’s hash)For example, in a multi-party contract, the naked key could be an aggregate key using [[bip-0327.mediawiki|MuSig2]]; the taproot keypath would therefore allow a ''cooperative'' spend, without executing any script at all. Like for all taproot transactions, this is indeed the cheapest way of spending the UTXO — albeit not always possible in practice.; * if multiple scripts are in different leaves of the taptree, only the ones that actually need to access the data have to pay a cost for it, in terms of additional witness bytes. OP_CHECKCONTRACTVERIFY can be applied to introspect the program and data of one of the inputs of the transaction (typically, the UTXO being spent, in order to access its committed data), or one of the outputs of the transaction (in order to define its program, and possibly its committed data). === Output amounts === When checking the script of one or more outputs with OP_CHECKCONTRACTVERIFY, it is usually necessary to also check that the amount of the current input (that is, the UTXO being spent) is correctly distributed among the outputs in the expected way. Therefore, the opcode already includes an amount semantic that covers the common use cases. There are three supported modes for the opcode when checking an output, depending on the value of the mode parameter: * ''default'': the residual amount of the current input must be preserved in the output (aggregate across the inputs that specify the output); * ''ignore'': the output amount is ignored. * ''deduct'': the amount of the checked output is subtracted from the amount of the current input (the residual amount is then available for further checks); The ''default'' logic covers the common case where a UTXO’s full amount is required to be sent to a specific output. The ''deduct'' logic allows to assign portions of the input amount to one or more outputs; the residual amount, checked with a final check using the ''default'' logic, can be used to enforce that the total amount is preserved. The following figures illustrate some common examples of supported use cases for the amount logic. This list is not exhaustive, as there are many more possible combinations. '''Remark:''' validation fails if the amount of an output is checked with both the ''default'' and the ''deduct'' logic in the same transaction, or multiple times with the ''deduct'' logic. This prevents duplicate or inconsistent counting of the same amounts. '''Remark:''' it is allowed for multiple inputs to check the same output with the ''default'' logic. This allows multiple inputs to aggregate (in full or in part) their amounts to the same output. ----- ::[[File:bip-0443/amount_example_1.png|framed|center|alt=1-to-1 amount logic|600px]] ::'''Figure 1:''' A UTXO A sends the entire amount to some output contract B, using CCV with the default semantic. ----- ::[[File:bip-0443/amount_example_2.png|framed|center|alt=3-to-1 aggregate amount logic|600px]] ::'''Figure 2:''' Three UTXOs aggregate their amounts towards the same output contract, using CCV with the default semantic. ----- ::[[File:bip-0443/amount_example_3.png|framed|center|alt=split amount logic|600px]] ::'''Figure 3:''' A UTXO A sends a portion of its amount to a contract A' identical to itself, and the rest to a different contract B. It would use CCV to introspect its own input's program, then to check the first output with the deduct semantic, then to check the second output with the default semantic to assign the residual amount. ----- ::[[File:bip-0443/amount_example_4.png|framed|center|alt=split and aggregate amount logic|600px]] ::'''Figure 4:''' Similar to the previous example, but a second input B also checks the same output X with the default semantic, aggregating its input with the residual amount of the first input. ----- Note that the ''deduct'' semantic does not allow to check the exact amount of its output. Therefore, in contracts using a scheme similar to figure 3 or 4 above, amounts should be constrained either with a signature, or with future introspection opcodes that allow fixing the amount. In lack of that, amounts would be malleable. === Paying fees === Since the amount-checking semantics of OP_CHECKCONTRACTVERIFY are designed to preserve the entire input amount across one or more outputs, transaction fees must be paid exogenously. This can be achieved by adding an extra input to the transaction, by using an anchor output, or with other future mechanisms. The ''ignore'' amount mode is not a safe mechanism for paying endogenous fees. An output checked with this mode has no amount constraint, which would allow a miner to claim the entire value of that input. This mode is included for forward compatibility with potential future soft forks that may introduce other amount-related logic that is compatible with OP_CHECKCONTRACTVERIFY's script checks. == Specification == The tapscript opcode OP_SUCCESS187 (0xbb) is constrained with new rules to implement OP_CHECKCONTRACTVERIFY. When evaluating OP_CHECKCONTRACTVERIFY (OP_SUCCESS187, 0xbb), the expected format of the stack, shown bottom-to-top, is: where: * is a minimally encoded integer, according to one of the values defined below. * is the Merkle root of the taproot tree, or a minimally encoded -1, or the empty buffer. * is called the ''naked key'', and it's a valid 32-byte x-only public key, or a minimally encoded -1, or the empty buffer. * is a minimally encoded -1, or a minimally encoded non-negative integer. * is a buffer of arbitrary length. In short, the semantics of the opcode with respect to the script can be summarized as follows:
Verify that the input/output with the given 'index' is a P2TR UTXO whose taproot output key is obtained from 'pk', tweaked with the hash of 'data' (if non-empty), then taptweaked with 'taptree' (if non-empty).
If the is non-empty, then the additive tweak for the data is computed as: data_tweak = sha256(pk || data) In the following, the ''current input'' is the input whose script is being executed. The following values of the are defined: * CCV_MODE_CHECK_INPUT = -1: Check an input's script; no amount check. * CCV_MODE_CHECK_OUTPUT = 0: Check an output's script; preserve the (possibly residual) amount. * CCV_MODE_CHECK_OUTPUT_IGNORE_AMOUNT = 1: Check an output's script; ignore amounts. * CCV_MODE_CHECK_OUTPUT_DEDUCT_AMOUNT = 2: Check an output's script; deduct the output amount from the input's residual amount. Any other value of the makes the opcode succeed validation immediately for the current inputThis allows to soft-fork future behavior by introducing new values for the . As the mode would always be hard-coded via a push in the script, the risk of mistakes seems negligible.. The following values of the other parameters have special meanings: * If the is -1, it is replaced with the Merkle root of the current input's tapscript tree. If the taptree is the empty buffer, then the taptweak is skipped. * If the is 0, it is replaced with the NUMS x-only pubkey 0x50929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac0 defined in [[bip-0341.mediawiki|BIP-341]]. If the is -1, it is replaced with the taproot internal key of the current input. * If the is -1, it is replaced with the index of the current input. * If the is the empty buffer, then there is no data tweak for the input/output being checked. Any other value of the , , or parameters is invalid, and makes the opcode immediately fail validation. === Script support for OP_CHECKCONTRACTVERIFY === The specification is divided into three parts: * the transaction-wide initialization; * the input initialization; * the opcode evaluation. The following helper function is a variant of taproot_tweak_pubkey from [[bip-0341.mediawiki|BIP341]], except that a regular SHA256-hash is used instead of a tagged hash, and the pubkey is returned unchanged if the length of data is 0. def tweak_embed_data(pubkey, data): assert len(pubkey) == 32 if len(data) == 0: return None, pubkey data_tweak = sha256(pubkey + data) t = int_from_bytes(data_tweak) if t >= SECP256K1_ORDER: raise ValueError P = lift_x(int_from_bytes(pubkey)) if P is None: raise ValueError Q = point_add(P, point_mul(G, t)) return 0 if has_even_y(Q) else 1, bytes_from_int(x(Q)) The taproot_tweak_pubkey function is also used as a helper in the pseudocode below. The following notations are used in the pseudocode below: * n_inputs and n_outputs are the number of inputs and outputs of the transaction, respectively; * inputs[i] is the i-th input of the transaction; * outputs[i] is the i-th output of the transaction; * this_input_index, this_input_internal_key and this_input_taptree are the index, taproot internal key and taproot Merkle root of the current input, respectively. * P2TR(key) computes the scriptPubKey of the P2TR output with the given key as the taproot output key. ==== Transaction-wide initialization ==== This is executed once for the entire transaction, before any of the transaction input's scripts are evaluated. It initializes three arrays that are used to keep track of the amount information of the output. output_min_amount = [0] * n_outputs output_checked_default = [False] * n_outputs output_checked_deduct = [False] * n_outputs ==== Input initialization ==== This is executed at the beginning of the evaluation of each input's script. It initializes the residual amount to equal the full amount of the current input. residual_input_amount = inputs[this_input_index].amount ==== OP_CHECKCONTRACTVERIFY evaluation ==== The following code is executed every time the OP_CHECKCONTRACTVERIFY opcode is encountered during the evaluation of a taproot script spend. this_input_index, this_input_internal_key and this_input_taptree are the index, taproot internal key and taproot Merkle root of the current input. BIP341_NUMS_KEY is the x-only provably unspendable key 50929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac0 defined in [[bip-0341.mediawiki|BIP-341]]. if mode < CCV_MODE_CHECK_INPUT or mode > CCV_MODE_CHECK_OUTPUT_DEDUCT_AMOUNT: return success() # undefined mode is OP_SUCCESS if index == -1: index = this_input_index if mode == CCV_MODE_CHECK_INPUT: if index < 0 or index >= n_inputs: return fail() # input index out of bounds target_script = inputs[index].scriptPubKey else: if index < 0 or index >= n_outputs: return fail() # output index out of bounds target_script = outputs[index].scriptPubKey if taptree == <-1>: taptree = this_input_taptree if pk == <0>: naked_key = BIP341_NUMS_KEY elif pk == <-1>: naked_key = this_input_internal_key elif len(pk) == 32: naked_key = pk else: return fail() # Verify the target contract data and program _, internal_key = tweak_embed_data(naked_key, data) if len(taptree) != 0: if len(taptree) != 32: return fail() _, final_key = taproot_tweak_pubkey(internal_key, taptree) else: final_key = internal_key if target_script != P2TR(final_key): return fail() # Amount checks if mode == CCV_MODE_CHECK_OUTPUT: # default amount semantic if output_checked_deduct[index]: return fail() output_min_amount[index] += residual_input_amount residual_input_amount = 0 if outputs[index].amount < output_min_amount[index]: return fail() output_checked_default[index] = True elif mode == CCV_MODE_CHECK_OUTPUT_DEDUCT_AMOUNT: # 'deduct' amount semantic if residual_input_amount < outputs[index].amount: return fail() if output_checked_default[index] or output_checked_deduct[index]: return fail() residual_input_amount = residual_input_amount - outputs[index].amount output_checked_deduct[index] = True stack.pop(5) # drop all 5 stack elements ==== sigops budget ==== TODO == Policy changes == TODO == Implementation == A reference implementation is provided as a bitcoin-core [https://github.com/bitcoin/bitcoin/pull/32080 pull request]. == Examples == This section documents some common script fragments that use OP_CHECKCONTRACTVERIFY for various common choices of the parameters. Depending on the use case, some of the parameters might be passed via the witness stack. In these examples, <> (empty buffer) and 0 both refer to an empty stack element. ---- Check data embedded in the current input: OP_CHECKCONTRACTVERIFY This would be used to access the data committed in the current input. The parameter, of course, would be passed via the witness stack. ---- Check that the input with index in_i is a specific contract with embedded input_data: OP_CHECKCONTRACTVERIFY This allows introspecting the program (naked key and taptree) and data of another input of the transaction. ---- Check that the output with index out_i is a certain contract (pubkey and taptree) with the specified embedded , preserving input amount: OP_CHECKCONTRACTVERIFY This allows introspecting an output's program and data, and sending the full residual amount to it. Logically, it can be thought as a state transition, moving money to a different state, but still under the control of the pre-set rules. Typically, the data would be computed based on the witness stack, while the output program would be hard-coded in Script. ---- Check that the output with index out_i is a P2TR with pubkey output_pk, preserving amount: > # no data > # no taptweak OP_CHECKCONTRACTVERIFY Unlike the previous example, here there is no computation over the destination taproot public key, since both data and taptweak are omitted. ---- Check that the output with index out_i is a certain contract (pubkey and taptree) with the specified embedded data; don't check amount: OP_CHECKCONTRACTVERIFY '''Remark:''' amounts are malleable with this check alone; therefore, it is expected that the amount is also checked with separate introspection opcodes. ---- Check that the amount of the current input is partially sent to the first output (that must have a certain pubkey), and all the remaining amount is sent to the second output, which has the same internal key and taptree as the current input: > # no data > > # no tweak OP_CHECKCONTRACTVERIFY > # no data OP_CHECKCONTRACTVERIFY '''Remark:''' in some applications, it might be desirable to check the exact amount of the first output with separate introspection opcodes. == Applications == TODO == Deployment == The activation mechanism, and the set of other BIPs to be concurrently deployed, are to be determined. == Backwards compatibility == OP_CHECKCONTRACTVERIFY replaces the witness v1-only opcode OP_SUCCESS187 with stricter verification semantics. Consequently, scripts using those opcodes which previously were valid will cease to be valid with this change. Stricter verification semantics for an OP_SUCCESSx opcode are a soft fork, so existing software will be fully functional without upgrade except for mining and block validation. == Footnotes == == Acknowledgements == TODO ================================================ FILE: bip-0446/README.md ================================================ # `OP_TEMPLATEHASH` test vectors The test vectors are split into basic sanity checks and more extensive coverage. Both are JSON files containing a JSON array of JSON objects. Each JSON object in the array represents a Script validation test case. For [`basics.json`](basics.json), each object contains the following fields: - `spending_tx`: a hexadecimal string representing a serialized Bitcoin transaction. This is the transaction to be validated. - `input_index`: a JSON integer representing the index of the transaction input for which to perform Script validation. - `spent_outputs`: a JSON array of hexadecimal strings representing serialized Bitcoin transaction outputs. This is the list of outputs pointed to by the inputs of the transaction to be validated. - `valid`: a JSON boolean. Whether script validation should succeed. - `comment`: a JSON string. Reason why script validation should succeed or fail. For [`script_assets_test.json`](script_assets_test.json), each object contains the following fields: - `tx`: a hexadecimal string representing a serialized Bitcoin transaction. This is the transaction to be validated. - `index`: a JSON integer representing the index of the transaction input for which to perform Script validation. - `prevouts`: a JSON array of hexadecimal strings representing serialized Bitcoin transaction outputs. This is the list of outputs pointed to by the inputs of the transaction to be validated. - `flags`: a JSON array of strings representing the script validation flags to enable for this test case. - `success`: an optional JSON object representing the transaction input fields to set such as script validation succeeds. The subfields are the following: - `scriptSig`: a JSON hexadecimal string representing the serialized input script. - `witness`: a JSON array of hexadecimal strings representing the witness stack for this input. - `final`: an optional JSON boolean which, if true, indicates script validation should always succeed with more validation flags than specified in `flags`. - `failure`: an optional JSON object representing the transaction input fields to set such as script validation fails. The subfields are the following: - `scriptSig`: a JSON hexadecimal string representing the serialized input script. - `witness`: a JSON array of hexadecimal strings representing the witness stack for this input. Location of code that generated the test [`basics.json`](basics.json) [here](https://github.com/instagibbs/bitcoin/blob/2025-07-op_templatehash/src/test/script_tests.cpp#L1820). Example usage of [`script_assets_test.json`](script_assets_test.json) [here](https://github.com/bitcoin/bitcoin/blob/f490f5562d4b20857ef8d042c050763795fd43da/src/test/script_tests.cpp#L1558). ================================================ FILE: bip-0446/basics.json ================================================ [ { "spent_outputs": [ "33790600000000002251205331c80448b5eb2daad3567c98bc99664d14e0ea12bdf3be755429055d67756a", "22921000000000001976a914079ded3e3befdab0757fe0e8842aeffc0ff2160288ac" ], "spending_tx": "02000000000102c997a5e56e104102fa209c6a852dd90660a20b2d9c352423edce25857fcd37041500000000ffffffff169e1e83e930853391bc6f35f605c6754cfead57cf8387639d3b4096c54f18f40c00000000ffffffff01327906000000000016001482074bdf6ce32b071dd120a17cf99cbc01ad3080022320d1f1955b1327167cb7ae3dc39d52c277be39d75737b9cb80514ce6e825fd8eeace8721c050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac00000000000", "input_index": 0, "valid": true, "comment": "Template hash matches. Input index matches." }, { "spent_outputs": [ "22921000000000001976a914079ded3e3befdab0757fe0e8842aeffc0ff2160288ac", "33790600000000002251205331c80448b5eb2daad3567c98bc99664d14e0ea12bdf3be755429055d67756a" ], "spending_tx": "02000000000102169e1e83e930853391bc6f35f605c6754cfead57cf8387639d3b4096c54f18f40c00000000ffffffffc997a5e56e104102fa209c6a852dd90660a20b2d9c352423edce25857fcd37041500000000ffffffff01327906000000000016001482074bdf6ce32b071dd120a17cf99cbc01ad308000022320d1f1955b1327167cb7ae3dc39d52c277be39d75737b9cb80514ce6e825fd8eeace8721c050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac000000000", "input_index": 1, "valid": false, "comment": "Template hash matches. Input index mismatches." }, { "spent_outputs": [ "33790600000000002251205331c80448b5eb2daad3567c98bc99664d14e0ea12bdf3be755429055d67756a", "22921000000000001976a914079ded3e3befdab0757fe0e8842aeffc0ff2160288ac" ], "spending_tx": "2a000000000102c997a5e56e104102fa209c6a852dd90660a20b2d9c352423edce25857fcd37041500000000ffffffff169e1e83e930853391bc6f35f605c6754cfead57cf8387639d3b4096c54f18f40c00000000ffffffff01327906000000000016001482074bdf6ce32b071dd120a17cf99cbc01ad3080022320d1f1955b1327167cb7ae3dc39d52c277be39d75737b9cb80514ce6e825fd8eeace8721c050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac00000000000", "input_index": 0, "valid": false, "comment": "Template hash mismatches: incorrect transaction version." }, { "spent_outputs": [ "33790600000000002251205331c80448b5eb2daad3567c98bc99664d14e0ea12bdf3be755429055d67756a", "22921000000000001976a914079ded3e3befdab0757fe0e8842aeffc0ff2160288ac" ], "spending_tx": "02000000000102c997a5e56e104102fa209c6a852dd90660a20b2d9c352423edce25857fcd37041500000000ffffffff169e1e83e930853391bc6f35f605c6754cfead57cf8387639d3b4096c54f18f40c00000000ffffffff01327906000000000016001482074bdf6ce32b071dd120a17cf99cbc01ad3080022320d1f1955b1327167cb7ae3dc39d52c277be39d75737b9cb80514ce6e825fd8eeace8721c050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac0002a000000", "input_index": 0, "valid": false, "comment": "Template hash mismatches: incorrect transaction locktime." }, { "spent_outputs": [ "33790600000000002251205331c80448b5eb2daad3567c98bc99664d14e0ea12bdf3be755429055d67756a", "22921000000000001976a914079ded3e3befdab0757fe0e8842aeffc0ff2160288ac" ], "spending_tx": "02000000000102c997a5e56e104102fa209c6a852dd90660a20b2d9c352423edce25857fcd37041500000000ffffffff169e1e83e930853391bc6f35f605c6754cfead57cf8387639d3b4096c54f18f40c00000000ffffffff01337906000000000016001482074bdf6ce32b071dd120a17cf99cbc01ad3080022320d1f1955b1327167cb7ae3dc39d52c277be39d75737b9cb80514ce6e825fd8eeace8721c050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac00000000000", "input_index": 0, "valid": false, "comment": "Template hash mismatches: incorrect output value." }, { "spent_outputs": [ "33790600000000002251205331c80448b5eb2daad3567c98bc99664d14e0ea12bdf3be755429055d67756a", "22921000000000001976a914079ded3e3befdab0757fe0e8842aeffc0ff2160288ac" ], "spending_tx": "02000000000102c997a5e56e104102fa209c6a852dd90660a20b2d9c352423edce25857fcd37041500000000ffffffff169e1e83e930853391bc6f35f605c6754cfead57cf8387639d3b4096c54f18f40c00000000ffffffff01327906000000000016001482074bdf6ce32b071dd120a17cf99cbc01ad3081022320d1f1955b1327167cb7ae3dc39d52c277be39d75737b9cb80514ce6e825fd8eeace8721c050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac00000000000", "input_index": 0, "valid": false, "comment": "Template hash mismatches: incorrect output script." }, { "spent_outputs": [ "33790600000000002251205331c80448b5eb2daad3567c98bc99664d14e0ea12bdf3be755429055d67756a", "22921000000000001976a914079ded3e3befdab0757fe0e8842aeffc0ff2160288ac" ], "spending_tx": "02000000000102c997a5e56e104102fa209c6a852dd90660a20b2d9c352423edce25857fcd370415000000002a000000169e1e83e930853391bc6f35f605c6754cfead57cf8387639d3b4096c54f18f40c00000000ffffffff01327906000000000016001482074bdf6ce32b071dd120a17cf99cbc01ad3080022320d1f1955b1327167cb7ae3dc39d52c277be39d75737b9cb80514ce6e825fd8eeace8721c050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac00000000000", "input_index": 0, "valid": false, "comment": "Template hash mismatches: incorrect sequence in spending input." }, { "spent_outputs": [ "33790600000000002251205331c80448b5eb2daad3567c98bc99664d14e0ea12bdf3be755429055d67756a", "22921000000000001976a914079ded3e3befdab0757fe0e8842aeffc0ff2160288ac" ], "spending_tx": "02000000000102c997a5e56e104102fa209c6a852dd90660a20b2d9c352423edce25857fcd37041500000000ffffffff169e1e83e930853391bc6f35f605c6754cfead57cf8387639d3b4096c54f18f40c000000002a00000001327906000000000016001482074bdf6ce32b071dd120a17cf99cbc01ad3080022320d1f1955b1327167cb7ae3dc39d52c277be39d75737b9cb80514ce6e825fd8eeace8721c050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac00000000000", "input_index": 0, "valid": false, "comment": "Template hash mismatches: incorrect sequence in another input." }, { "spent_outputs": [ "33790600000000002251205331c80448b5eb2daad3567c98bc99664d14e0ea12bdf3be755429055d67756a", "22921000000000001976a914079ded3e3befdab0757fe0e8842aeffc0ff2160288ac" ], "spending_tx": "02000000000102c997a5e56e104102fa209c6a852dd90660a20b2d9c352423edce25857fcd37041500000000ffffffff169e1e83e930853391bc6f35f605c6754cfead57cf8387639d3b4096c54f18f40c00000000ffffffff01327906000000000016001482074bdf6ce32b071dd120a17cf99cbc01ad3080032320d1f1955b1327167cb7ae3dc39d52c277be39d75737b9cb80514ce6e825fd8eeace8721c050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac00250000000000000", "input_index": 0, "valid": false, "comment": "Template hash mismatches: spending input contains annex but none was committed." }, { "spent_outputs": [ "33790600000000002251205331c80448b5eb2daad3567c98bc99664d14e0ea12bdf3be755429055d67756a", "22921000000000001976a914079ded3e3befdab0757fe0e8842aeffc0ff2160288ac" ], "spending_tx": "02000000000102c997a5e56e104102fa209c6a852dd90660a20b2d9c352423edce25857fcd37041500000000ffffffff169e1e83e930853391bc6f35f605c6754cfead57cf8387639d3b4096c54f18f40c00000000ffffffff01327906000000000016001482074bdf6ce32b071dd120a17cf99cbc01ad3080022320d1f1955b1327167cb7ae3dc39d52c277be39d75737b9cb80514ce6e825fd8eeace8721c050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac001065064756d6d7900000000", "input_index": 0, "valid": true, "comment": "Template hash matches with malleated annex for another input." }, { "spent_outputs": [ "33790600000000002251205331c80448b5eb2daad3567c98bc99664d14e0ea12bdf3be755429055d67756a", "22921000000000001976a914079ded3e3befdab0757fe0e8842aeffc0ff2160288ac" ], "spending_tx": "02000000000102c997a5e56e104102fa209c6a852dd90660a20b2d9c352423edce25857fcd37041500000000ffffffff169e1e83e930853391bc6f35f605c6754cfead57cf8387639d3b4096c54f18f40c0000000100ffffffff01327906000000000016001482074bdf6ce32b071dd120a17cf99cbc01ad3080022320d1f1955b1327167cb7ae3dc39d52c277be39d75737b9cb80514ce6e825fd8eeace8721c050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac00000000000", "input_index": 0, "valid": true, "comment": "Template hash matches with malleated scriptSig for another input." }, { "spent_outputs": [ "33790600000000002251205331c80448b5eb2daad3567c98bc99664d14e0ea12bdf3be755429055d67756a", "22921000000000001976a914079ded3e3befdab0757fe0e8842aeffc0ff2160288ac" ], "spending_tx": "0200000000010283e4f8a9d502ed0c419075c1abb5d56f878a2e9079e5612bfb76a2dc37d9c4272a00000000ffffffff169e1e83e930853391bc6f35f605c6754cfead57cf8387639d3b4096c54f18f40c00000000ffffffff01327906000000000016001482074bdf6ce32b071dd120a17cf99cbc01ad3080022320d1f1955b1327167cb7ae3dc39d52c277be39d75737b9cb80514ce6e825fd8eeace8721c050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac00000000000", "input_index": 0, "valid": true, "comment": "Template hash matches with malleated prevout for spending input." }, { "spent_outputs": [ "33790600000000002251205331c80448b5eb2daad3567c98bc99664d14e0ea12bdf3be755429055d67756a", "22921000000000001976a914079ded3e3befdab0757fe0e8842aeffc0ff2160288ac" ], "spending_tx": "02000000000102c997a5e56e104102fa209c6a852dd90660a20b2d9c352423edce25857fcd37041500000000ffffffff83e4f8a9d502ed0c419075c1abb5d56f878a2e9079e5612bfb76a2dc37d9c4272a00000000ffffffff01327906000000000016001482074bdf6ce32b071dd120a17cf99cbc01ad3080022320d1f1955b1327167cb7ae3dc39d52c277be39d75737b9cb80514ce6e825fd8eeace8721c050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac00000000000", "input_index": 0, "valid": true, "comment": "Template hash matches with malleated prevout for another input." }, { "spent_outputs": [ "34790600000000002251205331c80448b5eb2daad3567c98bc99664d14e0ea12bdf3be755429055d67756a", "22921000000000001976a914079ded3e3befdab0757fe0e8842aeffc0ff2160288ac" ], "spending_tx": "02000000000102c997a5e56e104102fa209c6a852dd90660a20b2d9c352423edce25857fcd37041500000000ffffffff169e1e83e930853391bc6f35f605c6754cfead57cf8387639d3b4096c54f18f40c00000000ffffffff01327906000000000016001482074bdf6ce32b071dd120a17cf99cbc01ad3080022320d1f1955b1327167cb7ae3dc39d52c277be39d75737b9cb80514ce6e825fd8eeace8721c050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac00000000000", "input_index": 0, "valid": true, "comment": "Template hash matches with malleated value for corresponding spent output." }, { "spent_outputs": [ "33790600000000002251205331c80448b5eb2daad3567c98bc99664d14e0ea12bdf3be755429055d67756a", "23921000000000001976a914079ded3e3befdab0757fe0e8842aeffc0ff2160288ac" ], "spending_tx": "02000000000102c997a5e56e104102fa209c6a852dd90660a20b2d9c352423edce25857fcd37041500000000ffffffff169e1e83e930853391bc6f35f605c6754cfead57cf8387639d3b4096c54f18f40c00000000ffffffff01327906000000000016001482074bdf6ce32b071dd120a17cf99cbc01ad3080022320d1f1955b1327167cb7ae3dc39d52c277be39d75737b9cb80514ce6e825fd8eeace8721c050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac00000000000", "input_index": 0, "valid": true, "comment": "Template hash matches with malleated value for other spent output." }, { "spent_outputs": [ "33790600000000002251205331c80448b5eb2daad3567c98bc99664d14e0ea12bdf3be755429055d67756a", "2292100000000000160014266a4832c001885db26e853ef1d1dde840f7dbaf" ], "spending_tx": "02000000000102c997a5e56e104102fa209c6a852dd90660a20b2d9c352423edce25857fcd37041500000000ffffffff169e1e83e930853391bc6f35f605c6754cfead57cf8387639d3b4096c54f18f40c00000000ffffffff01327906000000000016001482074bdf6ce32b071dd120a17cf99cbc01ad3080022320d1f1955b1327167cb7ae3dc39d52c277be39d75737b9cb80514ce6e825fd8eeace8721c050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac00000000000", "input_index": 0, "valid": true, "comment": "Template hash matches with malleated scriptpubkey for other spent output." }, { "spent_outputs": [ "337906000000000022512020f99a99681ccce328c592c92e0454b248e6ae65c2e97ce249da6612d0b6b980", "22921000000000001976a914079ded3e3befdab0757fe0e8842aeffc0ff2160288ac" ], "spending_tx": "02000000000102c997a5e56e104102fa209c6a852dd90660a20b2d9c352423edce25857fcd37041500000000ffffffff169e1e83e930853391bc6f35f605c6754cfead57cf8387639d3b4096c54f18f40c00000000ffffffff01327906000000000016001482074bdf6ce32b071dd120a17cf99cbc01ad30800223200000000000000000000000000000000000000000000000000000000000000000ce8721c050929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac00000000000", "input_index": 0, "valid": false, "comment": "Template hash mismatches: spending a script with a different committed hash." }, { "spent_outputs": [ "3379060000000000225120e498b9cc13e41d4b1d141989f2626f8de87162f2e97aa5c5dc818c85638b3015", "22921000000000001976a914079ded3e3befdab0757fe0e8842aeffc0ff2160288ac" ], "spending_tx": "02000000000102c997a5e56e104102fa209c6a852dd90660a20b2d9c352423edce25857fcd37041500000000ffffffff169e1e83e930853391bc6f35f605c6754cfead57cf8387639d3b4096c54f18f40c00000000ffffffff01327906000000000016001482074bdf6ce32b071dd120a17cf99cbc01ad308003232040ee92735bd9b32fc51d9b6df6be4dafc834cf383506dcb45a61151aeee3460cce8721c150929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac00550646174610000000000", "input_index": 0, "valid": true, "comment": "Template hash matches in the presence of an annex." }, { "spent_outputs": [ "3379060000000000225120e498b9cc13e41d4b1d141989f2626f8de87162f2e97aa5c5dc818c85638b3015", "22921000000000001976a914079ded3e3befdab0757fe0e8842aeffc0ff2160288ac" ], "spending_tx": "02000000000102c997a5e56e104102fa209c6a852dd90660a20b2d9c352423edce25857fcd37041500000000ffffffff169e1e83e930853391bc6f35f605c6754cfead57cf8387639d3b4096c54f18f40c00000000ffffffff01327906000000000016001482074bdf6ce32b071dd120a17cf99cbc01ad308003232040ee92735bd9b32fc51d9b6df6be4dafc834cf383506dcb45a61151aeee3460cce8721c150929b74c1a04954b78b4b6035e97a5e078a5a0f28ec96d547bfee9ace803ac005504a5045470000000000", "input_index": 0, "valid": false, "comment": "Template hash mismatches: spending with a different annex than that committed." } ] ================================================ FILE: bip-0446/script_assets_test.json ================================================ [ {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d719901000000ab0ab7f46a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d369000000003e44ecde02f5de320a0000000016001486053ceaa6b6ea601bdda3b6220dc75104485958580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a3387b50a0000", "prevouts": ["d8f103050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "fd89310500000000225120ff7caa3c95e4c5de622b8aa1c98fc7fd7f3e399b73404c84261ce5c6e9672a77"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_103", "final": true, "success": {"scriptSig": "", "witness": ["2d3f1623ff485c817f6d7cd7319c8ebc6244eec0a9a93a41cb0c5f521bb7b5f6", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["220d37b3720ee2c928452b7e4d502732a9caaa042604873e299350e97217767f7c1e5900ba825bbfe3ffe1615c964b952f4458b0df7212134b4056ccbdb85c81cd4a9c4b7c7f901bc9eb73cfa524259084466b568b27719afead1b45e5bead84319d733e5c738e", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cc9010000004894ac8fb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71de010000005b1623b202a5741d0b000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd243023d070000", "prevouts": ["dfd040050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "d294df050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_88", "final": true, "success": {"scriptSig": "", "witness": ["2e9bf51cd796559276a74a4cca1aa987a5d86710eb3e5b6df6af98704ac78208", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["764f2fc54b6b47d80806fb1018597762e35f2b272bcfb5a377b4d73de9b21d7be0ece7cc441e6ef39d16acaddba2581ff3ec845a7def94c94564a770fadc9bd3c05fcd6f3cdb752f0b9318276123d870f67c4c069fafa933", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "af5de68603636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5ba201000000a8974791636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b0f02000000146afc9b636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bd101000000d2c462e803ad34da0f000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338758020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88acc7988c2d", "prevouts": ["da77b7040000000017a914e5fa33516d725583dff8c561ad783a1a7296c80587", "9cf0b50500000000225120f429379794d9addc587a2a1fe5311faf96ad71c55796a74e587fce7f17630cae", "b3756f050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_95", "final": true, "success": {"scriptSig": "", "witness": ["695d6b4f4085bc36ef2f7bf2c61c8a06b65b4e7cd6f1f56a50b4f500b35dc188", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["256aa6b66cfcff19cb7538f2bbbd38b1f7aa24422328c852826e3bc68e2c2825cf8c464f8fe9cd782c116a6c0c03c40d48f061bbfddbbf408616b0d3a8901b9a3570af0198556d071784b0f35af72e495576ae546842dd765e6e5817c87d9a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "c7a2d4fa02b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71d300000000116a9bc16a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d36f000000003f86afc503fa9ae40a000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001600145e89b76f270f5a3384e042389be8f4c1040249265802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e05edbd41", "prevouts": ["8835be040000000022512040d8f5c0f5f206018f3c15ddc74045cab34f3b4aa686be17bf6aeab8429e74cc", "d22228060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_14", "success": {"scriptSig": "", "witness": ["2088d1386c1a2ae569bf533c2518a1bd3beb1a74c99fa204f76e6a61a8b790b3", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50ae11502f6e98873243f234a365ec"]}, "failure": {"scriptSig": "", "witness": ["b656a865509f8a67fdcba7ff89b53014ef5e6f1df37733ce11bbafda2cb69876", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50ae11502f6e98873243f234a365ec"]}}, {"tx": "1cfd2c77026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3c30100000071929bce02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4904010000002911edf303af31de09000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac58020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac1054423c", "prevouts": ["9ee09a040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "d4574505000000002251201e8533af3997eb750f70f7bca0d9e55cfcc1e275445a11f01aeb3f7e60789bbf"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_81", "final": true, "success": {"scriptSig": "", "witness": ["1463bce763d53f15bb2d59f0c2afa7a175dd43bdeb9b4a02c65e12c969552048", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["a7d4470bfe6f73172d915f753f5e7f2d8e64a653feb8d951e0fd94dec10baca9dc05afe1f256fba58297d0874ae9562a20d8850b4f3d54e802168ebbce0168e67d5a903b847f15f0b8a7b5a728be566bc8", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "146b33ae02636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b11000000004b1e55c902c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf494602000000dfdbcc8c048dc5390c00000000160014c327e70d62d692d5959c72b3411fee2ca31c546b580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338758020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac580200000000000016001486053ceaa6b6ea601bdda3b6220dc7510448595876080000", "prevouts": ["7412f4050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "715a470600000000225120a27a4722800bee09af9967ce66bb095129c320e4466c12883ec2f3b9e1ebfe58"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_194", "final": true, "success": {"scriptSig": "", "witness": ["90a815f250dff4ed14b37341457d441b1f61ec90e482020d87fd048b3c14b371", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["ae7fe3ba5176231dde37b0d4f1e91153ebf40569f06b9652b30b41d81d71ccb893df2d499855a950b4a418308501d713a054114a796cbde611c05834a4e677840ff532e34386ddeca836ec271cb0a1a0f19c624a6e7ae25b85f65df6896da10570ae9622ba0ad8e31960f92cc77c8691f2e8dd30a2811fb90e42cadf49bff950fb943c8d263f3981b8a381c8ef9d4680e209330d075e1bf47582a27bbc28843608a47dad38b2d401cf2d3e31b056ebd33957ec87fba8a7e111cafd8f0425eca8044c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d718600000000ab23beaedf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c59000000008b36c5b8030dcfb70a000000001600145e89b76f270f5a3384e042389be8f4c1040249265802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b5802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546bb3050000", "prevouts": ["bb3e6a050000000022512064b1c1e960613f5f1d3b7809a0fb69595b8cc7457e1424d0bec1a96b585dbd58", "df8a50050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_211", "final": true, "success": {"scriptSig": "", "witness": ["998ba34624123683415103a0c7844040e18b4a699b3ec1754686213b0b527fd8", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["c1706fc7503d3c59cb4d83f9aa781fd37df409c9f71c2b195f318453799ed1c8cb569ee49bf197b3525b3473b94d17bc1d3f7cb6ff1cf55667bd0954561a3d1d9ba36c4987404d47827d974396a22fefcc9583e2d49bce4012d39238f9894e0d6193b2a434d2bfb0ed1fd7a51dcecf7b44a0cd004366db1b6f7cd27d4b2bc8f61b972ffa45c4088a89a369bf43434203b098af56c6d7c830b434db07bbd19ffef588b0db7062ea1d8b24c92d11ee40378a379cf1eb3362618182175cdd0a7c92da070eee66592fc07cf5317a5fe131b0b9f48e", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf496c01000000fb699dc4df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5ca0010000009ef4efeb041179fd0a0000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb875802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b5802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac5a432a2c", "prevouts": ["42666e0500000000225120e64b355eabd4f3447aebfdf196a8649a33a20b9138d95c3e22e71d21503e680f", "e4af90050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_10", "success": {"scriptSig": "", "witness": ["3067c1066cd9f7be32fab535e33788f2bd0219ce844150c6bb6c97b73a7c36ba", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "5073ae2af8a5507ef3f09a"]}, "failure": {"scriptSig": "", "witness": ["ba1a05e0feae86283b60b94a734b1806b9b2c3c5ce28977457d187e79eb750f6", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "5073ae2af8a5507ef3f09a"]}}, {"tx": "010000000302c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49c5010000001ffcc77302c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4915000000007b0b940d02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf496b0100000080e48f2202e130bb0e000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd243028ad9502b", "prevouts": ["61acea04000000002251204eb54cbb95a134c49572fc3a96049bd15e850a02adae05f5846c4c7ab50c86e1", "f985cc040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "10d6060500000000225120d397d55c183334539c6df593b40e2f80025f07ff215fbd9251fdf1d4186d09a6"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_234", "final": true, "success": {"scriptSig": "", "witness": ["dbcc25fafef50065ba5ee3f08ff9f570eb008109db0ad9e0910fe6b5dcdad833", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["de3bae4b944ee9fcd4f604b371b66195107599e33bb522175eb9e07303bf6201869f37842c2c7613dbb30c0e262016a38f0c9a8ed1969d7fddf638813fe6946d73f03a21e4f9e5e046f93c74b92afa03f0b5190390daef0090d695fc08401cd2bbeb21afba359f596cd1a41e6cd9b90ce7a342a3601cd3bf09b30856f13ded8e65328b6be341685ff184875a50e43aa405e01d4c734e8c047421a9a7ef33cd4136f5846f46e595093d4916f4600a18b9bc7f879ca57543f737d83e6f02957ec6b58b5335c9095d8761f8b0a970141ca782c0e21a2f63aed036a670a7c77e41315512a673e0750d40d8d4", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7149010000007ca068e46a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d31a0000000078f50794048f16030b000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd2430258020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88acc4040000", "prevouts": ["cb23f805000000002251205f359b0c56fb94cc824c7891579f1c80f5cfbafb82628b3b456b347920082c7c", "36d00d050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_179", "final": true, "success": {"scriptSig": "", "witness": ["d85f7bcee158e3e9b452e643197f2a3b1d4406316d7a7f1a54b18d19ff66f876", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["25215a526e004a15da3aeb0579f9ea41025ac518a98dabdfd1242f3b467b8f2c4087885c63c5dbbfd9c42155aa9fd2646d44608f9646cc0dbe7750646d3bde5e1211de72923cbb34bdb07b81b20e226b563457342622791102542ac402140a05b93cf3f0845f06fbefa11af24967b625b285c3dceee85bb468334e49cc8e99301b4dcb9264e6f81473a464b7ae46151da4e5c680b5690af557243b01620894b8d369ebac497cc78733e5a0421eada93ae2afcd", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000003df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c56010000008dc7fca86a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d35e00000000d08fd896df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cc1000000009dd2d4ab028183dc0f000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a33876806864d", "prevouts": ["6ce496050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "c8940f050000000022512096b220ba74194f15ad18891a89aba0ba9386ff61ed54968473e1fb2f0b2df3ca", "201e380500000000225120bdbec184cec529a96e8fbec27a5917fc2abf7c3a2afbb544ab93eef95d1a60cc"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_20", "success": {"scriptSig": "", "witness": ["80f326b52bdfb888de112145573ba6ee86356a2edf25e689ba10ee4a05df6576", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50d54422b88ae42da8d33f4e531b39648b8e814152"]}, "failure": {"scriptSig": "", "witness": ["5d4a280ee1b90d76d09321858a01dba63cbeafe5358ca3d7ab9cc2166b8bc421", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50d54422b88ae42da8d33f4e531b39648b8e814152"]}}, {"tx": "4455742903df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c02020000002541828c6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3c2000000008f5b25f16a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d34000000000a9e23bc50398607411000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338758020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac2d0b0000", "prevouts": ["f57b98050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "da4c06060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "3792d8050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_183", "final": true, "success": {"scriptSig": "", "witness": ["af20713ee2424203e3abcdb14bbe5b612296a71f8e66926006e8e4311f778f31", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["6a6306ff956cbca637da669ecbca69eb8c590141f8f00a7305aae1aa028e06b5ce6ecdf68b5538ab00f27616c3256594fb71657ef5b702e82de370121b5dafb3ae649fe1f59c24a03730d61ad2ba4dbb4f97966fd454dc2fe5ebcf09c8f827160c1122923071c48366d50dce04fe697ebf4f2c520d50b7b41c3e6d448eeff99e5b9c7ddbb8edb434b0a4d89f48456a86eb11dc9d48e72230fbbb80c6e6c5475a17432f253ac38f77ce5fd9b606fd03b6d7c0b77ecf60a3", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b2201000000cef20da7636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b8300000000ed5e8ade0310cd880a000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac5802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b58020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac3b050000", "prevouts": ["4a0f530500000000225120d066dac2bb55679bd17f2e4b852d68e6819bacc38abd54d0260cf561412a308f", "85a838050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_25", "final": true, "success": {"scriptSig": "", "witness": ["f13e8bb776b7da1986a8c640f4d046fb732c8333e96ff67cb3516e5bdea49e5e", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["c677c2672d70ebafeeefc5b7ad46a9ef1963adbf962b1975e93e61d4bdf7f8d7", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "c9f87b870202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49d40000000056080e80df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c45000000008063baca032e4d9d0b0000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb875802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338767030000", "prevouts": ["106dea050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "84d1b40500000000165414d8103542fd26eef79006879e481ff31a67ad980b"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_160", "final": true, "success": {"scriptSig": "", "witness": ["424893816165683343986d42a53ebab82265174625e31ffb03a015130d6adbd7", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["e52c13c5e2f04814d423cd750ece5c8d09e270355dd655cc9b9ff18f277348d36b3aa0e5ca38f0e3f71bbe7ff7118c7ffe27508873a916e90707f3c70186f38a955505ba3e0623debaa6792e8535149bf865087356c68a996b16e8b3b5dace528d12ddb40f8371014483aacb90ac680d2573de65a209461cc6414181f72450d1ae2b028d314330f6d8c0dc6847a2942afc659b47a1057c93d81ebc4d32528ab2", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "01000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d32500000000c400b8226a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d383010000002503973104f7e0520b000000001600145e89b76f270f5a3384e042389be8f4c10402492658020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd24302260ca221", "prevouts": ["37486605000000002251209923cdad2c6ca4475cc3ce9e6c10397674806f145c15b1a6b07210a827662526", "ae61ef050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_40", "final": true, "success": {"scriptSig": "", "witness": ["9d0670006b759e0cab09fec57b1cd4ba1d11c148f33492d86d5f7906fb6f05c0", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["09047084a8c5b3053dcdf4151a1d009ff25fb48c56c1dadc5b055a10750c46e235b00e9e471f4ca2", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5caf010000002a7c9fa202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49e50100000081b798cc04590d650b000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac5802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e9957ba35", "prevouts": ["651e5d050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "277909060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_175", "final": true, "success": {"scriptSig": "", "witness": ["3764130d6502ebe679da57a591b4e95257be4df8a09dc9f083cbff194a0903f8", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["b89fa52275f21a8e2ce304632b463c5df133599fd0324f168ed7a661a0d278b54afccc2c9a27fc9bb1855a97e705d8bfa58aa4e9740a5fc62d7c30151a2a405ee6a0545dc392c6650620c6bdaa7385bee99904f5877d22ded5af367ae239f86fe9b0b747ebed9de9d3b8b56aaeb97fc52a4a1087e8622a4c416f980ac9f46a35ce07aceae6d8fc2385d071f10d1c1c294a89815465a9c541b1386b31b6c9a5f1c91a2e575f839d82cdf3f8f7734532", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b6300000000ea0c1d4c636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b2c00000000a036765004ac635d0a000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a33872e060000", "prevouts": ["64e87b050000000017a9149aea464242deb8c8ea8147e6a7293b0beed1005e87", "c708e4040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_9", "success": {"scriptSig": "", "witness": ["3e6067cc6f480fac972966fe4bb7966ad0e5c882a7843dcdb89caf1f33470773", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "505fd5a262d6d305f81e"]}, "failure": {"scriptSig": "", "witness": ["c11018d05b0bc67805a9d761212f33caae5d7dfd1a4e6c14648e9904ab278eb9", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "505fd5a262d6d305f81e"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7189010000002e93f4b3636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bd500000000dd46f6c60337965b0a000000001600145e89b76f270f5a3384e042389be8f4c104024926580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208758020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888acaa080000", "prevouts": ["965fbe050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "073e9f040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_116", "final": true, "success": {"scriptSig": "", "witness": ["696c4fa84d23188e294cdf0b593e609032f2fa529e8689cd172f380dbea64ffc", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["f11eb009058fb687978b6fe6e2df76501005146be6ec9476b9b2e6ea592f41745f14efde0cb188d64314055be5eb015230185f4798b1eb3c68c691c7916a0c845266fc28c64de8c2c3f19cb74b5f22589890c610b58da8f26087272c1c0a2b9a5987781ea2fc44bf7f13be63686cb9faf2ec244b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c1502000000a6eaccbc02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf491f020000007b8beaf203563cac0b0000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208758020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac2a050000", "prevouts": ["28a4e9050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "bfc4c4050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_199", "final": true, "success": {"scriptSig": "", "witness": ["125afa1dff382d594d8d759a5ed15dbdc0dff7b1c0ef8e7c8982ab1f34991e20", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["70d112ba1f38a669ba0205d6d6096d3a5f52a07e446b20f6a6eb1a9f97bd583622661d9020305a58d9a4711a55d2ec368ead9752bc292b3b08480bdd535d1660747dbfc568621b07140605e3508b76af410baa5e14daf0b0bab2a4667cbc87d5a5075c4f3bf4f2efa38b009c1f91cfcfda9b6a4af6e7600ac846ce4e4f79ded739debedf805981779436e4f3e112683cee5a8f1e770932db08d08e0316ef34d8a3bca86250f4dbeb2b17912b4d360fcf58ce05b6a892199acf0bb067509a0cd1a98048ee44e68d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000003df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cd2010000001c2f358bb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d714c010000008a8b82fb02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4955020000004e511eea03cb018a110000000016001486053ceaa6b6ea601bdda3b6220dc7510448595858020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac0b030000", "prevouts": ["3d4260050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "3da517060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "622814060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_150", "final": true, "success": {"scriptSig": "", "witness": ["2b32d4b5121a9d64bd182e8426726fc89ee4c69cec65d576f650a585ee5ef99f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["46e562815d7ba38c29c6b68bffe1bed39c251d8933159a87d416264babd27b1a1c75ab09272ecc0b5ab71cd1e517687b07410f564d1c39b891b9705badbf6f1cc6e69e0c1d580d12aef4248012308e1ff9064f9477d31e9b5bc6af06f70d152939f066e24e3e5124c2379ae205e9c92f04991eec2098d4de9aee83e0d975426cebec6e7d1773e1b728375c54d5390633f6f6f3120e19", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d710e01000000362d8697df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5ca300000000de7fa7d1025d7ff809000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd2430215ef8129", "prevouts": ["38c3b30400000000225120dd05ddfa12186922f66a8ec41dca157ada848c6ac616648cd66825a343daf907", "91b046050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_13", "success": {"scriptSig": "", "witness": ["4b638ad11f4d0ecb71a5bba7bc00df5321c1b8fdc2d34a66aa3b70d05b1155a5", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50519b773a55456c9650f5565801"]}, "failure": {"scriptSig": "", "witness": ["37c67d1a23ef363afeb50c262df8138761f3c77d77d0872195a76150ee522142", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50519b773a55456c9650f5565801"]}}, {"tx": "0100000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cae00000000bd0246eadf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5ca100000000d74c01fa012748a2070000000017a9144657010e5cf55af6acb627784c227caeaa0f0a33878a490a64", "prevouts": ["c42bc4040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "0fc6d804000000002251208812e5d1987e04a51e27107293068a623f4cf30b5d7b9e68068fec710bc8bf01"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_105", "final": true, "success": {"scriptSig": "", "witness": ["961e1796cf80213f759df5e81f3c81b6699ce61a18d9fa6236d85c06127f40da", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["b4da56b9cc7466264af2bda2b6088c54686b0e1846706fb75f2ace1d71e76093a0984d28ae8efaddb19982e004dd4e491f0377d0b160b20bd993189a3752e1181b2102a58aa48d566e62bf152c544871a171011ebf8086bf994aac3db7428a26b85b95500dffe11656", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c7b0100000085c6c9ca636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bc9010000005f64d9f002ddf2280a0000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338758020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac447ce034", "prevouts": ["8dfedb040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "ef6c4f050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_30", "success": {"scriptSig": "", "witness": ["9a03bce3f176a558c080721920b8fc9483cbaa7f362869711303ed32fe830bec", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50b54128744eed24cbe31fe0c373473d30d790265a473d91068240f752e06b"]}, "failure": {"scriptSig": "", "witness": ["d48b05c0b5a3f559c135688597c0571a0b93204a3f2d503ddc9044f0c719d864", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50b54128744eed24cbe31fe0c373473d30d790265a473d91068240f752e06b"]}}, {"tx": "d056ec970302c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf491201000000cbafaecc02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49c7010000009b0939a06a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d34d02000000a49002b801c28ee801000000001976a9141c428f4958c47293549411153bb54f9c0588618f88acef050000", "prevouts": ["71e8450500000000225120ed113a17b3833bd967ab54798fcf726404cb40d713297cf1bb9b5fa81815b27a", "51b502050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "376658050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_241", "final": true, "success": {"scriptSig": "", "witness": ["2c21fd489e7116ac245f3c9d56116a09ea961b6036dccae615632dc0e3b0ef62", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["1321a7d89fa6aaad779f8fbb65892b14f3c65dc9154186914e38f96e917959cc61f1f4f3c2c48f4ba1ede926c17b188372af38ed63f537e636b42804b274abdb0043c543f1831d1d61fe81b17c5c2c42f96bb0b296c8e1457cf0e5c349231bb488de8de919b995ba2231b8d426bcbf892a45f560311b11f397735bcd851e4404b92ed0c2a1e90463ee1379d46a1e585278d50ca3a7817b8464faa4b005abe8cea354df239a8ba8c4341ee05a1525b4bdf5b6371ecd349fd9a78de9328b5a4339b0e6d67e200e9814613bd2554603ce0af843b395eca0e7dca9cc07974b9a2e2acaeba365d83d6e9b06f4a9a6be2cd09cad", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "9e51912d02636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bd201000000459a83e16a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d317000000009981fce701520c80050000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb875c010000", "prevouts": ["5f989d050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "c641fa050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_58", "final": true, "success": {"scriptSig": "", "witness": ["186b4df73fcd334b2b3b015ed049d49bed10d6d275f4f5e05ab167418281afbb", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["c46a312d11779e15da5e65f66ff23ade29c0c2da92253e48d8bc817decad3500fcd9fb2ac613627363f780caa6cb8d0725bc8cf3599ce790b690", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000302c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49af01000000051c7ed9b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d715200000000771a4eb102c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49890100000020d04f9b01e7abad01000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac39010000", "prevouts": ["715efa040000000017a91490068009b72ed1852bda24410e83deaccf2c635487", "c2dc51050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "70dff50500000000225120b97b125092319d98b0ad739d9949a21e0745e3bbed230b66a8fb230706ba1962"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_139", "final": true, "success": {"scriptSig": "", "witness": ["1b891a7028d26546d6126b9b4411397a5d713ace261630ddac15f7fecf11294a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["055ce625c7dfeaa4e4cad1043ed71766b6c120a73d1a865cae1ef3d8c2de8f5238fc94f7b8b6784104ef5bfd67922d0973d9eae04539efc462240d22a9b28ff1534f828a8d69eeec0f1db5011f6937ff087635b556e98446c2f0f4248e89ab86f0a0b1ffd3845c3352a486ea1567483521066a41eca04ac64348e0c3b37f79e9ee862a4e4131321d77908e", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4911000000009e65c08e6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d34e01000000de0503fd02de4e1a0b000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac293ba724", "prevouts": ["6bc82f060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "3d1cec0400000000225120801f5e577a4c45dae865648a93d9d1e894a3e982d52a2769a193af4e39416b69"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_163", "final": true, "success": {"scriptSig": "", "witness": ["be4c61aef9e50eda65ca44b16d4ac7bf5c644a3d236dcd27340d0e9916f66cd2", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["1b3949143f8db13934b8a0a687242236df39d84e1218b1168f37de7e03311e68ea2ec06826803a68ffbac98a2ee9f8e4ab44c2ebdabedb5ed5bcc584f48e6d7a6c914f7fc389fcd157493095853552524f9ed3764d4c1dd86dce80607dcc07eb9bcf420f54ab1baa2a0db788485bcf54ba86ff21d5450c7edc18cd084dda279e7025f65e27f7f9f493d706f9ef2e19135b24c14d90cc511c80f47827d9d23661750bfd", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "235fa326026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d36801000000f80920f06a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d30e010000006e054aa6047ff5f90a0000000017a9144657010e5cf55af6acb627784c227caeaa0f0a3387580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb87580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec2087580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb874333e22a", "prevouts": ["2994f0040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "0e060b060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_29", "success": {"scriptSig": "", "witness": ["d1084a17e1c1844e4445e9b026dcd625da2c8ea555c4999d7a60329e67619c27", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50c3f8e7e1a598180d98ba271d49b87828b3839fe64c2070b8a90a091cd4"]}, "failure": {"scriptSig": "", "witness": ["eede4c112a814873fda16de40bda5984bf83cfe398ba04f1319a51e0b19c71f1", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50c3f8e7e1a598180d98ba271d49b87828b3839fe64c2070b8a90a091cd4"]}}, {"tx": "bbfd8d490102c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf496800000000bec107dd0441f41806000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac5802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac02a9294b", "prevouts": ["10e11b060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_18", "final": true, "success": {"scriptSig": "", "witness": ["4266cbcac6ee9d611fa107df05a31b3ab32cbf9508f0784e74a2a09ae7507689", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["3fa7c260a354e354f5434cb62d1fe520b18974ea65c41af4776e1240a5c1c39e", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "010000000302c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4963010000001a2f331c6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d325020000008886e39d636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b0e00000000925623bd04fe2abb10000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac58020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a3387ba78c254", "prevouts": ["1d033c0500000000225120fa5af02130d06bc65c351afc1132a61263ff845e0d7aa1e12d4b5c2a28ab6e1b", "d77880050000000017a914cb139519d2c8d97facc59e25fc2270e85eb5456087", "6f4500060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_2", "success": {"scriptSig": "", "witness": ["66d882aedd7bd5eead1c34f83957eb05ba4fd71146653ed81aa20c719356c7b3", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50eea8"]}, "failure": {"scriptSig": "", "witness": ["9177cf711be3aba690526e6ba3649ec83978f89a5b70fae082f0460c76b29138", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50eea8"]}}, {"tx": "e3f55165026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3dd00000000ae6e519402c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49e901000000e076d5c603d2f7d60a000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb87a91f7029", "prevouts": ["d68c82050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "bba556050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_29", "final": true, "success": {"scriptSig": "", "witness": ["f1d7c67375712a2c1ec7e0a5507cdfc19cd7e88b45d247cac465a678ac44f03f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["f88fe7e4dc5a2b5f85bf06603b765568455db07b92cd9b9a20605f803b5497a0", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "02000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d38600000000a8e649a502c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4967010000006e687aa0047bcf890b0000000016001486053ceaa6b6ea601bdda3b6220dc7510448595858020000000000001600145e89b76f270f5a3384e042389be8f4c104024926580200000000000016001486053ceaa6b6ea601bdda3b6220dc7510448595858020000000000001600140276cd59f2bc98ad777ccf7057f574395bd24302d5bd2f2e", "prevouts": ["9ae8cc050000000022512025e72e5a605b9996c7e6154664b2db9bdc28a01d2e1252c28425febc3356b440", "0870be050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_28", "success": {"scriptSig": "", "witness": ["6cc1cc99442d69b1df3debc2f91895bd1e8fe05b8389f4a6c1e14dd719ad81ff", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "5061666d7d2e52c380734a8c9e2dc4675dcfc7abd7027494cb06247e4b"]}, "failure": {"scriptSig": "", "witness": ["5002d08bbe563dfa97f936135f1107a5a555690b6b88bdb5b65de19127199304", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "5061666d7d2e52c380734a8c9e2dc4675dcfc7abd7027494cb06247e4b"]}}, {"tx": "061df8d902636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bac0100000064d413f36a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d30002000000b4df97ee04e84cc909000000001600145e89b76f270f5a3384e042389be8f4c10402492658020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888acee000000", "prevouts": ["586d1a0500000000225120ecfbf93602118ee1ca30a1b5da0d6a8a8aaea082d7b6e1e00e7147de95da112e", "0555b1040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_23", "final": true, "success": {"scriptSig": "", "witness": ["6ed42c50d760f6ec7d473a982d18febfe2502e378076ef3a3ac44014d421c385", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["d40061eedb52d93aad22d94fec530d8434df7cc3e9a1a4", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5caa00000000e3166d6a6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3470000000009ebfe3302a061440b000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac58020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac6f040000", "prevouts": ["0341a5050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "1bc6a00500000000165614d8103542fd26eef79006879e481ff31a67ad980b"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_54", "final": true, "success": {"scriptSig": "", "witness": ["04b8ddc010ead7121c97c3ca8886218763ca598380eb09af33c973549af391a7", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["ceef4f8943942bf4b32f17c97e801f7d7f7b2cf06abba28ff35161af5426989d0dbf4a8bd24fd93b11d7437e2474e4c69c7f8e9a7a6f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "be123f8d0202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49ce0100000053b693e3636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b67020000008ec1c89503cce1570a000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac58020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac6119ce4f", "prevouts": ["d5de2f0500000000225120b3b9297d2d665ffffdaa838b9d4b68fb2335ee4357a66164af0e593ba4fd5b39", "593a2a050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_227", "final": true, "success": {"scriptSig": "", "witness": ["0874b45a4120c231209507c55c84123717ad3c891e61cfa3405287a963783c83", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["75c15055823625893631529f7a6ebac2d35f4b3147a35778ef2410ed9e174b524d4c7015a63372dad936f2d9e42c368ab538c3072cbccbf08c46bb7ae1c0cbd4322ecec8fc003852560b6db12f1624edd7302766332bc20bf0dcfc7fa5b7c2f774a949ae08ac288dbca3d36fa8c7f80ab55c2b66e5e7b0a4aa9d34c7756b241b4422b4e3c012cf481fee93ebc06c89499866eaff13235198f059093b09ac72f0a520bb61aecfbdb57ee4ede04b53ece68ca3518992b7f8967a8c941050b195d5f3a5586dfbdf9b4ce09cab7f2aa1cd4f261eb7b9123e79c2b70168c1dc53ca7b195859", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bf10100000014de9cdb6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d38000000000307a9a8e026693270b0000000016001486053ceaa6b6ea601bdda3b6220dc7510448595858020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88acfff8af66", "prevouts": ["cfc2b3050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "8b7976050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_11", "success": {"scriptSig": "", "witness": ["1091c5da7058b36e22affe13e163293b3e787bd6701af27bb4bd6e8d0f366a70", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50625dfa176cdc1b6644602b"]}, "failure": {"scriptSig": "", "witness": ["f88fcdf86654625bd91ada7e21028b35f7757a3296b137f65479dd08fa476dd0", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50625dfa176cdc1b6644602b"]}}, {"tx": "a775e34803df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c9c01000000172058b102c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49c2000000003a312ff0b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d712000000000077da6a00153f37401000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ace8090000", "prevouts": ["31f676050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "43827a050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "989aac0500000000225120fd63067374922077e29b191dd6d9bde947ed35790eeacbe1ea402d9d8e21fda5"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_5", "success": {"scriptSig": "", "witness": ["f3dce1bce209ec495cc5e0673be36b05edde9859670912fb0a7ec75702c3669c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "5071a55fae3c"]}, "failure": {"scriptSig": "", "witness": ["6baecc3d7837d6bfb713bcb9a4cc9036b09f8c2a3cc12625d1426c87c2569923", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "5071a55fae3c"]}}, {"tx": "010000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf492f000000001cbe1681df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c2801000000588e3108042e566d0b0000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb8758020000000000001600140276cd59f2bc98ad777ccf7057f574395bd2430258020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac5802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b967ec564", "prevouts": ["9585510500000000225120964da72986c43bb07598262123c0241d3f7980354e82105a23845cc4451ddcb7", "201c1e060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_16", "final": true, "success": {"scriptSig": "", "witness": ["4cc1ef253ee7bc17aa1a0bdbe0d9703e9031d56ec836d0d306e3af9e8d1a0e7b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["e10e49a853500f25fbdbc7f6df3397fb", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c0801000000b1deb87adf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c4b01000000b1c6184102f8951c0a000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac58020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88acc68c4e48", "prevouts": ["62570b050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "6cc613050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_107", "final": true, "success": {"scriptSig": "", "witness": ["214bf5d606699f0931494a13cec294eff124b97158ac17af23ebebe2e83b3b58", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["65ae40c5d9b3cf59743ed3f26683ecd33a2e348379415dccc7308997100642aad7042e1ac6262ae799dbb97c48ed29e20996aca9cfd44ef54a43454e1ab9f47cc371eac163fd4233c3d2e69467c80d0ef18b8951bedfa1e7ff20cfe07d5d9b099c2e1ae8b1c3701737bb7d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "e8dc474702df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cb301000000f2d3a9bf02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49fd00000000d6af65db04709ad40b0000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb8758020000000000001600145e89b76f270f5a3384e042389be8f4c10402492658020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac58020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac2a8fab67", "prevouts": ["94969e050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "e2e238060000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_180", "final": true, "success": {"scriptSig": "", "witness": ["54e82a9922a1b55610b6161bb774be0504389a5b81fb87db382468ac878107db", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["556701422e7e5e381a4093b27248537fe81c9bc40fe699cc9145a8980c085eba702a87356fe2323502978e0511f4bd7cb89462615f2bb5e979a38c66038146f91a5917882b6b4797318fd3139d3f0d1145ee0d8d9e21064a28c3ed6fd069a8f5e535730ffb85cec976de13bbeebce0e8f33e6663feca046e11546fcd8ff2c1f76426b83db8fcb6e2699077c12f05b1390bb1e271be28a248b29c6e6fdbee2e39eb728148c237a67c0337828298cdf4853b952f4f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "3224e2fa0202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf491d020000007fd8ebbb636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bf600000000668b8aee01398a4303000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac07040000", "prevouts": ["6617720500000000225120b3b9297d2d665ffffdaa838b9d4b68fb2335ee4357a66164af0e593ba4fd5b39", "5351e9040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_138", "final": true, "success": {"scriptSig": "", "witness": ["94c55608a7ee9225bb71169dd0858b05aecee8ee7d1f11153acd3ed940314df9", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["c7757d780773c016eb58476aa5bfd4875cbdc2c98a06589d93bb01fb928865a153348d486b7373da132cd621930a107f8626540726c0971051c44c187d69409bb26b05db02a67a37a0ed3da9488392bd7aa6c4f28dd3034f038b9a369da9d7ab638c9985c20719191abcc7b8bf683ef1e024007278803aed0195be5aec961547b3e05d0d2cb008873e54", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71130100000023635edf02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49cd00000000faf29aac021e18f609000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac580200000000000016001486053ceaa6b6ea601bdda3b6220dc7510448595823030000", "prevouts": ["589748050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "cf54af040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_182", "final": true, "success": {"scriptSig": "", "witness": ["356c5aaf56ad34c9e92534f16033e768d0bfcdf2820c7d8984e95bf25b780218", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["f1c2f63c96989a9584ef6e4fcc4b499f0c892adb2d591ba08bfcc5680f000676a9fcb894195aa75805cc02999b1367c04de07074f077afefb745cae9fbd01a7ca3c68b1ac9779c03372c72c63821696380207d38f25814e54ccebed2c8265dce5b1e3d4942869a836532bfaefd476ff05c71daa9ad747e2fd258c071f71cf1f5b50ffb0b89b983a3811990075dc99160698b425dd09dd384323960866ee3de5c6c6f89cda682358521501648c87a88a160bcee53b591", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "a2576121026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3240100000011ec96f8636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b1400000000887627e6036c045e0a0000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb8758020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88acff050000", "prevouts": ["4f14850500000000225120131ec57935be51afe63724462a66e4bcbbe32b759e6ab53c555f882f6e8a5085", "31ebdb040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_208", "final": true, "success": {"scriptSig": "", "witness": ["693d908fb49144f750e1f0a256615bb755d7fb3c37e0fafeef65e50dff87146b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["a7d71365655de0c2ffb6ecc204d550823acfa4d75550b195b1aca91b5b34f8aff0a6e5c835e8f86282c15c4160f3e1bb6a226241935a371a25f53ab0f3cb739ff43685d35d540d23f606aa79f5ddf00172955d202a15ae7261d86d5cc92512dc67a6fb7e85d283e5d905c2ef5bd1282ba848bcce128b59029865358d960477575dda5efb7770f5e26623417b6b567de55d3dede13c946d87d39aa539a84728faed8d3ff5514cca7496a38669c3e3ca283a51464c96268dd21a800da937aa95e154354b4ff9e919fae5dd44acdabc318e", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "70215f950202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49e3010000007d9707cd02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49b0010000009d585eaf01cd1aba09000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88acde671339", "prevouts": ["15dc6905000000002251208dffa0b556e6ff04f29cf85757353ade0336c5b55e04b6a17fa1edf30309e77f", "b429ba050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_242", "final": true, "success": {"scriptSig": "", "witness": ["beecd3e94539318296bc74d7f900b9b9bb8aac6b9900cc2abc206d0236a51106", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["0b7c45ba6e032336373747d352d882b20b661ab6b7f7fc8f593c9b35987c3b3a8080c86e29b3d37609f934a507ed38a1de7164081fc91f1b18e7ada51b0b77022957979fb4ca7a5a39a86c1ec2d63217c34735c2977dd3dc18be0fa3d61ff949e46465d5995959cae5af14c21e76aa0fcb7e39c48a3a7b9975d0a5a6c80bd33fca40029eb15fe8522c67ca7516db8c08003bab14e4fc2c095d1cac1d9964b30faf3eabd77466c6d74559479c9be346a4d79b412a1fd9435c66e1ca5756fe606a2bd4be96b570e7d8cd32d43d3ffd25dd6855f8087f73bad48226b854d7890416d302c07722496d9ec9195205815f933fa761", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "02000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d30700000000e4e600e3636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bb0000000000c2e3ee0033ee2740a00000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001600145e89b76f270f5a3384e042389be8f4c1040249265802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92edb0b0000", "prevouts": ["86016805000000002251203b46a920157019a3083083735fcf4ed1fa9d5fcdd7c824b73cfee716c3773642", "ed750f050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_4", "final": true, "success": {"scriptSig": "", "witness": ["5f0763712bb3c873181ccd4b42cac45ce0aa35f2981e4d9ba4a40f99ae6f2d2b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["3b0e8a62997ed0301f9591c4b24aed8011e356358c7e13374d709cc46dcea856", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49e7000000000f1a73d902c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49e001000000adf5c09f0162ef9c000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338720080000", "prevouts": ["70513b050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "3193bb0400000000225120444577651e37fdb7a210d2cde3a2cade95ffda3c149246dba0d617bb4880d3ba"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_21", "success": {"scriptSig": "", "witness": ["596d3538f3d2e700bfb3d0b82033f635c07d81a0d399c8c5e269e3b8f1fdd8a6", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "509c27d559f1d2a8da05e65ffce80325b16657a579eb"]}, "failure": {"scriptSig": "", "witness": ["a378970e9e02dc6ba92e08cf77f97eca06609db04c7ccb0abc34b3d65fc7266c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "509c27d559f1d2a8da05e65ffce80325b16657a579eb"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71530100000061375cfbb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71d4000000002eec0cb804b05acd0a000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb8758020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338716000000", "prevouts": ["44eb98050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "4718360500000000225120cf45838d4bd4f9180dce927e5a04daa9c15358f954699434c8bca00bb5cbd720"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_26", "final": true, "success": {"scriptSig": "", "witness": ["c89bebaec19c24ef6eba1f257771f1e2af62a9e2a7708e9b5d61ef6755be6c28", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["4b3b612d3dbc5512911055902da8a2c325f87a947329e3204329f4a7d1f0e22c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c89010000008c1ce1da6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d35d02000000b5cc229102dba1a00b000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88acd6214a4a", "prevouts": ["49ba00060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "c643a20500000000225120a7a1e5216ad408763de5cf96f1dcb455183b8acdf7450f69dad8aadd72f959b2"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_106", "final": true, "success": {"scriptSig": "", "witness": ["d66f8c589ddc8cc23cfcf3fefa2053865a264aac9783811818a14672fa59698f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["adc6e07f43e237b02c7bea501aacff2cd02d4981315ce78edd166f7cea95f1c91d0b02aa24536590584ba2dbcaae3414f69a7f98e90692b60be285622dd33e32fcdac7e0b3bacfb0aa180bca3efad7170aea73ccce9f8571f34dfff9873356bcfa5faf4ce5fa6d7a2b83", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000003b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d712b01000000b60be1d1636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b51020000001762eafa6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3500000000034e1fe8103ab51c01100000000160014c327e70d62d692d5959c72b3411fee2ca31c546b58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac58020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac33bc0e2b", "prevouts": ["ede0290600000000235421d8103542fd26eef79006879e481ff31a67ad980b893420b2253e9541a0d656c600", "28547f050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "dd3519060000000022512081448e25da33ac22371e60a088822b5b3f2d02dc6282d5550f4d60cd5f29e549"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_22", "success": {"scriptSig": "", "witness": ["5748f4bb2b9fa75ef12dc1b851e873f25bd62f0a8ab128475b977b2052fd58b8", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50f1d5c56cb77791e5ecdf8a3116df9cd20c71b40e34a8"]}, "failure": {"scriptSig": "", "witness": ["c5b6b68bf66bbe885774dbd2cd2bfcf1263d70cd5c4b4b69b42d836d3b89334b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50f1d5c56cb77791e5ecdf8a3116df9cd20c71b40e34a8"]}}, {"tx": "0200000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b880000000001056098636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b37000000006b3a2a9b04b813850a0000000016001486053ceaa6b6ea601bdda3b6220dc75104485958580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208758020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac58020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac4f040000", "prevouts": ["097126050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "3a05610500000000225120d5a69bd9eedcca12b487bf3f2826b2d1d5d33411360ffc47996b7d60ff4d04bf"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_39", "final": true, "success": {"scriptSig": "", "witness": ["5d871453dd4593b1a68adaf5e9a1ffd48c4efd032ec3a00817b6af30014d9eb6", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["fd38f5944de6f921383379c6b24ebe82220b1360fe90e546b94589e38d039e5b1bd4b830935af2", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7189010000002e93f4b3636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bd500000000dd46f6c60337965b0a000000001600145e89b76f270f5a3384e042389be8f4c104024926580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208758020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888acaa080000", "prevouts": ["965fbe050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "073e9f040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_110", "final": true, "success": {"scriptSig": "", "witness": ["f1cb150cd3e3e31e4ae1e9dbb147c7c796ac366db43234ee104e6815bdba4577", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["9b974d48b90124a83030ff5e4ccd7b1a10a03fac0dcb3c22187e15d4fe81043bb526e88f5623adc39b70528045fd46aa3d67b0d129d53574fc943f2655a4894efb24618886804e87e4abb9827ce47a11f6b11692550a989028d31d34f47a054c2f2e94c416639df24fa6b8774d01", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c3e020000006d22329d02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49fb0100000023f8c7c901d269fd04000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988acbf953336", "prevouts": ["e0a7e10400000000225120faa3930e65e7d81b6faa2b2aae8805aa3d86c366939437b956ce3fbcc2c193b8", "2b7fb6050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_27", "success": {"scriptSig": "", "witness": ["b9a671f74e2091c826750bf98c1cab1807b11d12680e21e62c5efe3a8f638fd7", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50c865001fb534fd09c0d534470a9bd54c63b90e6ce189646b46dde9"]}, "failure": {"scriptSig": "", "witness": ["cfb33d9cad649ef1d572dd31c2b6e1825b694779802a2734b84e049d283245a0", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50c865001fb534fd09c0d534470a9bd54c63b90e6ce189646b46dde9"]}}, {"tx": "020000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4937010000002129fef9636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bf0010000006c2f078704ab4f6e0a0000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208758020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac5802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b58020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac42077948", "prevouts": ["30d6e2040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "c1658e050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_30", "final": true, "success": {"scriptSig": "", "witness": ["5b08fb037768d80921e627f634dffb67e9bccb5dce7b0a9427d39369fe590ae2", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["7e41d9a818242825180ccd37e0124261dd82e8f7d39f04b3b6f74b9591fe194a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c1d02000000d511cd8702c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf494600000000dcd19bf10143e03b09000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88acec902e65", "prevouts": ["3e0d2406000000002251208812e5d1987e04a51e27107293068a623f4cf30b5d7b9e68068fec710bc8bf01", "83a324060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_3", "success": {"scriptSig": "", "witness": ["f98e4a0b5cc98b62defe97eefa32dfee6848c6b41acecb5e9f62f3377e71ac95", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50ddbbb1"]}, "failure": {"scriptSig": "", "witness": ["3ff819c1c19d6c8ea6aed76f6eb8abd954f0cabcbdc1bd50fce91626ce297ded", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50ddbbb1"]}}, {"tx": "02000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3b000000000213d5b92636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b44010000008eb244b40129162305000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888acfdf1475c", "prevouts": ["e03e1c0500000000225120ded485ff6c1159db1ff859634589d999316e04344c155b7f1fc58addd48c38de", "ca0d30060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_131", "final": true, "success": {"scriptSig": "", "witness": ["708e90f228386770ed1613fec16a8658af8fed625fd1514b0fe11a451e142530", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["aa79a19a92eeebd1abe859750c326212b0b46a3d08879c7afe2b85ed9a7463a3b7cea5009c5ef15fa13563f6fdf583849be717f0b96b54b7efa21a630e6bb80a85f8bfd77bc475e21a1b54f9ea5dfda81a811f026849b066855d4f1e2a98511dd6a5cf839189700199f657645605c71c73b520887af701d2a1d594f768e391ad52ccbc", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "02000000036a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d32302000000c18709a7df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c3f02000000ba7ca4afdf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c5602000000118956cd04ae796e10000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd2430258020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac65040000", "prevouts": ["f5f717050000000022512040c7cab649150bf107f4275d5ed543038f365e0a263752622a1b1de144392eae", "dd500f060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "41be480500000000225120fecf0d290c1689b530cc3fc59648242adcacf20029a4f827fdfc77a90725140a"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_69", "final": true, "success": {"scriptSig": "", "witness": ["bc93ee3182b5b1c7838a1a72cbeb9fc7cc1cbccdac32d9493e1d325e9a1ee334", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["a7ebd841f1fbd53bffbc3e9743d24cc3dadb721f879fbe5bb7ab8f3b34e711ec55a1452c8d884bd7a8fff18c0b99a3124049649c72af7ca12c92e82a9151450dbef32d2a3b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d710800000000e4e4709902c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49b900000000c994c7800322fc890a000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac5802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92ecd020000", "prevouts": ["ddc869050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "365c22050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_156", "final": true, "success": {"scriptSig": "", "witness": ["68c72362b1e8c59720bcc3e5b166ceefe26b91b0e2900c47f2ef4f4472004a4c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["4504c2d8f9667fe3852ce0051222c4dc0d407edef4a87c76cfc3af6ec5e87d58fff82f4c7210ab9b6abe7f4935f68f10021207ac0dca8789d8ec01655125ef6b66502fb194859bd4ed54b55783d56d0e9cd8079f2df60604be391c193cead398db88aae5ca6943a55f355987c729e1edeb747bf0fe020f02f306d806eea89aff68c409f32266c96ec16166a4284429aa500b3dfc818ebbdbb4ff0ae0", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "3d3930060302c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4971000000002dafa9b6b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71f301000000aaf185c5b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d716801000000829a95f303c827ef10000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac58020000000000001600145e89b76f270f5a3384e042389be8f4c1040249269d401a68", "prevouts": ["40191c060000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "335fd5040000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "8d5900060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_248", "final": true, "success": {"scriptSig": "", "witness": ["b2a30f2bbf4468918cb880409c36decc32107ea1e056b1a217a00776833d0c3c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["df49a875995c129a28ef1fe4cf6ea1abef2363a040b9ee4d8c0cfb8773925acea9e3c9f0704e81101e66e2ecd67f6ff36ebb947a97ad7d786a8ef68772b3c1396fee95082465d38c1187f7c860cd6f36790a133db3f4ca93fd16d316a7311d5fcae2257b3f489776fe7a115837c08352ab1d467c287dd11f1d59f1e7e5e70db05cc9304ccc69043289b992216890d89a246c100286ffe591de04741f7b4033f5cca22a402d5d6cd4aa538ab8d2e85b3b1e0a00e7e082d7ecf3b0809e03ac09bd66b1c908c5dfc968d8725ad0c76988723c7e45cdc87ad8376adce7cc9fc6cbb165ad3868c74b614ab1243001e7f2699c6e427ec61d988091", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c0d01000000168c426002c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf490002000000b9fed06a01d80d780a000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88aca6010000", "prevouts": ["696dfd050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "e2bdc6050000000017a914d005833d09f3ca8722c64ddbdda5b936d94f704f87"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_222", "final": true, "success": {"scriptSig": "", "witness": ["447fb633d2dde1aa9fc9050ff67371d88e3a678a868b8d79664c0d7b06bf7b51", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["453f90fa477ea249bd6c01a9cab07d59ee0df77381bfdc25e54d41833e5e8dc9d404ba80abfe9b3ceb8b474f9672b25704d9683035c6072e87480315debf9c3d1d4324c1bebaed9f5745825693b4a2d2e3b1f827dcddf9515d6377aa332abad25de7a688db3f9be03ee7148e70523672b1b7ba270a124921400bf2cecd99cf63e6e6469037713c593e86311d07e0063e76d885e2a22dcd3f8554d909e5731bccbc30670399b22369c1209206303873949a03778995fb21cb5df906d876bc747acee683a4d5cf4a5ff870ae895f6dec5b5ea1d9b2559854ccd71f7d3ed959", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000003b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d713a0000000049657ebe02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49ba00000000eb5531fd6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3d3000000009a93449502c006ef1000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88aca552f83e", "prevouts": ["9b00d7050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "d9b63e050000000022512018bc9b7bb5cc5fbb2eb02aa0decfb057631f529487e64aea5d15e307678a72af", "8f54db050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/32bytes", "final": true, "success": {"scriptSig": "", "witness": ["ce82012088", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3496857c10527c252a8f634fe2045907d6cb5fdef71cdd3c832ea67e90983133fed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["ce82012188", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3fc8334f7af5610b177e3637dc583bb4a306f13b788f0e2a1320ca50a3215b13dde47f2bf66024fbb8883ae0d6d6630c707f27731ea61d0eeb0d4d6d90a5d27d788656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf493d020000009b0ffda402c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4902020000007bc9dbf804a9f0710b000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac58020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac580200000000000016001486053ceaa6b6ea601bdda3b6220dc75104485958de8afe4e", "prevouts": ["f69b0a060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "714f690500000000165b14d8103542fd26eef79006879e481ff31a67ad980b"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_16", "success": {"scriptSig": "", "witness": ["8caa20d75c772d4848ad8321941b27ccb06d0aa1efe8e41baa2bd83df470cc38", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50c84f481a7b1c6468788025a2e0bd41e5"]}, "failure": {"scriptSig": "", "witness": ["4e0ac9ec15877496d332fc465f79d51d68acdb59d56ce2030a5a6a73575f283e", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50c84f481a7b1c6468788025a2e0bd41e5"]}}, {"tx": "edfe4076026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3f6000000008f2bed91b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71c80000000057351fb503e8b73b0a0000000017a9144657010e5cf55af6acb627784c227caeaa0f0a3387580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208758020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac06090000", "prevouts": ["6a2b90050000000017a91493179af9b96fb4da6a4e8193bcdbf6a50109b73587", "bfd7ad040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_28", "final": true, "success": {"scriptSig": "", "witness": ["5711a869dbb4f99a479afd87090155cbdb310e3cb57107c7253d561f19fcac36", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["f83ef2802d292f0020f5e3062194c9c5aa368199f667c425ed0a5b24", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "23dd676e0202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf492e02000000499d29b16a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3f000000000883af98b0249e3d70a0000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb875802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e74678a33", "prevouts": ["661f82050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "a73a58050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_246", "final": true, "success": {"scriptSig": "", "witness": ["c18753d085c9f291255c3da1c617f18e7528c9b4e6c4b3329b7687bd2a697741", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["b1bbe805b0ad554793941633787807638080a77e1b49e989867ea2c4299d2554f18499b4f50a5b23b7a6c6baf637a2491b06d91ec587eb8698e9b68c952933edfc9798fe878825257ddde1fd210602713d9b9954db68946ee8f30c302b874586d852a157e30d75b7424c32900f6754540fe6d668bf39d991a9b390452c1fe91e6091888d88c5d903fd459308546c1cc7e2ffb2a42d2eb993d898e33eaf6e476a5cddb8ee5537e006a4af00a2684b5f0e01aca47e512617d8595cd83b777f6cba4864fe92aa8702a6d850648700e533584bde07e02145eaa12dde38e0b7cc8a3eb4195664222f481183e6bd5e8d0ac07f97751a0d338a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c69020000001d88fdc4df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cb200000000ce31b09d01fdf35f030000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb87b2020000", "prevouts": ["b9cd7a060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "9690a60500000000225120348e2be7446b82700fd8b5317793c40ff5d97863329e9960884d3c06e543e644"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_13", "final": true, "success": {"scriptSig": "", "witness": ["2b9240c442f3ee07e37e2a30b1637cf7676cb6ed719772333df7d5141cb633b3", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["8145b3b0a9ef21861658ace977e023e7a197c4a129ae9aee36c63c07dd54542e", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "03ef0788026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d38d000000008f9567db636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bf70100000001ce38ae027e3c580a000000001600145e89b76f270f5a3384e042389be8f4c1040249265802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b0b8e2f4c", "prevouts": ["8f22f5040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "86c9640500000000225120cf8fa6ff6acbf3cdfcc1c4e96aa03e61dcdd47cd05da7e6f4c81c85e5a5b2bdb"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_17", "final": true, "success": {"scriptSig": "", "witness": ["54b5eb4d79d2a066ad0e762c9ccf8e6345d53335da470f2eb77339c585c05614", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["16cb1da190067d898cd83b71c7dc5fc2e72e0bcc86ee7fda366a765226ed8ee2", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d714e00000000acddcc8a02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49ff000000000ee56b82045fbfc20b000000001600140276cd59f2bc98ad777ccf7057f574395bd2430258020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac580200000000000016001486053ceaa6b6ea601bdda3b6220dc7510448595851567342", "prevouts": ["ec929205000000002251208ae25010575eeb01ba7d54e7b159e8cc57746ea69ddb94de7edfce81d607b184", "841833060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_129", "final": true, "success": {"scriptSig": "", "witness": ["2c77b3c73a4b8807abe8c8eae49607384ce379a329c32be4825a3f410c952392", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["ec7e14e52f2394d5cda07eb67af87073e00ef38f3bbbe14421f5f1eeca9f31e53ee0bc1bfffc32d25ef98b560342bf6ed8f3495069c2133607702b680c714c1c26bbf35cf730a767c5e8e19985a747c54b4196049a605d71aaa8b13557c6c1044bf226e63e9a5e9f34c7ae7190bdf9a9d2b4d330cc80bc12b7100d5fe853743e4b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c3400000000a3f601efb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d711b020000005135aba401160ca101000000001600140276cd59f2bc98ad777ccf7057f574395bd24302240b0000", "prevouts": ["e583ae040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "eadbb5040000000017a914dd4aa9a50603812c2e28b4ebf4795b15efc5c41487"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_201", "final": true, "success": {"scriptSig": "", "witness": ["6a81a8df2af435f28090bf0a6b5ecd2be924ebb2db01feaf11819d1623ce2158", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["d8f8e69defecb27669251149efb65cb78fa099005172850b35c9e31fe215701fc0c3fbd82a8f6ab6f58b3335755b614ad87a9d683fdc7a35fd0ad519433d34ab51376a162bc604e5ae328c57e5c68e95d4aef98abb1e7313556561f28928f46964c30adb67e62037b14566530ab730811bd4f66f945c5faa952b4e4d55d030c7dff2d400a8929e173bd5e7ec61b1159f72c3c5aac3b97c998d073e7b0cc842128c1a4d25f32f37c3135ab7840323f87037a5046fdd73c1e5f0a08da4dd892271d79937d65bf725b63a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000003b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7125000000009b3722cedf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c5800000000ae00b31b636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b500100000005d2ad02041b34d310000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac58020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac44020000", "prevouts": ["b0aff9040000000022512040d8f5c0f5f206018f3c15ddc74045cab34f3b4aa686be17bf6aeab8429e74cc", "d07fb1050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "482a2a0600000000225120aca26f3d7c40f0943a9eccaa69c8b35fef03a08c5252100fd6db098b7d004b43"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_162", "final": true, "success": {"scriptSig": "", "witness": ["dce844c201a872f35649c1a2ad08d05270e29d53b38cc3d1047216340c193eb7", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["2df54d604cf48b3578a0b760e6a916b411e099c03b3ecaf7a8bc3bfd1c80c11ffbcea7a1e1d4dc0043877b551f5059b6f6bbc8e016161ae1072d7d0131a0cde07c37891a83d14213adc53f25751d8e49b5527ffa3b58d8066fbf7a8592bbc29ad856b97e2923fb99a951ece7fd915769ef2e1a324d9ebf2c4bfdd6e852ffffd3a37d1693631ce5ca10ac49134775cce7bfa6a43bc96e4fb7f174a519b4e32390b71d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000003df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cfa010000003d0d1318df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c6e0100000025dc1b3ab8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d710900000000c2d1864d011b7dfe090000000016001486053ceaa6b6ea601bdda3b6220dc751044859581d070000", "prevouts": ["5125b6050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "bd68cb050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "0577020600000000225120f2aae555fbe32d09fcb0c2e73b3c5769f65c28c984bae3ae14daead9c5b8a8f9"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_77", "final": true, "success": {"scriptSig": "", "witness": ["234356f91e0618c9a3311d6b65b65cb47f148c0dadc1a6ff9d508000b67220b1", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["3b68062dd2a7079707a5ed91a9da1556d0e585814fa7514f0274fdbe6d380a1678fdde75e1282f40404943d4f2169b7e30c7749217cfd7c71b3d60ee3c6e2bc2993ae85355c0966f82a290d03b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000001df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c8201000000e76f0e710330b2e1040000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338758020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac58020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388acad010000", "prevouts": ["0b32e4040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_5", "final": true, "success": {"scriptSig": "", "witness": ["7ee82af08cddccd2314c47499b547f394a3b8cbea668a49a5c5d71806eceb1c7", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["09b3f92a26", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71d700000000c58f16bab8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71b400000000cf79a8db04e5c0210a00000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac58020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac580200000000000016001486053ceaa6b6ea601bdda3b6220dc751044859586705245c", "prevouts": ["7917e20400000000225120ee3809dad2b40075d7e7a014477358c898a21020f9a31a35ee6d57ed487c8b92", "3ea542050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_244", "final": true, "success": {"scriptSig": "", "witness": ["7b38dead4db7f35761d7f662a043b52d978d89996949778a007b86436591b85c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["31a5372d869838626e0c45875ac3e8c89f0741518fec6029914ee94d092ca703692b57a4f5ce443183c9cf913be7b4a549b7bbb4376354e8f3ff4491368f1eb2d7dc792a105b1eb925919c87e2eb985a23e7d9cca568bc70c9dbdbe548077f889eea68fe26e3935a291d6b14b3091c7e0f1c237af7c6361c41463ab7d994363d3aae8c79fe929ef3c90973a54d9e080ebbc126540a9d0b3b7eb13c6e49a44666f6bcf9d89a085c99895f86d72455a7306fe1024f7cd168c1af9df05e8f8c402545053fd5250bcd51c83840cf319390927c21a840569acb7f8975dd38272ea9d782a288c77030d8864f5755106ccbd5c0d2f50a03", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c7b0100000085c6c9ca636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bc9010000005f64d9f002ddf2280a0000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338758020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac447ce034", "prevouts": ["8dfedb040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "ef6c4f050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_178", "final": true, "success": {"scriptSig": "", "witness": ["4d08b21a8a263768a535651d16371894b65fb112bb2ad3f991708f4c6fa9af4e", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["f7405f6595b4ea74a13b100a50fed69791905cebf8eb3b16664c15a14849adee7b1c4b0154e5bdd7a6c2b0f67403bb9c954a29240a7f6779f9eb11179badebee37f6bea6a8150fd609cdcb4d8a5a98653d473142d6d1d30237e8bec9cafd1f7789da048599a1b1226a5689f1b6285091936789e6562e707212b6bd3c115f4d362dbfc675d519a42da13c0b66e7a4329bab017e5565bb4ccd3569c1278976fc052edeb1458bc003d0accf33cc6f8ddf661339", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "d4d68ec503df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c9f00000000b4326bb2df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c8f01000000c2ad80a6b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d710f0200000063bf4ef302563cfe10000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac15fc9034", "prevouts": ["7aee6d050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "367412060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "622480050000000022512077acfb70e8196b8f7ee4b8f141973ce396ff7ca359bae84a0da9fa85341a52f8"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_45", "final": true, "success": {"scriptSig": "", "witness": ["12e996a4aafdecd23b3516419974815c45549fcd3fbb67c4c11f223ed17a31a1", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["59ad0b54cc237accb6f643f89d5b9712f06f5f2174829a490b1ab959acd2cc2c1bd27616295937c3fc0c1ce72e", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "f4e5a7590202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49300200000045a1cceedf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c7401000000cf1d6aba028697ba0900000000160014c327e70d62d692d5959c72b3411fee2ca31c546b58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac741d704e", "prevouts": ["2d250e050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "13c2ae040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_253", "final": true, "success": {"scriptSig": "", "witness": ["37118ad221de572f0a95b284052378a9913fd6d9768a48a6b0e800f2d313fb83", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["53fe7478053f4e06093303c8624d9079c26e349e65f28c1902ed7ee9199c3ee6cee1fae644a5a14ea635b37945e11cecca5f29d318d010c1e3003970c87c4b0a9070c5331584f078228c411e55721353c3cffe77bbb4cd597cf01816e558250fd1f0d6b6507cf673b45c098eeeeb6ca76dccdafad87740e2bc32954a4c2fd70e37071b81698e6e426c17d9f4b769bc9d337416165b148fe508a7e133c12cdf5e04603569184689674847c1872a2c1cc0e657c1b8a3a668a193553ab6e38cb7da9ba7d8008ce69a67eda0f9f6e1037fede49c1715d1205649ca9ec81518fd7915af6a2055696f58a047c64d0449788d47c13506c7db6e94780d179ac5f8", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000003df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c16020000004850175c636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b8e01000000847eb5f4b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d714301000000ce3a328a049c087410000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac5802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac6a92ee51", "prevouts": ["df86970500000000225120bb7e8c3c0d590ca9e24a780cf353fa21823cf0a588d7a87aaff97c975939347c", "a6bfe3040000000017a91453b1e5425530abe6bff440ce552150c3eb8df47287", "b7d5fa050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_67", "final": true, "success": {"scriptSig": "", "witness": ["31b42106b0fce41e2c687309e5f62a0319350f0abf5037e6fb603f3fc538b242", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["8cfc6ae99662934d212b38965bcd50caaa1c5f13046bd46892829b67599fa2beca6fd5947087d8cc37e5ca41c77cca31212bf6de02ab37d2c970c35cc0c1fb9e8a24be", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "811e003402b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71f401000000018a9d9fdf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c2e010000002e6709f202e5a60e0c000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac5802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e2cdcdc3c", "prevouts": ["5237e8050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "b54c2906000000002251205f388422c7022ae2f3c1e53fbd2f6be9d8414329fb5fa50626d2dfad234f565d"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_224", "final": true, "success": {"scriptSig": "", "witness": ["09eeea5636dea497c4689b0a74b97f70eafac451f40373a715f7840632e456a3", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["9e7f40c4d8163e1f664a533e83a56762f2588c7b5516da8ff9bdd017324949a6c7e096c51e39e43dc86fb7e2441bb4b71729df01a538c6dc5e1eb6db5d28dc00b57de40ee027bd3e343c524ed75c4ed72dbe7660aaae2d87acf9d57e451517bd9a4d3bea795e93f8e222ca7299f330860602b54e24574e451c18e4052e15d49c9276dde5d897357f1807bfd02e5437715b77208669876a1ca8e50995b952945d84a0fee96af2e72a208b507f76de7c6a5b7add708d2ac736b3fbad1da420607bef8e06c656b03feaf792a9a49e93b8f9e65d21f44388269551f00fdd8bfdceff", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b9d00000000c8f804d3b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7133000000006603429a0148be2c090000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208786040000", "prevouts": ["9fa214060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "c0ccbe05000000002251208ae25010575eeb01ba7d54e7b159e8cc57746ea69ddb94de7edfce81d607b184"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_123", "final": true, "success": {"scriptSig": "", "witness": ["d36b4f5715344b8172f8b3681545dfb64b2e676bcc75262cc931e683b9cc041f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["58254c8145855536da6294f10f32291dc9f82dce62e1fa48b5653cc4c237e5a0f23c90c9ef96fbfea5e74b2f42668281fc39b2bba49deb320b312e4f70763f95b009d38a9b13f5773cd726c6024aa7a8312f3e15b67d9d3c709739ea0f23ff1b76345e2bfa22e5b9c102675ce98a7d92631ffcd351caa04dbd2ca5", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "43290cb102df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c5301000000c94949a1b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71ee01000000f61ad5a0023d24a90b000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac1e2d8036", "prevouts": ["890300060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "d5c1aa0500000000225120d44e7e2c906379f7ec38af60e636bca3dd8501434494c9e52c10d4dde3f3d669"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_134", "final": true, "success": {"scriptSig": "", "witness": ["3e33bb2febebf22fcb9fce439aac940f0e2227c5883c0504eb6662c41b1f0278", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["14d076d80dffa9d62ed676a4a8877a136a484b33eec592dc7e40eedcc1bf20029c9690926802808b68df9abaa5f6c9b68f3870906962b0a555614b9e501d995ccef9848971a0364e61d22796f4ed69b38c3e91f3865e09516b7f3a71a29a2a4e3e383442b74382add709751b3b8d85f6305c51362506954f3f9722af82a3a189de3ce1209352", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0e12773303b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d714e020000003405d7dc02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf496f00000000653a78bbdf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c2500000000604f4ae301d468d20100000000160014c327e70d62d692d5959c72b3411fee2ca31c546b78020000", "prevouts": ["ddeae704000000002251209ab329e1ce759bb8a1db84a814101c9a3ab8f768be47a55e0ac8b65b12e2f336", "dea314050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "4c4cf9050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_229", "final": true, "success": {"scriptSig": "", "witness": ["3f8eb912ddb2af6807b4722575de9a5ec84412f5125d1aaf2f0e6a6539862a2f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["d808a58d4aff380543b7aa630ea74846ae48ac51b6feac465eec15b5523906b98b0b1e37400209bf22746564462e1f6960af895d25fd43e2e244b6d3e5863f91dc38be87fd0de0cc7d074f615d2df60ac33ec8c3bf1f6c912bf2ec4b5e8ee1b6ef525c8658b39618779ab5a875b52ad8bcaa0e80d3adc43ff4054fe16b76dca4c257b64e1316a37d0dd1117d521781e38a4637d1ffd618450ad6633ce441d29d36376999a9a3f0e3005126f7855b4fcd45d39a34c5de5f049fc683593cd195f0165732248e69797602793875c6505a6fb2260400c829975a81dc0326cebf31c775bc893fc9", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "02000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3910100000009a7c7b402c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49a5010000003a5d5efb04430d030c000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd2430258020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888acf9a7855a", "prevouts": ["cc3ec4050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "87c940060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_10", "final": true, "success": {"scriptSig": "", "witness": ["0a1a5bd4b5822429f3e0983175c585a248ad4db5d7aa8aad37347feb4afb1e66", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["f2a73246cb2b97a986b5", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d717701000000a38353efb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71a2000000007668c7c803b53a1e0b000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac58020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac58020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988acce050000", "prevouts": ["a1138c05000000002251204716f368ff34aaddd589015c90fdcb17981d69012e3d712684f6ece151afcbbe", "070794050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_12", "final": true, "success": {"scriptSig": "", "witness": ["9892a5ef5d1350745e05a2d3a0da609f5d2f74238197a1ca4dead822b1d90f55", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["d56133270b27759189f3955d244ddf2785766530956e23bfb79cdbf81541d911", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "1aaeb963036a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d30300000000cce76d9cdf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c42000000006a9d14836a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3a2010000002824c8ac021498381100000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e580200000000000016001486053ceaa6b6ea601bdda3b6220dc7510448595887060000", "prevouts": ["47631c0600000000225120ed113a17b3833bd967ab54798fcf726404cb40d713297cf1bb9b5fa81815b27a", "c4fbd2050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "7e2b4c050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_26", "final": true, "success": {"scriptSig": "", "witness": ["b668f8df38ebc7bb9ef111e88d903e6c5072fb061dc1f8b2c873701ca9792d6f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["8c368355e015f1fa10919ef544c9d4fa8156e77e05fba15172c4", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c8a000000000c5c6bcc6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d30f0200000038acd99b021d1bff0b00000000160014c327e70d62d692d5959c72b3411fee2ca31c546b58020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac44030000", "prevouts": ["4774e90500000000235c21d8103542fd26eef79006879e481ff31a67ad980b893420b2253e9541a0d656c600", "2bac18060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_28", "final": true, "success": {"scriptSig": "", "witness": ["0dd2a8e3f8a3b116e743a1c78dfc8fa206324698c7cec87fc227b24cec995c81", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["551aabba5a845d8e83fa56168b7745834dd6bbf1162c1144478762aba8b2f0ae", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c55010000004d91d2b9df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c2402000000790a79940115581f02000000001600145e89b76f270f5a3384e042389be8f4c104024926abc36c61", "prevouts": ["462dfa05000000002251200cc62765611fd72a67fa1c6f0b67585b8648bc26c4ad0eec7968194c906a9056", "a48f83050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_15", "success": {"scriptSig": "", "witness": ["e573a035187b0c2866ecbca5d5c59cf0a8151e2db394c5304df181452e5ae2b9", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50f8bf4fc30df12f50bbb72ceabcb766"]}, "failure": {"scriptSig": "", "witness": ["7b0fa107699325a50f1dd76c4e6563094fffd85cc7f6532b47e9bbc263d38bf8", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50f8bf4fc30df12f50bbb72ceabcb766"]}}, {"tx": "0100000003df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cc800000000603edd0fdf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cbe00000000e9476678df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c9901000000fb2751ee024a3f0a10000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd243027d088363", "prevouts": ["31300d0500000000225120830a733a18b85ef4b0312c74547cd56d5f9e0c3d25a3cfe191c507f1b30d25b0", "15e945050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "f4b0b90500000000225120298972734e68cccaabbc4fce3a790eb7d4a6ec05a497b5f4abfa76a3ba310eee"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_181", "final": true, "success": {"scriptSig": "", "witness": ["3b4ce17f594c86033ad47b553dae73d80b3586cb45f8e7d60dcfddb58f10b2f6", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["4943a7724614528491f9627301ffbc6ce6a31636d34aca9bbee0256be44e8e0973e8a36c1bb6318e688fb4d0bfc290986c2d6a97763931dece3d23ec1985f3e0878cd3a29b453ad766d7a63245ff97f024a77d28ad518af319984d038f917b100a104179f0d152738a64308ca9675eb7145533c4ac91168caf247578056a2ba8463f91c68ba6aeeba8968f7a285ce274959f45c5794e70c190282df478e8a87e65d1eba7645b4653d1f5aa76251d207ff471f90036", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "02000000019207be2a6c990176af46d129404176ca236dd0b9556637a8c96d74dd2e37965d0100000000bd1373fd03ddd46d5d0e0000001976a914001ab88085e18cafc158818ee31fe7a878a6d87c88ac58020000000000001976a914e12a54b79cd3518ac70070d2f9a1b8d28017bf6c88ac58020000000000001976a914e12a54b79cd3518ac70070d2f9a1b8d28017bf6c88ac70bb1f1e", "prevouts": ["3fb1705d0e000000225120c8fca798f6db05732136f92fb7c8c1c45587befa6ed8eaa267ff78889e288109"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT", "comment": "discouraged_template/emptystack", "success": {"scriptSig": "", "witness": ["ce75", "c17787c4346a2348830203d75461a997cb3aba4b0c94368711f4a176bd0caae6388cdeb0de8daf44e986d19e114a7b8ed70d46e74ed21bd6c6e785c2a6747f82dd"]}}, {"tx": "c228fb78026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d32c01000000e5a0c9d4636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b6f01000000a589ea9f04e1a2a10a000000001600145e89b76f270f5a3384e042389be8f4c10402492658020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac0d21062e", "prevouts": ["f40078050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "46a62c0500000000225120ee85ba3018e04fc8f1589c44b5742a8c5f2173ea5f6655223b73be51d2672e71"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/doublegood", "final": true, "success": {"scriptSig": "", "witness": ["cece87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3f9e76dfcba1dc6f85060a8dbf4fbb2673cc4cd0f077065fb065ec870703b3a2dde47f2bf66024fbb8883ae0d6d6630c707f27731ea61d0eeb0d4d6d90a5d27d788656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["68", "cece87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3f9e76dfcba1dc6f85060a8dbf4fbb2673cc4cd0f077065fb065ec870703b3a2dde47f2bf66024fbb8883ae0d6d6630c707f27731ea61d0eeb0d4d6d90a5d27d788656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "152e8fa0026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d39d01000000f3d75387b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71590000000093d4f7b601dea7fe0b0000000016001486053ceaa6b6ea601bdda3b6220dc7510448595877040000", "prevouts": ["452fd50500000000226020d8103542fd26eef79006879e481ff31a67ad980b893420b2253e9541a0d656c6", "83212c060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_21", "final": true, "success": {"scriptSig": "", "witness": ["db969115d4a15e49c70df183ec60d701fa38e0508a4ea1cf0344b951355faf46", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["e4b52c2066b0f5a87dd382fc4c413ad9396ed9a04a4d4497abdcadd04d6892b5", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000003b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7198010000005c0a4587df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c700000000026d5f9a6636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b7d0000000069a43e800184580f02000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac127e1a51", "prevouts": ["89567705000000002251205f51f1d9d36060d0e3fc6fd13c62d29970fab15b07cb103daa0757509f41d4cf", "1b33d005000000002251208dd2e9e0dff54592e51652a78d2b49f1f26e5cd540552d1ba10db850bc7b003b", "a721be040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_21", "success": {"scriptSig": "", "witness": ["2e3ef08f80c2dc0b61391680e82d2cbac668a87d4da7626f4d628a7d476f5c95", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50f4a95c963f7f81f7f57176f665dd0945972528e69d"]}, "failure": {"scriptSig": "", "witness": ["4b95c64e67cfad876d9715a9be296628df89a4a7d69e1ef60f438132a870bc1f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50f4a95c963f7f81f7f57176f665dd0945972528e69d"]}}, {"tx": "95d01f3502636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b1201000000847977bd636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b020200000022b0089d03f443c90a000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac58020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001600145e89b76f270f5a3384e042389be8f4c104024926484d1e39", "prevouts": ["b8cefd040000000022512016419205b4c696a5dbb724624e42c25f49dd7de83fd616bddae2dc9c34c91fc0", "8b79ce050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_66", "final": true, "success": {"scriptSig": "", "witness": ["6cedf71c3e9ccf9566e21d0652ee8ce9402cba35cc07667dc1a06e995692a9a7", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["8b7290dc09ee867ae4eb6e2cfb3cfb3e42ecd46657855c52c71a995d7b7097c817cb355f7fc0afb3dff8cf393ab19d542f9d83b9eacd28afb2ec80d78944604180eb", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000001df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c2400000000052c19f004c3086705000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd243025802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac70070000", "prevouts": ["935d69050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_13", "success": {"scriptSig": "", "witness": ["bc0a9d1577e7d2f1aa0e64c1da6e6acf9e26f0c5d0fd1ba3be32fd02adf2eb51", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "504fff99154fafd29e16609d4882"]}, "failure": {"scriptSig": "", "witness": ["fe5f92bf9c81e41a5eea39ed5184daedb01433cb50053e2539deec0b559d89e6", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "504fff99154fafd29e16609d4882"]}}, {"tx": "159f336301b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7159010000007b9b3aea043e2ba2040000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb87580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb8758020000000000001600145e89b76f270f5a3384e042389be8f4c10402492658020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac6541124e", "prevouts": ["49fca4040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_216", "final": true, "success": {"scriptSig": "", "witness": ["ab560b1c60a610053987caac1a06625e3579c95481db6246dc0e056a20507f9f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["bcf7b0b22a81acbc6f80c40c36f302293afdd3f59981a2483ede5a1924b2f4a378f81c211739c71b03b340f000c623e334cde8776c686b5519effce9eacd6980cb779f46ecd400079a78a5be745a79251d93fb10aa9ce02aab838ecaff54aeb79bb25a8c432ad6205b5e8aa723b58ab2c73dbcc170ad5f398490d2da6ceea92e914f0e993944764e48aa13ab3a9d99fb7e8d32ce617fdf6ee5e60982cdda8c71b3e275e7f732e7d7475630f9770815856f9741af09430e2986e2f33bcabe42e412932266e23d90d90d624a0bd2ca1578b78eee2404b2c521", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "99d739800202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49a500000000954944e202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49da00000000d83718c201b434a201000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88aced5d1d34", "prevouts": ["616dd8040000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "256fee040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_68", "final": true, "success": {"scriptSig": "", "witness": ["d977ef2f3740e716675e84ac0f8c4a3b31bb53d35ce365337fa988435fcb3740", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["37150baf40f9617c4b41f54282aa39f25a06985565635051f912dd51d2e7108008e138b2bfeddc35178f6fe4f00e2a8b42e913cf4e3728b2c68c17998989a1894c468756", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b9a0100000022e500fe6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d30200000000919242b0044dd9860a000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac580200000000000016001486053ceaa6b6ea601bdda3b6220dc7510448595858020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac54060000", "prevouts": ["7f2df5050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "a7de9304000000002251202630a74615e8f77b200aa7f36f21efda4b827bab2a2877b79da46b0bc2937b03"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_17", "success": {"scriptSig": "", "witness": ["4757b33e85c533dc1d5ebad8c0fe2af27ab180ff73160edacdf0b1ce924c7d22", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "508c752d565a69509178e0ce9d066786e07e"]}, "failure": {"scriptSig": "", "witness": ["3092e77835db6bc0cd8be486b0aa3b79548ce428f31b247b09d392775ea8daec", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "508c752d565a69509178e0ce9d066786e07e"]}}, {"tx": "f4e5a7590202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49300200000045a1cceedf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c7401000000cf1d6aba028697ba0900000000160014c327e70d62d692d5959c72b3411fee2ca31c546b58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac741d704e", "prevouts": ["2d250e050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "13c2ae040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_135", "final": true, "success": {"scriptSig": "", "witness": ["c3c3d23b45caf8e5daa0f7f1cba73394b0452a07aed28836070fbd23c2948c4a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["b2a4c358d871ef0a9f607f756fb4d527610bc0e4894c7e1e4b2cfdfcf3de346d934db47a8494d35d29137ddfb7234bf08de3897f3cafead91a5d742aa48f836fb200332f2f69d062c85d110a0b42821a60445674b41e5fe9ed6b84dcc7a5b94b9a4e037aa6f6c8a3d1c3a42d6bafa9d75b6e45f0e71346df3923b6bd5cb1798b28ce8c4254da72", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cca0100000043b1f7bcb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71b600000000fa941e9c01eb2ec901000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac62ee5c4f", "prevouts": ["1a34da0400000000225120733884b8e445c9b8b98adf61cca764decd4087095d1eb16355189602c151ac26", "50909c040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_71", "final": true, "success": {"scriptSig": "", "witness": ["74c0be8406f71943bf1ce3618f10492b8d1c54efd06f29ec11e5b55450fc8f2a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["1b56eeb7b98a9548a2f38b0436cd8268b3aa5c5d0fb5aaeeb879cf55b5f306ad96fbef869847e5cb90615d6b2410cf2a66293cd7173b98842e80a06b34e35084f841a65b8781b0", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c020100000084bc66166a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3ae00000000e35b5fcc02342df809000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88acc6050000", "prevouts": ["0241c2040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "799537050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_14", "final": true, "success": {"scriptSig": "", "witness": ["0ba5c424ca1fcab39073a461653f4bb15970521d02dc80b204129ad390f06e99", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["12396aecdccba07e569ca4f8c93304cadd3dcf591901acd2f980a6dd1b6fccf3", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c6d0100000087b04c9d02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49df00000000a7c81d9a0131f2010b000000001600140276cd59f2bc98ad777ccf7057f574395bd243021e070000", "prevouts": ["5212fc050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "e4244d050000000017a9144f7eda758017258735bb84dc62ef86d79caf147c87"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "compat/noth", "final": true, "success": {"scriptSig": "22002085979fac9dd1a0ebaa6528ac118e6f3c489cab4019bb673e80e9070a73070003", "witness": ["", "63ce6851"]}, "failure": {"scriptSig": "22002085979fac9dd1a0ebaa6528ac118e6f3c489cab4019bb673e80e9070a73070003", "witness": ["01", "63ce6851"]}}, {"tx": "0200000003636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b68000000002005b1d4b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71ac000000007f8f1b9d02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49b1010000009b793b92038d21da10000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338758020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac8e983664", "prevouts": ["f6a6ff050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "e994dd050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "ec9eff040000000022512077acfb70e8196b8f7ee4b8f141973ce396ff7ca359bae84a0da9fa85341a52f8"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_239", "final": true, "success": {"scriptSig": "", "witness": ["70d4e923a69b17f46ad16c8398d96604a0e8f252fcc730ec58d82a48ea94f054", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["44b863d8b64980067694e07c8450f91cd29c6fce7456bf55f34e82f3bce8bb21bc86b5f99b0029f0469f6d818739afce8b5bf703be80ccdaaafdef91be9b7f6d38cb914b1ad8668cd18fbed73d0fe823fffb2e6a02be4fc80536a6dcf836b457c106d626150c53ed5f5fec1cc24fc229d489ce5bb3ea9d22bc4fcc8dfc12ef82c39caff405c910d39f8656baecb2bbe8712870b01ed43842e86c6abda330d11723ade743ee60fd2739d92605a9dc6aa80dae826cb7541fe8779192e714cdad3a82663c3caff9f2d8a2d6dc69129c3af1de13c9f45fa2d9d45c87b2be98f3cd2dc5a6fe3db2f08efb3e1a4724dd3470", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "5529ef4b02df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cc301000000089ad383b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71b8000000003449558d04f7e2500a00000000160014c327e70d62d692d5959c72b3411fee2ca31c546b58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac58020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac92237b5c", "prevouts": ["f53ff0040000000017a914dd4aa9a50603812c2e28b4ebf4795b15efc5c41487", "18fd62050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_249", "final": true, "success": {"scriptSig": "", "witness": ["27ed320f51100a68711c6f30b7169d5bc847644dc59c9c412a7293d9b14b4f68", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["7e8086517d1b2209fb0d559027a2b085b7ed4ba32b18fb6c155ed32ace2dfb59333aed147cc5fe5a167deb22694a8272c4594fc04a3d6014427b95e1019bb6793c2d01726f6a9f93940860eb17aae7a7557e8c7a5ddc851c8d7296bc468ddf83216eff4cd5bdf74fef21648310e375b0b789a323698d829b94f814443914655c7ce7479ace953e141a3501f42a5bec6fe75d9e10f668fd3877fd6ea24e465f2b9d5713e6718975507821fbd738f54e4392af0ad335d5667a1b876e6238558387cb39aa8bbce3c81c71dae6dc3dc67cc42c22cd08c6bb6b7c88199d745e07d1ad65ac92979a26002c582a261e5e7f53f6c332ad2e2bf2683c57", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b6600000000291e269a02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49be000000009294a099042df32c0b0000000016001486053ceaa6b6ea601bdda3b6220dc75104485958580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb8758020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a3387c02c2c39", "prevouts": ["1af55b050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "02e0d3050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_171", "final": true, "success": {"scriptSig": "", "witness": ["b37104fecdf70b56b68c0544124c526d2edbeceb0d5d4ba92d6d8320db227070", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["06a72bdc3c275cf5f4008528b347b33e6ebb93ff41a63c5325d9a8b9cda1801996a01673d029b47f43a728a3d54ffbfc3c9d52dfaa88b86e6344d8fea1103155a6a08310be354f365be6ee28e47148318f238dd015c0889b17e769a2374af21f35ea58a9c830baf8f16a4362d5251176f90e646c38a1cd018452ede10a24bc6a673592323569e5fa169b0de913a00c0412180df1d436f23dee0395249143c3ad05e85568b75b937008cda8", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "27e52157026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3fb010000000e847aef6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d35d01000000bfc611d004f3f6b20a0000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338758020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a3387580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb87aa000000", "prevouts": ["0ff9470500000000225120a6ee9fe2ffc739f132f18d35a0cba95efa5a60abb6c27b2a53975e649aa427de", "fdbe6c050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_80", "final": true, "success": {"scriptSig": "", "witness": ["c4560642ed2558012fd423318032030c8cdcad42631cfa7f3d4f31519638f81e", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["ad6292f5c4661a6485ec0d3a5ed5be629846f867800a7cd12012484d44b698051ab5de0b5f3c92c7fc823f75b98eafbc0fb7ec2a316607f75ae2dcfbde42e8b4d492e94601581b34a7c4cd84ac876c36", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b7f0100000081e91681b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71a4000000007c924b560167ab8307000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac06000000", "prevouts": ["b2fb9b0400000000225120cef52713e0135611a92827dc02b2082e39ca6c7f6dc69482b076648400485331", "b2c8d8040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_19", "final": true, "success": {"scriptSig": "", "witness": ["5c2898b7e0ce1f953dbcacefda03014dd93da22d9904b44fec5e95a8c21f9d04", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["7ac56e3daa0a112f78ba1730b2b8b0043acd3b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "999f538003b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7140000000008f818b976a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d33501000000b5163bb76a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3de00000000590056a702caa93510000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88aca6ad3740", "prevouts": ["76c80f050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "7de8e90500000000225120830a733a18b85ef4b0312c74547cd56d5f9e0c3d25a3cfe191c507f1b30d25b0", "25ab3e05000000002251206db4dad0930358a2e9f41842e1b23d91fd331c2a182c8577c549eb8d129d69a0"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_3", "final": true, "success": {"scriptSig": "", "witness": ["f812ee9391c2499e608b3e222fcdc7481e3c7f475d65a80de1373a4fb9c3b78b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["8953c8", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf497301000000676a648f636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bda01000000f3152c9f04847ec80b000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac58020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac6f5e0c56", "prevouts": ["04eaf20500000000225120faa3930e65e7d81b6faa2b2aae8805aa3d86c366939437b956ce3fbcc2c193b8", "93a1d7050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_251", "final": true, "success": {"scriptSig": "", "witness": ["1072a24350a010d19b8bfe9a743cb5ed7c3f6a772b1e19e06cf1352f0f0f09b7", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["7e4c1154ebdc5d8d4dfaeca4b481809412471e055df3f19069dbd116779e254f180ffc99ebb05395c6f2729aeeb49e40fdd8b4b42de08d07271ed8a43e0a0f711c2019396832aaef0a6e9d3ec7ed4a81593b16ed5177f8a495861ae78d7416aabe2d035b6dce47383dbe63bb15798a6a839753832ae86f4cffba8d0356b195ad6acf5f63de38ed11f8de75a4a0d51ca43ccda0c71fa90fee657de127a7cda8d9cf969607ef385026516a8f9cf983871c11e1d52a78a183dcf9ec10f15126152757a9cabdcde95dc1e203cff1b215dd5681e9b7c7364da9a8de37596e941a7447c2f886d8aacb14f6d989060b2d42b5fb1c64d26544035552b9ef9c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "256c3916036a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3cf010000004fc9d2916a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d30501000000063a80fd02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf496d0100000097c871cc011943d602000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88acee355122", "prevouts": ["7c69ec050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "b0cdd0050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "a9e6a4050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_50", "final": true, "success": {"scriptSig": "", "witness": ["bba071cd2b277c2e398ee31de3dc7fde8148743ca486eb0f0fc4b6d6a7c8a743", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["b5da3b0e35f11ea8328cc1046e862924a85c124693ee9a76a36356742e633bbf649ada23731a49010deb4c4e28325dd75bb6", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71b2010000009a6f5a86b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71a50100000032c40fac045c99050b000000001600145e89b76f270f5a3384e042389be8f4c10402492658020000000000001600140276cd59f2bc98ad777ccf7057f574395bd2430258020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac58020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac76090000", "prevouts": ["f8a02f0500000000225120bfb80c2c38ef09f1d66533081d540aa84078c139725d480f736ad9ed28e51554", "1785d7050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_23", "success": {"scriptSig": "", "witness": ["2951857cf178104b985c20af4d67694e331e9db74c216aa4fe7b5ab45096e892", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "505e71352c79b9960b5a33b99e9d18fbfa24e78eb7d01220"]}, "failure": {"scriptSig": "", "witness": ["74ba686453feed098f4bebc0350c129c54700eb13f4e7fb559ac857696b40430", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "505e71352c79b9960b5a33b99e9d18fbfa24e78eb7d01220"]}}, {"tx": "01000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d32300000000e27e8434b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7108020000007903ff0a02c5b44c0a00000000160014c327e70d62d692d5959c72b3411fee2ca31c546b58020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac3544824a", "prevouts": ["a8f5af040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "6f779e0500000000225120d5a69bd9eedcca12b487bf3f2826b2d1d5d33411360ffc47996b7d60ff4d04bf"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_1", "final": true, "success": {"scriptSig": "", "witness": ["f9e95dbd86cc392fe50a8763e938a90c87588b3a5cd9f9b881bd2d344d24a7c0", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["71ce7eb14ca0c5197572300dd8ffdfcd49148475de5ea86e39b96ce591966e4f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b1a00000000e55ad6b3636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b1b01000000246929a40497fba50a000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208758020000000000001600140276cd59f2bc98ad777ccf7057f574395bd2430258020000000000001600145e89b76f270f5a3384e042389be8f4c1040249262edde935", "prevouts": ["f83365050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "ba86430500000000225120bb7e8c3c0d590ca9e24a780cf353fa21823cf0a588d7a87aaff97c975939347c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_55", "final": true, "success": {"scriptSig": "", "witness": ["1ef2482388141ae0e469f95ce04cb45fe3fe30a49f08abd2287ba4769448579a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["8a9cb89f5663ee1d9192f5814379561cf9e5a4a9485e3b277f1ffa16aeaa231c2efb5f524a14e8d797613dccee6bbd305af8b02b8c4516", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d711900000000ddceccfcdf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c1a000000005538765803f2a31a0a000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac5802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b58020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388acd7070000", "prevouts": ["1de8ac04000000002251204df70a95daa8d4e5c145d9eff7f8ea2feb65fd6936bb40a5042381d11d9f9859", "a7b96f050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_220", "final": true, "success": {"scriptSig": "", "witness": ["fb3bd1925c208a58e5fc3277522d8187bae98ad1d65cddc23e8d756e9cdfb986", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["c59823144c0794ebee11055c97c57493916b4847d8aa68df841ed3c216c02be0fd421fbf157dc7ad73eba3eb3ba6857b38d193dd2b7c0354aeff72e6c4e29cb9e8c60d157b8616636d8198af5ab28e73603673cb2a7890b6f6df170d4898ad12c98327132e17ae7e0cd0f1d7ff078f5f2ed4dc15f0c6007e9c2dab163ce6db0fbc4dc07478dfa61a0a1955a73780165de20d533855a44eae3fd07f81c08d0511583225ca2f5d5f91ba53ffeeba27bc4e5e43eecfcc8d94a42f174a2173ed5307227af99b94e2042054ad62582a33160905076dd0fbc12de0231b04b7", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf497500000000f1e7cc91b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71b101000000682c1ac40409ce3c0a00000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a33875802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338772000000", "prevouts": ["b6859e040000000022512097065eaeb2d2aa87fba26e38f67779e0bf409db1165659c14b47e88e5fee9115", "2966a0050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_152", "final": true, "success": {"scriptSig": "", "witness": ["01ccabb4fe2d94fb7d7d8a5e2f8b17145c01e93cd692122d72c376d1888164c7", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["7476eba723c32c4fc1782b27b210ad47e9f04f4d41dc3f6d53ab331a59185d8954c638aa32d7650f3f22b78049b93c754d06a699a14a5562229d1fbf63785af720736f7ef743bc64acbbfdc8a611a19e1a6ec5e0846d1defa5e0bad74a9d82ea9a75a4a5a08e74b08717e197edb56fb5f45ce1d076da83d9fcae67f132f533dbc8e397875ac497d7fc0ee866cab01bbee88b6b0fd4a045ef", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "010000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49f90100000052bd0a5e636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b0a010000003367952501d1c35107000000001600140276cd59f2bc98ad777ccf7057f574395bd24302dd26d252", "prevouts": ["da16e7040000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "8b072f060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_102", "final": true, "success": {"scriptSig": "", "witness": ["701e752e7bef79843a87ebbac28e8922f18ec0af811513b20ad84633df4970cd", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["574d8d7f9da5a86bb8ce3c68133ce1007772b89dfa5c096dfb959e25871d8c21d30e2da024593f7937fa4c3b7027a1ed385c100b2a5cb3da0e4677babaad13aaf9c44332713a81168fceb39d49bf7750501fd6c7e305310ad9612b53f8a417d3426f3c587653", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "02000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d30a01000000ff7e18e5df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5ca901000000ae41c7a90311f9d10a0000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338758020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88aceec22457", "prevouts": ["8a13f3040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "dc7ae005000000002251206514d992213eb94be85d83d5b2b8fca47137b82b7ee822019b7a252ae48de1ce"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_90", "final": true, "success": {"scriptSig": "", "witness": ["dbac827a940bebd0be1ac11e3ec6f3aefa8c1110295196ebeaaa8452add9cb9c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["5abad564bf834b6144b701bff848fa9e17d10d28ed08744548455d477b4e1be3f70173e7680323c7aef0e94ae11f44f170bc3648eeafa08a526ba535b6f3b0ee4ef75bc89bb578ce952a9daf7c47c7cb7570025182ecf9b4745a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "02000000036a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3c70100000054f218c5df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c810000000013be67a2636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b1900000000eab45d80039869bd0e000000001600140276cd59f2bc98ad777ccf7057f574395bd24302580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208758020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac408fc256", "prevouts": ["c047cc040000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "05a548050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "e735ab0400000000225120ec67ec72af91a054e1907997b523b7ac52fd48b2fa4ad837e25a4ad46754ea92"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_9", "final": true, "success": {"scriptSig": "", "witness": ["ac101cd231818cb3dbe704eec244d637ada26a3c972dccde5d14d94afc315bfe", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["924862b8ab3b8b606bbce39af70692b664e8ba885e8845f13fdff60ee017495f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7100020000007771d2abdf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c22010000009f5e2b9202fd772a0b00000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd24302e9020000", "prevouts": ["f19b78050000000022512080ccf679d6436298235f93ee7a59dfb01de56ff7ae507d4540a3543eec0980a2", "a985b3050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_104", "final": true, "success": {"scriptSig": "", "witness": ["6d4d2d86a1f731c1271707dd4814ee40ed74a376d8a4a3c7c106e00ab9802947", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["370747bd4581493eb2182c7f155c955864c6e1495fee73e41b2528a46635778af85e8e03220b90ea55d7b6ac20eb2306aca1bdce8cac6f8ff1535af343a707bc5c8e46f287bf1b884d55db4eac717f7ebf6dd42961ad9fd2e146986367f9d695a41dfb3b31d5415f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "38475413026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3e8000000005ad2c3ff02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49b4010000005bd00489048a1e1d0a000000001600145e89b76f270f5a3384e042389be8f4c104024926580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb87580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208758020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac830a0000", "prevouts": ["3b0cb9040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "123e66050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_245", "final": true, "success": {"scriptSig": "", "witness": ["9831d9093c4c1a290d2643e8fab8492ccceb56a33cb98f4feb87cfc52d650920", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["d423b61a99385a795ef82e0dac3485f7ade67e25dcee28d754627041959134e54f58191d2c969d41f28909671dc2143a65987f8a9ae02598d7a85e364a62165b403271a4bc643bae2d3f3c7e140f7a62319b11cc4734c50139f9260d77d0f6d6ef61ddb8bd1e1407eb63b98ef1fa43d68812fcfb914cb866f55afc065b1d9988e0a41c80a686cf6eeb197bd6d9828d1a2ae3ac531b348d560995054c9713eec1e683a4757d2729239f93939dc23cd5e0b656f32c3029a0b9e7289ef9fe2cc4828d79babd2c45ed31960e2583be7e16412b08c79afef349146cceec5c0dbb514a6b1a00000bb7af14dd6d98f82daa63c6348cdcceaa", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000003636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b1902000000a8c3008802c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf493a02000000641dd0846a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3e0010000006192a2c804c8292c0f000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac5802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd24302c1010000", "prevouts": ["fc08e5040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "7c91b30400000000225120a6ee9fe2ffc739f132f18d35a0cba95efa5a60abb6c27b2a53975e649aa427de", "ae9d95050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_219", "final": true, "success": {"scriptSig": "", "witness": ["5fd6ce2681bcd79fb81bc9ff6cadf22905b1d4302f0f47630f69457eea61a027", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["aa8d74949e671db7b7759b5a491c36ef68250d2b39547507629c6d674e9d7ca3a71320d820a8138055781e7d31445b8f0d720099b743c48ef198b62df77b75d9c3669a8a1b345d8913f0046c2e02993daa5e90f8c6c0e89b4599983387009a593cda0211b6a78f660a065479a138a4575c8ad1ad585c60ab603c2948264331693894a46023365aee3063f3a4418f86c90e35358da193cf0fc7abdb936738ae8711fc5939b572609d897322f5a9f257441cbc3a150114ae8c009eff8bc71c6bc368ef340d6e65922e9dc762f02c1be72cb00128c31a4fd99b45ac70", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "c3f49c99026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d33402000000dabc8eaf6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d35402000000dafbcfef0277a99c0a0000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb8758020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac33e6201f", "prevouts": ["e2d373050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "966d2b0500000000225120bb7e8c3c0d590ca9e24a780cf353fa21823cf0a588d7a87aaff97c975939347c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_61", "final": true, "success": {"scriptSig": "", "witness": ["18f66ed5e2da4d3314a42257e82f261776414dc9e2ebb0fd60ef6f23ed77ffe0", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["dd242347d27a9ca055ee24a3addb63df43e5ee1d6291a458c28308a6f008b40882a698915bcaf3b9d4fb8233f8376f1e30201ce924e9ad7489b759d01d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000003df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5ced0000000003e1fe8902c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49fe01000000e49bb5cdb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d714f0200000030996c9c036b1c7d0f0000000017a91460db42f735e17b0d826006ad8d411b7445b1ec20875802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac00e6f847", "prevouts": ["6ffe78050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "4961c40400000000225120ff7caa3c95e4c5de622b8aa1c98fc7fd7f3e399b73404c84261ce5c6e9672a77", "32ef4105000000002251204fc195a861c8787178074f98b58f66fbee4bd7a6981677c25bb4acf2f019862b"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_217", "final": true, "success": {"scriptSig": "", "witness": ["448ffbe569a55732bdb4215e458222b390b2babafff47a93efd95c0ea1bb77b2", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["4f6335493007d9cd5fb711aa88636d59fcd6c58c1f283fde54a9c43647b0f443d2e820abb3ff93a9ebe900002c00780443aba51654f3c758c2c07ceadc2d6f1b34ca15baaf2942dbd446e6740084f6068fbbfed209e19734d6aeca61c6514640230a8f36cbd1b4eacd0e04f0bc9916a7cdd1f1d208cadba4e31b86d6468bd913a513d8a7a47028ea7bb1b9df805a4e0509bffe779775017da80104959a5a69c10bef8c2cc8e8ce7913b0db287a11a4dbbb18693708e2924253c2ff717393a6520ec1585cd6219926e867ccc31aaaa97ae46bf9d2c5d4527b5f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c5e000000004bf63fad02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf493c0100000086ded5290192d7b80a000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac8d8a6547", "prevouts": ["f966100600000000225120185cbe45afe6718cea2c2d51aee821670120d97384988cc4c2cf7ff0c8bffaf4", "1e48bf040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_14", "success": {"scriptSig": "", "witness": ["92e09876284d4ac449a5f46096f62b406e4702d94dbc2e4858a720e6573b5387", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50de993fdf8ae6016cca5eaa020d42"]}, "failure": {"scriptSig": "", "witness": ["8a9fc306badb6ab6c273484c24693fce3978d19070e6239c3748dcb3aa864ce9", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50de993fdf8ae6016cca5eaa020d42"]}}, {"tx": "0200000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c0902000000106f2fa102c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4934020000003c9e5a83037d3c4c0b000000001600140276cd59f2bc98ad777ccf7057f574395bd2430258020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac580200000000000016001486053ceaa6b6ea601bdda3b6220dc7510448595818010000", "prevouts": ["a4301b060000000022512047285d4db608faf83c2eab530e34c0ddcdc8cc019ec84b084fe32d89d95ceb48", "835133050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_51", "final": true, "success": {"scriptSig": "", "witness": ["364a52a30a850801645d4fc177110d858d4ed5a844d8e82770926fb402509f6a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["7e3afdccbdec9420e1181739c78e06e76db98a8cd5e08e7c6f4d8c4209bd8366430feffef107706082010060bf9f91b0b2c12a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "02000000036a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3db00000000b3e5a6c5636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bbd010000004fb22ce0b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d714801000000786a3c8002bb817b100000000016001486053ceaa6b6ea601bdda3b6220dc751044859585802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b460cd74b", "prevouts": ["173005060000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "70d7be040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "7840ba050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_73", "final": true, "success": {"scriptSig": "", "witness": ["a02f3e24a7ba2b05d0bd4d20d65de57c6885e6dbdac6c7e213cc6b9d0a1f027a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["63eb94c13fe8e42528ad7cfce58a09d420420a5bf9712c530cd64bf7185199dbd21a8c842a47c092ccc92da5d4a5bc41bf88f3f68cf278886f87e1325a2e6157d118dff1b61ece21fe", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "ab7e18cd03df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c1900000000795f11ce636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bbf010000009c96139f6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d35700000000d99b00bf01a7dd66060000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb87c0edf567", "prevouts": ["7666e3040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "84ca7c05000000002251207c2f23ba05a0df05c2462f9651592f6bff3bc405939b228b16d4f3a8f923b21c", "3ec62106000000002251208ea52dd5921669e851727f096151cf659bcf831a4fff67a5838fad99f6cd2438"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/basic", "final": true, "success": {"scriptSig": "", "witness": ["ce", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd38a6a253592f3bc89560b38ca138fd38c9f706c809a5fcc553f3d89fcf45aecb0eb7a24b98f8b4d99cce3fe406d5b51bc68ef5ae97d2c5bebc358d8b5b5b78b2b"]}, "failure": {"scriptSig": "", "witness": ["ce75", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3a2dfff65b7d0f0565b13a2072188894dc90140e08c8cc8812307d68bde53dbad8cdeb0de8daf44e986d19e114a7b8ed70d46e74ed21bd6c6e785c2a6747f82ddeb7a24b98f8b4d99cce3fe406d5b51bc68ef5ae97d2c5bebc358d8b5b5b78b2b"]}}, {"tx": "22454dbd0202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf491602000000b0c22ec86a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3f4010000001d240cb6014db6d7000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a33877c000000", "prevouts": ["241bcc040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "a00896040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_18", "success": {"scriptSig": "", "witness": ["f31c7c6edc8008705035c1d1cc272d9784b34f2e427985e349f41ec9bc085a5f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "5079c40f807bc2259fdc6a2f9dc978a3c726e6"]}, "failure": {"scriptSig": "", "witness": ["eaa3242f37862d43e03632940f2d429d9f348574ecb16bf7924f4925988031f9", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "5079c40f807bc2259fdc6a2f9dc978a3c726e6"]}}, {"tx": "8902093d0202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49e400000000e6d813a2df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cc2000000008f60ffd30496192f0a00000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208758020000000000001600145e89b76f270f5a3384e042389be8f4c10402492658020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac94c7b831", "prevouts": ["68bb6d050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "5618c3040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_9", "final": true, "success": {"scriptSig": "", "witness": ["abd79bd5eb20952d61f9a4b1ea13991f5ad10bc6bf7847a34d845943ede4381e", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["605507452782914233", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "23dd676e0202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf492e02000000499d29b16a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3f000000000883af98b0249e3d70a0000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb875802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e74678a33", "prevouts": ["661f82050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "a73a58050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_36", "final": true, "success": {"scriptSig": "", "witness": ["84f472e0e962082ded1ab8d5e56a9f44be36805d7159ada888f0230806393858", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["f992c2fff1fe481db0ef1977da87130a6c1b530f336593a0a437888e09465f58cdb0d8a6", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "477c39c3036a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d31002000000527d6bd66a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d309000000008cbd58e0df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5ccd01000000fb55358402d15b8b1000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b580200000000000016001486053ceaa6b6ea601bdda3b6220dc7510448595846050000", "prevouts": ["3c0fd405000000002251205b8b48b429d3707df5bcc86dfde72372228bad9ebf329df0c01d544f1b4c05f2", "c2fbe20400000000225120e419f07243a01cf29e5e987dc32985b9f04e727bcee6dd08977bedb0b339dd16", "4112d7050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_207", "final": true, "success": {"scriptSig": "", "witness": ["07f3261c6e7bd3f4c7ccb12c57f508225b98e31ab78c5ece7ae9f557f9603670", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["fee5fc036dacc73cc8a0e70f12d1552ddf05d73332db692c54c17452451e1f81020397fb47b2088a1dd8ebe6d703b909ac84a69fc659f83364ab15d9b056595d42d69790c05ab7a3d627e1c8124771546be4d0fbf0970b62990ee9265cf6e26925a1266fa5a82104619d57389a39e8e8dab491e1b5beaec2fe0548872c0bef058dd23179720654f8821626bdd5e3042a4fa79ac8fe73443303635b9681d71dabc4305b5dfa4fd6bdfb57bf6b37902094b29ddc13ee121c67277998df937f6f3b84df5d98b07ae56f70b4d5fb775ec1", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "010000000302c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf496300000000ab25c602df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c0a00000000eb5ed36f6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3d001000000fa7b08d30430b5d00e000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208758020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac58020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88acd2020000", "prevouts": ["eea6dd04000000002251205ab03f35dcbca9e1f686c649abe5fef2c57b644c870a065a421e86ddc6235dc1", "8209ed040000000022512016f466b4c47ba5a0fcfa62d31b6d2856c66f1a2da0fe8fdac21ce2fd4f55fc60", "8f6908050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_23", "success": {"scriptSig": "", "witness": ["2403504b0b535806eaa3bc8b3b12fa607ede77331d2592f991bc41696d4dead0", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50a5d79d49c2824b0865a577a1ddc5eaaaba421ecd4233fd"]}, "failure": {"scriptSig": "", "witness": ["6ecae0abe5d5dc20f8994f1bd6786adb0a27132ba8b7145f98f0c02ebcc93e16", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50a5d79d49c2824b0865a577a1ddc5eaaaba421ecd4233fd"]}}, {"tx": "62b1f9b90202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49f3000000000c487ebf6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d33801000000d51b01c203e48e1e0b0000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208758020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac77020000", "prevouts": ["8ce1fc050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "ba9923050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_76", "final": true, "success": {"scriptSig": "", "witness": ["5c447c97620856f0075d43bac2f448370288de595438b41c418283b3ea51ea4e", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["0972c22cb5fcfc030861d464465e0f8b3167a764ca07893100277155820f751f25094708d896744089890254367ad0cc1f8d4d6bcdd202918d829e9bc83cb659a6aecdfb5cdbdab24dfc7a78", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4937010000002129fef9636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bf0010000006c2f078704ab4f6e0a0000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208758020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac5802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b58020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac42077948", "prevouts": ["30d6e2040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "c1658e050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_127", "final": true, "success": {"scriptSig": "", "witness": ["afb2eafe7f382e2d042470a599d4089ded0e4b4b8e93154801e308783d16c013", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["62235e5ced4a1e50c1273906fc0b4a0b49929f99d5e884a21d89ccbc5fee6deeafd6189404222c84ff045bcfe83a577328f281acdb2046e7f9e0baee690c8714c067f079bae9ecd3bb233e48a0ff70e5a5ed192fb894a86abfa132f56778b8c37973f2ce04758efeb9e64f1db2d4c34889a5be4ef843e05ba0d556aab67eb0", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "812be3f702b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7133010000000c43149bdf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c6702000000feeb13e3030c970b0b000000001600140276cd59f2bc98ad777ccf7057f574395bd2430258020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88acd2050000", "prevouts": ["136d7b0500000000225120d53c137abc814ea3ef118522a977fcd89d55703868fd655e83ea2c680407fcb3", "6e9592050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_20", "success": {"scriptSig": "", "witness": ["8ff737e94db66d91f9b3066d46f8b4b5eb33af7822f78097d4b4652dab094825", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50f789505af46ad0e8fd025dc85792d68078e5b45f"]}, "failure": {"scriptSig": "", "witness": ["d50ca38e8943c48dc1c621d7af9c54dfadb7502ded9f970920dd5bbfe530308e", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50f789505af46ad0e8fd025dc85792d68078e5b45f"]}}, {"tx": "0100000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5beb0100000086a05b2902c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49c00000000044e985e9032223ad0a000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac5802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e25cc2f55", "prevouts": ["085bcd050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "cb80e2040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_232", "final": true, "success": {"scriptSig": "", "witness": ["3bec3624e77400e2e74de9a1fbbdae6e2e38c47a359639cbab8a51f5eea9529d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["94dd720c0bffc0461b4bf23e61a495dcff61892810eb34d91af91e1815876c13daac2370aba0046d2f0b33e6f6083209e79f274021aeec1232b98c4c18909275bdbbcdb46a645e361b072eeacea6f99d4b5f350d99769917e428507e0eaf1edf8ba400be3a5ef54221a820930b5d5e701f01c26176f070a132e694299afc60ef7f908a4ba8fbed1b5d760f6d304bd38932e85587c915648c91e1e6f00775b5f37a680fd51119543d4af7e51f77e6655b7fe04a1c70b114f712fde57e9b9127d8ce1e9603b1af0cfa0212d902e56388bb4e79fe42b071c50a1bde22ff100f1f7a86936499eeb78b1d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "07e64dfa026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d35901000000b6ddfd94df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c1702000000b4ef31cf04ee50630a0000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb8758020000000000001600145e89b76f270f5a3384e042389be8f4c104024926580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338758020000000000001600145e89b76f270f5a3384e042389be8f4c10402492665060000", "prevouts": ["de07a405000000002251200b7800d759a549d669ff8d5f924b2686a825278fb22236a72624d19d8d1e1620", "b903c2040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_82", "final": true, "success": {"scriptSig": "", "witness": ["ecc3afaee8848baa3017c843b5b1d822ef7d9dcb68a3a9d2c60a27a3df3f24b8", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["13125537d3c3295d35ed2c2bb5f771dae14af58f2ec6d5b8626aeffe6a19137f91b14d9cb564d5bd0ffb05a953bbd3982e8c19fed09f471018108493dbef4655417ea044a3aec3d9e29ffedb6c0b10ca64ce", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d717800000000c3e4f5dd6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3c1000000005faab0af044e52550b000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338758020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac79f21a52", "prevouts": ["305dc6050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "e6aa900500000000225120c139e54392c7cef91a1aca835f95c261d08f93152f54be164a62ff27db2f2848"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_7", "final": true, "success": {"scriptSig": "", "witness": ["595c9d7b022272134d4ac10046690b563ce69a8b26775c1f718ca267405082ad", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["021f8c2f653bee", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0432e38c02636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b5501000000b60d4b8202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4958020000004ea48e8c04f6b9c60a000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac580200000000000016001486053ceaa6b6ea601bdda3b6220dc75104485958580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a3387580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208777060000", "prevouts": ["549ca2050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "54e526050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_24", "final": true, "success": {"scriptSig": "", "witness": ["622246097f896a6381b37ad0db5ca5c8c39d5bf55845645b1754581b20236478", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["a160470f61c472a23b2fb1d5b7129948cbb606426dd6472467d7072d9ffd8ea7", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "01000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3b2000000000fdf897e02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49540200000059b2097603ce1c400b000000001600140276cd59f2bc98ad777ccf7057f574395bd2430258020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208703030000", "prevouts": ["fd158a050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "72ddb80500000000235721d8103542fd26eef79006879e481ff31a67ad980b893420b2253e9541a0d656c600"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_8", "success": {"scriptSig": "", "witness": ["eb83709ba0a44fd5b8dd1946d859b1b763f02eab95afbd7a4f181b67d736e962", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "502a0801193dce4819"]}, "failure": {"scriptSig": "", "witness": ["5f2b6ea0c5a73c1fa9765bc4b29c2574fb94a0802c7868b2d76ee3fda986d92b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "502a0801193dce4819"]}}, {"tx": "2c33cf4e02b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d715f01000000ec166cfbb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71dc0000000058708fb304b2e6190b000000001600145e89b76f270f5a3384e042389be8f4c10402492658020000000000001600140276cd59f2bc98ad777ccf7057f574395bd2430258020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001600145e89b76f270f5a3384e042389be8f4c104024926cb050000", "prevouts": ["e6c936060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "eac6e40400000000225120b97b125092319d98b0ad739d9949a21e0745e3bbed230b66a8fb230706ba1962"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_214", "final": true, "success": {"scriptSig": "", "witness": ["cd4a9befda53a6474139e2c321652890ce6b26bf1c958d5bc2f80dea42c86ccb", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["c03a6c3cb2f33f48d2747ff44c2669f06adb4a375777cf3bc125af6d0b00d8ce24a014d0109daa2d6b4b39adfee550228f38489b0b33559b3fc5de55667a31927988342fbc7ff935a40298747cf2b64e90edef9289d6c63628175b2e5e2f75ae31df971facb18bd5dc2c68def2972a51352f102b0a9b0a04d8318bbad540c684a885dc74f7d07ab94e94a83de58abe5c7639cc240a90b768639c4f472d878b4a257fa7a927272f9383bcdbe8d279ac6f4f4a0a5a9be58ac37c15aaded832e77ed3ff1accaa754f94cf0975e11ed4e165fbfb653e64c8", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7116020000005f297eeab8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71df01000000ddcd0fde033f14b20b0000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338758020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac5802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b67010000", "prevouts": ["6449c10500000000225120da09873d8fce7038f3312428d7d0c8cd978fcf54a6b59cd28cdc533d57b47db8", "00e2f2050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_126", "final": true, "success": {"scriptSig": "", "witness": ["87a74612d5d4af348cd51178271c72e05f3174f8238e0202d41b041178b46786", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["ccfafbb2f835d44f0dfe865d3d9065feb27adf69b6906b021555760c39cdc3a3aef136417d59e16dc62997530f466fbc20ee1ddb2508a366d4718f52ed524f9e35b6004be239ec2c9c1502142c6c4106ddbd29a0e17248d1c09170e3e2ae9db6ed1a276b96ba3535996d13fca63bf102cc59f79a5e6cb7c8e4547ae49a64", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "de27f33802df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c6502000000d1c578c4636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bca00000000ac49a4b9043d68630a00000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e5802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b58020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac5802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b440a0000", "prevouts": ["b8d4470500000000225120aa4e9abfc853fee96122382d18ca654fb12bc4ff488126b09f63615d6b68aae5", "a7471d050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_113", "final": true, "success": {"scriptSig": "", "witness": ["6244411dc7fa14cd850cc2899478edd61d64fa56109f954875ca93079c7966ac", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["4d7ee28eb7c0776e7c59fcfd4b13cff4d9ce33da579e510f47fd7c6b9f6f464885e7ca971d770ffd5840fa91d464b3945dfd954467230fe9fac28b4cb0b6b66e344e6749e5eb7d743f389d4032eb101a886a4ec103dd6d72a92245fda129083f0558ecf24c96d83acff55e8775b1d92c7a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "a4483e2003636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bdf00000000c277b7b0636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b28000000006cd03ecc02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49b701000000d3bd88bb01bf89af0f000000001600140276cd59f2bc98ad777ccf7057f574395bd243028b070000", "prevouts": ["9f3e7d050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "87ff8b0500000000225120bb7e8c3c0d590ca9e24a780cf353fa21823cf0a588d7a87aaff97c975939347c", "2693660500000000225120cef52713e0135611a92827dc02b2082e39ca6c7f6dc69482b076648400485331"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_70", "final": true, "success": {"scriptSig": "", "witness": ["a74f37ede94e211fc70a20b9d7caa20abb0992507c2e0bac42eedbd5fd6818bc", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["fe442a166fd188c4fa7da0f2b30b6e91179e628a5c70f65b233ee06dcf102c93ef8018da5d95852f33309a29c15b70724193367792335b2ea7be10900b76ea1b26f7a704f980", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "a2dd6f4002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c910100000090affc846a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d30800000000199325ef04ad51310b00000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac58020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac69a1b823", "prevouts": ["13d9040600000000225120a6ee9fe2ffc739f132f18d35a0cba95efa5a60abb6c27b2a53975e649aa427de", "c7ce2e050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_0", "final": true, "success": {"scriptSig": "", "witness": ["73782dcf071367b15b687d21f81822c540bdd27454ec1bac34d915a85bc1e09a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["f2bd605511c2348064ae980aece8e71d9a089c21bbb53fd402955c255457be28", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0f6231d6026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3d1000000005614bf8cdf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5ca800000000717822c6023b001f0b000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac580200000000000016001486053ceaa6b6ea601bdda3b6220dc75104485958aa030000", "prevouts": ["77dfe3050000000022512090bbfe0215597481aa954f7bd70bd281f8a97f33ba923ad2fd4063dd4a04c780", "71d13c050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_6", "success": {"scriptSig": "", "witness": ["39d227b179107af2a6c6857cac8fb1ee102fd063a12f5a2b4aa07e9800ab410c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50a76d7d6ed428"]}, "failure": {"scriptSig": "", "witness": ["b8ea4420bb78a98fd7c4ab65e1611ee46eda41ce13d911b535a09d7fafbc4aae", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50a76d7d6ed428"]}}, {"tx": "02000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d35b020000004e376ed46a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d34c010000005d0e2fc804c690980a0000000016001486053ceaa6b6ea601bdda3b6220dc7510448595858020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac580200000000000016001486053ceaa6b6ea601bdda3b6220dc7510448595858020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac5905a63e", "prevouts": ["99b4bc0400000000225420d8103542fd26eef79006879e481ff31a67ad980b893420b2253e9541a0d656c6", "f653de050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_206", "final": true, "success": {"scriptSig": "", "witness": ["a80865ffe2e6e28f01ffab6e8c577d38b67969e826b32831c16d0e4fb0dbd9a1", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["206b5ad2b2a07763571c1b9d6312e7d81b548807da6cd6198c7475764924edbb052c603fc2c59cd4ca0173ad5c261a27a31da79b0014b0fab9930246cde0afa8fcb670cac3237c712ae8bc1dc6176f0ed5cf16b5d70dfa378e1bc61d421ebbe766a1e1cdbb3f2dc97858020cf1fcabeab4c0000c5d461b2e8c3267808372a3636632c9bd91e18878a90212476678ce67da87aa7395710bd68a2688a1142fd05cae01a567a3319a629d931077e48db943c554279fd497927deaedbf909a76607102496d75aa64761c74fd3c00c657", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c1002000000d0f486b56a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3c001000000a82c7a3b01868fa501000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac6e98c658", "prevouts": ["19b2e8050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "792aef040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_42", "final": true, "success": {"scriptSig": "", "witness": ["05f7e85c4b3f004f0929a550a1807789f03f8fc6a7b0b729a84ae5d9ad29182b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["cb57268a905e4bf5ceaddef5ae05594b4abea565dbe517167092cc44cde13437ff1374b009ae092ba4ef", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b560000000014e122d96a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d319020000000e8e0a8a039820330b0000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208758020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a3387bfdbf75a", "prevouts": ["413429050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "3c980b0600000000225120e372be687b6d745c76d126c977ec4e32f9f61b9f678b873ce4d2a154eeb8524e"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_5", "success": {"scriptSig": "", "witness": ["4630371d18d057bb816d06f4fd5fd0f4b343ef8cf1ea83d6385570e3bc96ed80", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "506ed2f3d493"]}, "failure": {"scriptSig": "", "witness": ["082bf23bcbbf837236397196f920bf3c9ebae4a6eb97145357bfbd333d90b5d7", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "506ed2f3d493"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d711802000000cf9e57a1b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d718601000000313eb0d302a0d4eb0a000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb879eacf725", "prevouts": ["5c626705000000002251200be538ebf2ba640046dfb17a21757a6cf07353700b054b36d166606227015f8a", "cfa786050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_193", "final": true, "success": {"scriptSig": "", "witness": ["06e37e59429f1271ce9d5b28ebdc53ea427f6d3031421073a88f6ea24282f765", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["bdc86e402ec5e0794295437eac5ecd8cd809406299b86ae84710e1f373d42e09ef35452f8c07fcea28b6e45691e77e932268796836191c82619584ec8df4e64bd3707f4949a0d5e89e8a9387e48500345204ae0b26589ce0cac61237e90003a85237a621926cd119ed60494de57b19846d18b1c18474ba5b9354487f7c4cfc49bc0d7343994f986fb512bbc9f6f775e4db05e1ca1ff73ab6e3eeb77a92f319d676c7bd771277a3b1a3391c227864c179b9f56234a4c8fb7072dafe7b77075c8be7", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000003df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c1e02000000c78c5de4b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d710902000000288d4ca2636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bf9000000001f0325aa0360e66d10000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac5802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac0d060000", "prevouts": ["9513f0040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "10779b05000000002251204f3d77b569b6849e46b5ba6044d6856f289d67c734facf89248478083ad0c6fa", "8d2ee40500000000225120801f5e577a4c45dae865648a93d9d1e894a3e982d52a2769a193af4e39416b69"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_114", "final": true, "success": {"scriptSig": "", "witness": ["9c34551cca9a27010945b3b80e6cf3d56d657c5ae482e1637eacde352e906fa2", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["becc814cf5699c4b3946dfed8dbc33aeb5eaa5d2de4ff3fb7c7111ae4894715810c159003857e79d26c7fc34c87f2333fa2dc9f1fc4ef63b5016d315ec5e7c0875c6aa41e1c8db7928c13ea09fa7845e07608729da85c913b2e5c245b1ea817282ec1af6bf22e8c64e39fcdc76901afc7431", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0432e38c02636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b5501000000b60d4b8202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4958020000004ea48e8c04f6b9c60a000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac580200000000000016001486053ceaa6b6ea601bdda3b6220dc75104485958580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a3387580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208777060000", "prevouts": ["549ca2050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "54e526050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_221", "final": true, "success": {"scriptSig": "", "witness": ["77541bbd09dcb1be43b290bf6037b2056e7ae67c6c5b0629b2d16c39cc57cccf", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["6a40f1beb8253e628c310e50675f2b5efc4d6cdc2dfed1a93a9d1c8215c4a4eb73da0609a0ab2e7ac7c66aeb8c1ad9345c26c0ac4cf4695e2653bf14ebf8d5ec7ff647506c90de8193cb0e67e864fd470eac4873cb7117d453e4d2205f972bdfaa1c441ee710656938d5f6747b6362684a5b56d6ab1b5b3ae53cf060ba18bbe01f91570a72a2b0b724337df0c239bef8ec560632bfd518cca033c87a0e9c9263d76ff9e98e548960e9b5bc5049541dca5a2dbcfba9c05e5cbc1f64e9f58621cbf8e127408c59118fe17dd8b216bbf349f2b0be0a24f1149be3055611d2", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf493f02000000a523d39f02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4928010000003c4932cc023dce660b0000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb875802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92eb3e71866", "prevouts": ["d9fbd0050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "df4a98050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_196", "final": true, "success": {"scriptSig": "", "witness": ["2064c4c09939d34b6544075ceea39b649a34833e14d161a5eb403108b3beb034", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["4e4a84e12908e1fdbc9df13a484b0c807bbc7cafbf69355a6885b14ad69be62236c075a2a7cbe0f98d72b63322ae967f1bae1891b6b1059a54420b7f5c63b299b23ec47b3cedf4d502b2e3731ba25e05612aa69d10bc255cd8f0f7121ae8c6bdbdc40bd808d1c5228d846bb7f7ea9cc928d7bb0049e48253bd9403d7cfca60459bf981906e95ad1eec56369d9a34ca670b66fe9cdd1639949747f3a15c4385e7c686158ba1964ace3ef519b68da405aefc50dbf037657c8495c1cbe01c3dafe5104fc81b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "01000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d31501000000fe45004cdf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c0b000000006c0f5d9f04c76b560a000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac5802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec2087729eb964", "prevouts": ["828a05050000000022512020f87ad80e2594f1c1791f1e4bba1aa296bb996597ffa0ecd13ddf7fd686d2fc", "bd7852050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_7", "success": {"scriptSig": "", "witness": ["0475573d4dff86ac9971c49e3ce018de85906d9456175c1d1b255f6220ec4313", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "508ca0969ed8def5"]}, "failure": {"scriptSig": "", "witness": ["71fcb90d67ab991be32e424b07350f643c8014bef77d2be7efc6c63b89666412", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "508ca0969ed8def5"]}}, {"tx": "b27379ad03b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71db0000000033d6c0cb6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3490100000053ea6eee636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5be401000000e66d829f033473301000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac2d75001e", "prevouts": ["d7d7f505000000002251203f98fd29baac0743734ddb1a95dbefc9e3b5bc40a20e830548531fd74a1ef1ba", "dbb636050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "68d805050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_243", "final": true, "success": {"scriptSig": "", "witness": ["f75e9d7ec19ea34ae4c1813f78b694bde0951545357b55f693791b94eefc97be", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["dde070fc0de15e7ae6251ced9e3c4fee9601e6a4bb144899db56ff1a1bf2afc75ec680a89d3de74cbec0a0984a6f60f7d7d5d838e5b37b00e5a2c58b6d48dd0dfd208d5acf39f6f1e7b5973dd7fb97edb441d942090a35a9af3ad2cc1492022fdc2712fa470dbb370ef36d77f310f4ff91dd78a7b1825ea7b67e54bdc3201ff6359e84e3533a8361345a561754256bfd16621af3a91ec90fa32903bb5b276233499be6fcfa38f9743acf5f363ec220c99aff07a06dffa41dc0f6a105581059ff3bcf5181b5a89ec58547241b69e03d91013021c8aace849348a2498f736578ab96ec494cc1e66553fa38965ca53d2d9139d8e9", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "5514a52e03df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cb500000000b26bc8dbb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71c6010000004ce0ee8cb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d710d0000000073380885019f23e102000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac08050000", "prevouts": ["fa4c10060000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "6bf4b305000000002251202e1102bcfca588ce70cea734a59c7c036c157981a36eec09a0494471ab7c4d07", "652220050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_252", "final": true, "success": {"scriptSig": "", "witness": ["5fae812acb7e3dcce7f984a532cd44a9daa52ff88edb4f0a7e960814ea2bec31", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["4b597a8a12dd12e27bf44f34a97fcd9b62a3ac7ccfb483d9ebd2eb86e04724f7675a69bdbb6b83bbf23452e6f3b0d21c51b3fe37cca5461c3bc7570e66efefbc220823a4f8b5dc187765d5a702b9a60c7856cf0c864f2c71eca7e062f4724a6e912252f1ba3382a7d1570baa945198504e53b57cde8467c4a078001598d97b4223ccad55bece3c78da42c3f176bfb8260adfdff3beafb2edbeacefe523672af373830f257432b69174c5886edacdb5e86dfb1e484ba447d7e2a59b29c976a7718d6abe327b18e2473d233624d1f6210830d6475d443ff576d213733e20e42907a4f8262376041d8849e676014e43a8a891dc96e8cb94d1c16f342835", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000003636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b5002000000f4fd472d02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49780100000039ce792cb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71e900000000fa242dcb01b2be1a0b000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ace24e8f55", "prevouts": ["1b1a330500000000225120bb7e8c3c0d590ca9e24a780cf353fa21823cf0a588d7a87aaff97c975939347c", "6326d60500000000225120be52f06644da4d51cabd3575026d0ed2f010227fd68ac6ce16c2e3adae9f9ce9", "becee2050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_91", "final": true, "success": {"scriptSig": "", "witness": ["4d4c0f223983702e5b4b274c850bef7e8b40d44c06a7a9f8ec4ab32704cfcc9e", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["7fba80797094fe35cc9075290be9593c03fb8afaf6fb5b98c60f50c97f8d4acc02db76f577853944995f6b1e3442b26897cc77f588877fcf3d7dfc5e40912a30fb9424c25442f086a3b1eb5ecde74a2ca339a09d342e93890da67a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b4201000000de1c4bdd02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49a20000000046a73d8004c429fb0b000000001600140276cd59f2bc98ad777ccf7057f574395bd24302580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208758020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd2430275000000", "prevouts": ["281c0c060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "ac6df10500000000225120339abf1cdffcc82b11fbc85b5b003b6db4bfceb9d27df157a179d4a74a44adac"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_200", "final": true, "success": {"scriptSig": "", "witness": ["3c2a3eb8e957532e6fecac6e820147b5d73fa2a9c93fe594ebb29f9309d137b0", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["b148289962abc00830af022dd73e81f1909c69f9d0ab8e321f6f9ef3afadd5767e7e93bc53f305f664b707ebdd8c9de21eb392f96a6b8e4310615de4fd895aa69c1d531f9b76645a4f3487a31f384bf2f771f533497bb99388cce2c680247ba8e716c80097f6606c16d4c4b9c3b61c725ebaf79fc576ac91f02546820c04718e91d217179d2f3d8a5236c8c98fc6f49f89b9e4329e2f20c84de60f1799f2ab93ff033cb08e57740657aeef0231b5659927ad07c7ea8df40cd5bb53a9833953819d89ca84a7da7be7", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0f465b9503b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d712e01000000d5eb90fe636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b6101000000c4290ab602c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf492602000000e43d698b0272953e0f000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac580200000000000016001486053ceaa6b6ea601bdda3b6220dc7510448595845af8d48", "prevouts": ["f1a42a050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "1c6857050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "e99dbe040000000022512008be9de2fa3962821239154b9fd02301346584b45154ea1ac9dcb1bd68bd9560"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_155", "final": true, "success": {"scriptSig": "", "witness": ["6a27447ef9019131e3300389c6173d1573a58433b209622d439a314b285e55d5", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["8da55d49f54b708a047fbc25f51c586ff63bfd1dd5ced64a30b9897cebb30ee45d2fe2e2880b8fbfe4e99dce82caee4ec773696f075339d9ac2b7db64a05017c1d5344ecc0f9f0b982f34ea44c9fa5f674781c139dc33ebf30c7545d62c75507aa16bfb4d50cde7e2a90b8d677a2e2aac1848c2db82f4da32e7492dd4c8f108024943d6edb595d58e22ee423ee771a384ce0f8bbefa4ae96315be6", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf498a00000000931ebbdadf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c4900000000cd8b1a9104adf2980a000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb8758020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac43020000", "prevouts": ["7716f2050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "2f1ba9040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_174", "final": true, "success": {"scriptSig": "", "witness": ["f7e0868e5420def00bd54e222597447c168a1c33c16fbf87f4e0c2653d9ff3f1", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["6d7078695732ff136efd0f8da4b96f5d580a8a60f2bf61ad400ec2777fb4fe6663ed46a7567887006823430c609602469d18adc5c05e9cae3a77e0d3aa74bc1310863d917569233f7e12beb41a8be4ff41330350943b951e3e20c69cb0e9298a9360762a79d194d0d054ccab561147d596f0bd10e21b8d305f4c249a3492dd262f8ef5c24d36d11c13f78bef1e9effbcf0ca419295e7491304ae1b330b6033c3cbee10ccdb46c9e6f83a05f356fa", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "eaac107e02df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cfc010000009f4d03a6b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71f90100000021ed36b104063d340b00000000160014c327e70d62d692d5959c72b3411fee2ca31c546b58020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac58020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac986e2653", "prevouts": ["7e6c1c0600000000225120f45cf403f108ebdd7e35985e98deb6660563e4e4528e843dee28998a583a4aa3", "79c719050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_8", "final": true, "success": {"scriptSig": "", "witness": ["2f3c5011d20ad7431df85b95ddf0b2033d53df194b0040c138e9661be676314d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["108f05a87f8270d801e6af9655d3fca8265d8950c6c6205dd40a3ebf3d7f6a2f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "e482097c026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3ed0000000093f1679002c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf493900000000d891d0cc04703b0f0b000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001600145e89b76f270f5a3384e042389be8f4c10402492658020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac580200000000000016001486053ceaa6b6ea601bdda3b6220dc75104485958b2e09f43", "prevouts": ["84ffee040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "259f220600000000225120968b07dc4be7bf6c7a91e2ed2a5ab072e6335d982a84da92c70a8f27ebc9042c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_250", "final": true, "success": {"scriptSig": "", "witness": ["d2cb320ad5200bbeb26e1af727c61ba89825ba6ed7bb6badca16d82d18f5b2c1", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["e5a8c4b08a00115713296e1939f9c9f6bbb284df3f1d35f1e41f240e9904b79547e744dc2fcff0cf459e986ba78bcebf82aee02e256ef49c0c60f8483b73c9d605ed60cde97089b3583da7b08e0de805c4f9545be3e7be644deceb74861d6072121339a8b0fe830e899ac7aab8a39011e3fd0e44b7cf5b53134f4467fb6e184d7fa735c0252a5fa7e1915d9e2dead4869e02fc1d9d8f3b0c2a81f0f78d76298bbcfc746d9614b4478255ce4250e5f3cb7219a132c3ae859dc84bdbcf648bbca38db8cb2a7d1ebc9dfbbf2a7d87cda72b49246e1a19e1ddd8faef9dcc8059ad028b0080eb78047c1f092a407344bb5fb53eecc8c6a4c2be9997ce", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000003636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b3d02000000911b19c8df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5ce401000000f4c91369b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71bc000000000fb3e16804ec038f10000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac58020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88acb2060000", "prevouts": ["e41d7c050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "2bc524060000000021601fd8103542fd26eef79006879e481ff31a67ad980b893420b2253e9541a0d656", "d528f1040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_247", "final": true, "success": {"scriptSig": "", "witness": ["982b7d16bda061a7d7c39235cb94a8784914e84973852a41fd7fc7a37b59b196", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["0f67c5a6405c0d7e3747c3ceb30638f9a5455b28f6440110bc19704d06c70b7b5f17254e181eb927470e14af8e601fc260ed93d176ed17684c10376fc48b2a6ca6ebf6d651aa9483259029ac0b51544b6ba05e06faf9621895f8ad860fd3ff23a5233a032b8d93bf0735c9b38d1e4ee9e7376e9e6b001441c5f1e05356d11a1f526cfcaa2bb22c27466dde912941eb41b22aef77001a20ec77cb1f2f6e71de4d9a781bd8c9bf4d0695f07baa658357d9b04fb9c4d48556009b54695a33d6fd0ebc4a8d250ae647dbc17ff6a051148557b82ef1fc18dd4d5207b8c88457223a2a741c4ffb2922d86d69a19ee29f45221b6940eba76c5be3", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b07010000006f050ebfdf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5ca7000000000448db9202e70a300c000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb87a7f05542", "prevouts": ["e31702060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "5a7e300600000000225120753241cbc7b6034518bbff13d46d326a6ecbec017764d5c413ddc0a1f74fcd20"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_120", "final": true, "success": {"scriptSig": "", "witness": ["403312b58cf3c028419e488634505921b6f352bce7eb36fb63e9c848d529d07f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["25b3e22ba53112d6f421113594f9da023995e3e9dc8e16003ad2b036851487ffe33822d360f68307b0a4aa1a720711d31ebc75d549b2576f589447dee21eea592de4bf06415e815a056f40865a6ce80a6a84aabbdc96203a018da2b5bec8649f2fd5653777c705ac7da36f00a5be7da65c4582603c7732b7", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "546ca5d902df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c1a01000000d3da6e89636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b64000000003c3a10cf04695f280a0000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208758020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac8015e753", "prevouts": ["9de9d70400000000225120845f7406b6d822a519f3f176f5dc3a516e1b6dd738f0711ba3c59186abdfb905", "874353050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_12", "success": {"scriptSig": "", "witness": ["d243421a41caf35977f5ab2b4b213821bd3f9d235f4727730937f50efbdbef2a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "506d7ecf22403dd2a866163e41"]}, "failure": {"scriptSig": "", "witness": ["c8f60083f74030ea8ecead6e5976306b0924f52d837013b4f4c294b384c6fff4", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "506d7ecf22403dd2a866163e41"]}}, {"tx": "0f465b9503b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d712e01000000d5eb90fe636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b6101000000c4290ab602c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf492602000000e43d698b0272953e0f000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac580200000000000016001486053ceaa6b6ea601bdda3b6220dc7510448595845af8d48", "prevouts": ["f1a42a050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "1c6857050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "e99dbe040000000022512008be9de2fa3962821239154b9fd02301346584b45154ea1ac9dcb1bd68bd9560"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_44", "final": true, "success": {"scriptSig": "", "witness": ["cc57cc03419ac3bdee66a13c13c7e6ce11048d46dd60d9345628491e9cb6e926", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["f2bb3339a457df1775a6b16f8457dc1f53c26a1bb2014db26995d4a020eceda0cbbdceeabff33b1357acbae7", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d715e0100000018e668a56a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3730100000056504ac504b077b00a000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd2430258020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac29726226", "prevouts": ["f2a5c6050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "93c3eb0400000000225120b34b85c875839be471fb202fdef008a0e62339543befb8a8cc46ea5d31327c12"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_128", "final": true, "success": {"scriptSig": "", "witness": ["d064e6e0c69ad002a7f37e0bf06c2000e8518d31d47c726a63951b66d49b1b7d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["937248df7c1865dc2f6c32e8691fbe35396a11db7492e8037a05d2a979e6bcd2eb994d77562f4b842cd000bf6af6227edd9ef4a31df61e77b8fdf0d9630d7afe7df557f5de824a6cde07e090cbcea3088203182a6c2b4c515f4b9de7e5455a6235ec4733a7527e604c64ce50329ee472a3eff8df9547026be2db24f6fc409e1e", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "01000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d36902000000f7cdcbe2b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71490000000036b8559d012fa5d005000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388acca44d668", "prevouts": ["9e6b2d050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "51998c0500000000225120faa3930e65e7d81b6faa2b2aae8805aa3d86c366939437b956ce3fbcc2c193b8"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_62", "final": true, "success": {"scriptSig": "", "witness": ["5c803b0e2ea0d99d60ec8a87406cbd16485f3777bc34b18d4029d4848cb952f5", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["250d6675e1687f494ea12b897b144a5b1601fcc7012d3f15cdc97b7602f8d6423fef31b63586987d70ee70e8c6b5bd0f33c902a6eb06267598955a339d78", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "74f64ba8036a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d32600000000f742fcb8b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d719000000000be1d13ad02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49c801000000d16177e702dc7b6310000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac5802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b0b060000", "prevouts": ["ae52e60500000000225120ee7a5eee6d25348914812529d37d39e46f02c0078439e33b19309e6d0c3f0c8c", "8dba33050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "cd284c05000000002251208afca9529fc2a84b5340cb811b38efd391132ec270d8475a881deee3f9b08b8c"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_121", "final": true, "success": {"scriptSig": "", "witness": ["c05613ec47696857b3a2e2f13dcd89b160f3c2e4729691c81cdc8a175fb2a4d4", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["32d4fec1616241151e1bd10583608112f116234205f83704ef7e351b50064f24f565b3fbec965c907c209401f6c1020d9bc71430b1951d01696c59349f853046181d11a1fa3a4c45789f10b91e1e5fd01a38ae4f64cb515997a7d5dcc3e8fb285aae1e6969e16827aee954ade83202696eafa2ab50e86bfa51", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71f50100000088fea35fdf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c3600000000d614070e027315510a000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388acb4060000", "prevouts": ["b91e08050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "58b34a050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_18", "final": true, "success": {"scriptSig": "", "witness": ["d680b1202799294a202f11eb9ee701127e80ed4381f362f3a07ec680aec1ae66", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["d1e2674c66344b94437ee9af3e6616756de1", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "adb55d5c01636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5be700000000ddab57f00479a9ab04000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac580200000000000016001486053ceaa6b6ea601bdda3b6220dc7510448595858020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac58020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88acf0020000", "prevouts": ["00a5ad040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_38", "final": true, "success": {"scriptSig": "", "witness": ["397e43372c3af2b58ccf767014f722a48fcfa4256130ebe7fb9e5fa81d6c1c0c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["a14a3b5cd9f81499c5155be6bb0f8f1d952158f327addb795c4da5105d1386c2460f5ae42c33", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf493802000000c7df27906a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d34600000000e02e4f9601bbe3b509000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac9e89c15b", "prevouts": ["c7cd5b050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "417601050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_231", "final": true, "success": {"scriptSig": "", "witness": ["c6bbbc6fbb8a687957a47f9eec0c305b37e90781298cacee90ecfbecf2598e31", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["1626b7c891f03483ea243c0c54d54dfe28d8320ef945a60b87979526913fcf4d0104f094b75626222005cea4469527969219bf2955c7051c78a96a1f0eb86e938da5fa879d4a730439b6db7c92542267f810ced7d737ffac68b5ea37249a5086266fc3a626984835e27f4cfff63a7e6ea97ee63f1fc91dd99351ca767341b65fd65fc8a0adadb864a3410971904f6e3e475da6c457f3d8a2b3f42d8c3294fa66eef8da187c78606441f79b95ce734846bf5544d7d5cf12ede77d365a6f74d9235ee5816647a23ddd1034ebd83892ad5fa3402e13238c400dc1692aed48354310f3465c4691326d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000003636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b1f010000001d522f92636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b2d00000000d0736b9ab8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71ed010000002b4244fc03191f2411000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb8758020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388acc6590d26", "prevouts": ["4ee1db0500000000225120a576f86cec4c2394974d9e1c31b93aed490a73a505154a58f81fd67a489c02a0", "36f71e060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "738a2b050000000022512062a14289e1f3f2f5844b531989c0b0255a3350bc088840082786a7e6d9306e86"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_154", "final": true, "success": {"scriptSig": "", "witness": ["a0e11a6a84aad7a662f04b1695609163fb4856402708a42b5ab124086f959d88", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["1c72f431f02ca6bc303af72ebd7bd051b543f312bb0ffa21d15547417ec283f7cabfff0adac3aa767f40c856fd51be9b9d5bb66f5613eed4cbde4e52372df79828017715d1783c0ed2b2e9835d63d6e08794e33efbe91c5ecc503d3a8186cdf99c4c968b76d2d3568aae32c0acb06425023f770f00b17871f55ed387559186211225618164b75a77fafe3d9623374412ebda8829c99647ed23f2", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4904020000008c08b1b46a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3e40000000059bd3ae003f88ad00b0000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb8758020000000000001600140276cd59f2bc98ad777ccf7057f574395bd2430258020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888aceb000000", "prevouts": ["e1cfe50500000000225120d65e92da0ef658a4db1ad73c022666508f5b3c7113c9df2be119a6939253bef6", "4f81ed050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_233", "final": true, "success": {"scriptSig": "", "witness": ["3edc6f3923ef3621eece71ce09fee3b0b5c1e21a3932d6b65177e28851d3ada3", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["a18d1f1141f725e34ea7cfcc72ca28de31a7d5ccaeb82054fa761ab753745fd81e7ac7d1f3705b8a4bd3f597176139520265b2c5ab1bfbc445a0c4d811af9c346d6e453243d6eadc407184372e42b23b1c4e7e973de4ebeb8c78115219d524d555276e7117f61efe5a3141d9e8c4d7a50f5f21e78b55ed1fe10d41d0a6af28e32950e2cb79ad6c5aead32f374cb24b09a8b170fe68ea69e8bda3f533dce057abc449e01f303ba030bb5d78b141e6b09830f5a866416413b60deb1886f77ee5cfe829974c849ea21b2f439845df1ad6f242d9be54c34aa6f2957cfd8dc427fe58536071c1dd3ef19486", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "c5c0ab5c02df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c6b0000000014782ed2636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b3f01000000eb1eedfd038b1a480a000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac58020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac6bdacd4b", "prevouts": ["199abe040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "78318c0500000000225120db29754ed2e3aa712b2d465424f59225ef90e7ed1db91954b2b0b6cd836f21eb"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_118", "final": true, "success": {"scriptSig": "", "witness": ["477d2b96784ead4fc9e4ff800050e165fba5e26b5633e228535e469b8c2bdb3d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["7d1e556c5fd6b8902b25175cd255ff56a854dfad6191850ef7212bfbfe254d82dbc0d70af3d5524db3c77f5677852e8f7234bbd4652b259e40072dc303bb4be3bdee85cf7f83372018a8095c39e18ddadaa8e14e008696d24aeb6bb8fb27b926f1ebe1e211dceadddbea4407a0892b0b306647b1b858", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000003b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d710a00000000499f67a9df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c5401000000e91b5ae202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49d800000000312d09e20337c4341000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac58020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac9c040000", "prevouts": ["97ee220500000000225120b13ba20c4fd1dd8dc29c377d0abc896efec7957488ae9de03e92174b33c94e8c", "9ee250050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "50dec3050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_22", "final": true, "success": {"scriptSig": "", "witness": ["a7616b64f606aeda4f593e426e71b6052f64fe3b7909bf773aea510b61611426", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["2b49defcea6e42d888e0532de4ce9520873907984a857e0def4710b942aa6968", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "02000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3d601000000990360fd6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d35002000000638264dc034311f209000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac5802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac06090000", "prevouts": ["441e37050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "1c2cbd04000000004341047bdff53a177bebd4c66280cbbe0819e46b911d39a45d8c72fca4f54dcee8127a538cb4e394a0b102398bee0f1d7a94fbb50ff6980c6912e62e48d87fdfb2b193ac"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_22", "final": true, "success": {"scriptSig": "", "witness": ["8153beacd414eb3f9bf56c26f60df85b5f4b0fd58933cf5ec2b49b6830999b44", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["c5a8bfce8f0644513cde157e1dac34b2f91d29eb0b13", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000302c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf492802000000678463ca6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3e9010000003beedf82636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bcd0100000053c533c4034cc2a810000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb87041cb239", "prevouts": ["d9e9ff050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "ae00380500000000225120e9b5c0b653527417e3fbac8930e934c4f9a391a0207dd6f0afd48d3742617a46", "a030730500000000225120db8fdbde80d98b61ed97a3f3d977005e23d455f0622ed1be03f295474d6e915f"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_2", "final": true, "success": {"scriptSig": "", "witness": ["6826f61bdd0ae0c6ffefe7f9c084e806e51e610fceb475abbba6cb8a906554a3", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["a0077881464dfb932b39999abe5f3fe94c4b5a5978688b6e933c418d1271c59f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "b4cf0d8901b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d713e010000004b8f84cc014673b30100000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e15010000", "prevouts": ["188dab050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_93", "final": true, "success": {"scriptSig": "", "witness": ["6344f7e46a4d3b3c7acfb574a821f6af4799be9bd925e4e8d67f3d71bc2bbd1f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["276cd3dde637cbf0f1a57f4b8eacccf44a9cd1f48f6af2a642d417379326f3d09fccebfa6b18eacb7d5c2023013288904d947d624888ecb77f29bc1e0704098cccfc070919fce4e73c7b6fcdd0b548d95738ef1efcd31b3bddb23f9b4c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c0f010000004ccc0f6f02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4956010000009177b55201ee4ee306000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac91060000", "prevouts": ["13e589050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "2eab3f0500000000225120d0425c23886458c1852be33e2d21b5179de26c19100a418dbf3c717ff17799a1"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_228", "final": true, "success": {"scriptSig": "", "witness": ["ca12bbc9f23385cde538ba19b2d61f8b03f2d9e779a424aeda37793c7f371ce5", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["60a24f19c837cb46d8329c5baee6dcffa5b34b15abe58dbe04b23ea311630bda360f549af845d6b55a046e717328e99641743b8f05f56745989942bde96f7aed812900c8ccb7a18279e297d23cf7a11dda467e3ca816ef48aa4653f63126ecf485b625fe35c37a11a4470a35160e511b6a2f64d5a263293ed35490ff1c8c95798144b5f7cf4183c21cff13c4f3cf97daf4fb7c8ffccf659b073217803318f98dad53dbd7402c37b5dc6289c04b992d92aa28f788b55faf35add60781cf5369f664d6784c2b249b30be8fe0553ac00eeb7da78dd5cb1879c394394362e915d6d62e3681b1", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d714300000000af9ca9dedf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5ca701000000667e778b01a116e501000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac52090000", "prevouts": ["09fbda040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "476e270500000000225120348e2be7446b82700fd8b5317793c40ff5d97863329e9960884d3c06e543e644"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_137", "final": true, "success": {"scriptSig": "", "witness": ["6c6a1beb71a0bd08b7e21fba910394598d4b8be33293406bfc73b2aafe78568b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["44ff97d6f71acee8a7035cc8b7f19d500072e7e65251563800de6d503655be7e24fa0f4f4366963fcb6ab52b27a1763879843d0970662c8f03c321571f15acc63569cd6bbfba7821a6ff593473160e5752262e7f84174ea0911ccbf88696d2d7120180cff0ad719dee64c205d334af68025adcb14dc30059e0cafe7c077a7093f903fe16026eb796eb", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "1e7a0e4502636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b9001000000a605fedab8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d716502000000619293d504c809d60a000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac580200000000000016001486053ceaa6b6ea601bdda3b6220dc7510448595858020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac62030000", "prevouts": ["4da7c20500000000225120938f91f21f84985f9aa1eeabae616adefb0d48f75db5f9e4fc147bc299fcc8a5", "3d5815050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_204", "final": true, "success": {"scriptSig": "", "witness": ["5e58646279dfb7199cebd9b9491fbaa9b58b9f683acac4fdadc102791f62cc99", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["acf38b053d1e2c9f6e0605d663e2202beb582d4da6e881299b44712b71a7c83ffb94de929bea1c3e577e8f612eab30cd07e4e6f83c96642cd8858faeeee759e419ec37a94b9266f33877755ca9ce5c5cf8ece2a1a91c0a16be352a99c19a930ca524e578643a6a016ce284fd8266cab30c7d68ac94977e39eb51317fef7f41b6e28de12677d73ccafa16c0c9a7cfc2963c38b2529063aff4660ddc636fa08811e62a1f03f0753313a88212e438403960ed4423ff5f8665ec90711503f18d1b473895247adcf9f842ee67c75c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000302c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf493301000000b4a35890df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c0d00000000c195d08b02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49f30100000088e3dcd9033f8c8510000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338758020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac88b56737", "prevouts": ["848099050000000022512062a14289e1f3f2f5844b531989c0b0255a3350bc088840082786a7e6d9306e86", "94d71a06000000002251200cc62765611fd72a67fa1c6f0b67585b8648bc26c4ad0eec7968194c906a9056", "cd9dd3040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_64", "final": true, "success": {"scriptSig": "", "witness": ["cfc33a09cb6d9a9365c4c45c2adec462837064533088e9fa7319a97bca565d7e", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["97ffb4cf137b3482ac80b855ecb147479c5415eabd7a3628d940a484b102310ab018e57a59a55d27e3cbe39a287e7f3250279759dd1d87fa1b5d9c226b786336", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "010000000302c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49d700000000022c7f5502c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4926010000008825bc53636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bbc01000000b2d7e458017bf9e50e000000001600145e89b76f270f5a3384e042389be8f4c104024926900c0000", "prevouts": ["26e68d0500000000215d1fd8103542fd26eef79006879e481ff31a67ad980b893420b2253e9541a0d656", "3163350600000000225120e9b5c0b653527417e3fbac8930e934c4f9a391a0207dd6f0afd48d3742617a46", "43ca73050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_1", "final": true, "success": {"scriptSig": "", "witness": ["ea66caa21ff8fcd0b338e3ead2f9b8512078310c119f373cf31d2b7463ab265d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["ea66caa21ff8fcd0b338e3ead2f9b8512078310c119f373cf31d2b7463ab26", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "a45de6b203b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d718d01000000963232f26a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d32101000000caf0fb9a6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3eb0000000021aa018602e13d9810000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac91000000", "prevouts": ["bc5c97050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "ed27a3050000000022512025092df578254c31fe4066670eb3d98c4d225346a54b6d19a6a55eeeed80dd2f", "ff775f050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_31", "success": {"scriptSig": "", "witness": ["6e63a0f6a090f5403512fe6e613d51e2c0b8c1228980ac54fb836621dc79a297", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "504e31838b31623b61fe688c3d15ca0eaa7fbfe31063497ed736e7ef8f1aae9c"]}, "failure": {"scriptSig": "", "witness": ["428ea5701592d09445431b0413af8d741b83c84b75faf9a4d5df8b688ee27257", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "504e31838b31623b61fe688c3d15ca0eaa7fbfe31063497ed736e7ef8f1aae9c"]}}, {"tx": "0100000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d715c02000000a492046cb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7154010000005d3556a90434b4d70a000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac58020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac88060000", "prevouts": ["f4091d0500000000225120f8cf05b144d6b912cff9220968e97e85ae8fd42929f3eee40786194f29ce5f40", "f2edbc050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_16", "final": true, "success": {"scriptSig": "", "witness": ["b678584ffc0900267c177f4814ea6d1bd18e62d0d0bfbfed0df7b001db5d8f23", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["488b675ba3dde85ca9c4b81e59a3519db8d615e3fa69da2c22c9339c59f3a968", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cd001000000131e5ef302c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49fa000000007ca3069f027f68e409000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd24302897f1b57", "prevouts": ["18faa8040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "523a3e05000000002251203cab2ea51c96c12f10d05d3967d3ab54339ed5152b41a9a913015a9cbf11dce4"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_111", "final": true, "success": {"scriptSig": "", "witness": ["cbd7b623ad2b76f7dccdca512d5455cae5744a42356c611a196c8159900535db", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["0eb668c5f2305d87eb0b32003654ac139a87ac48e5baa7af366d3effe9dfbe1f031693bc621da566ee21cd615cc52eae18de3c0c61a37ff1d289890d96104f6ed6457cbd943802a0340649a78a5688f770e1c69c8ba77d0562a6c3d5790c7f271a334dc72cd2dfdb9c22530c3a738d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf496b00000000dd5907ea6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d32901000000f31609dc02372fec09000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac96090000", "prevouts": ["c37a13050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "6e5fda04000000002251209f9391a1a1cbad70e9458e6ddd6a6f3c48e46fea8e5133e3d665ab1e3fd1ee29"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_96", "final": true, "success": {"scriptSig": "", "witness": ["9794a12ad219d1d6e18bb4350da868fd924243ba46770bc3ef59863f2b4875ee", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["ae41e38dc15d0c88e6413fcae55c5878a390171af1ca8d5b1c7a0b595bf5e6273038702266d14291c0587cf174dc6ddc0d6dc7d3b8302f48e088af52411ee587b686028e12e5517111c3b5ab1196ef5c7c1a90fd43596333b1d554a09818b043", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "351e91c002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71d70100000061a9c690df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cfe01000000c08665cf035206160a000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac58020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88acb3c61d57", "prevouts": ["5d74e9040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "bb902e05000000002251202b3e592132d47f4d2d3e51edb33e9164cded46eb146b86b12a068fe5729a7f7c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_15", "final": true, "success": {"scriptSig": "", "witness": ["b8dee5658a5e061b9596d4c12bcab9d0fdbf7ca56e0529e91973e94d32647e58", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["133fff364d28a04949b9bb71794c3c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "e19f25d60302c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49dd01000000ffd6da8a6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d33900000000b98feccc6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d34601000000e1f355a104d970661000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb8758020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988acbbc63135", "prevouts": ["9fae770500000000225120a576f86cec4c2394974d9e1c31b93aed490a73a505154a58f81fd67a489c02a0", "00d9cf040000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "8b8820060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_31", "final": true, "success": {"scriptSig": "", "witness": ["001033ee2eea96675e0f4a2716e4a96dd5d2be7ce708a5f713a544d2bbfb476a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["e739d32ed4ee2c94535240858f6e0c5e7f400004fab1a45b88e7879f2fe304ef", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf493d01000000547112b76a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d34b020000009df532c602d8d0580a000000001600145e89b76f270f5a3384e042389be8f4c10402492658020000000000001600140276cd59f2bc98ad777ccf7057f574395bd24302a7020000", "prevouts": ["159e50050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "c7c40a050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_30", "final": true, "success": {"scriptSig": "", "witness": ["c4e9e980cf30f355e1a2ea4186e32f9bd9293de9d6cf3e20e0ea21ce58579644", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["f250bb30bf8f8dc2b1f872ffbdf49a9c13a0830c77094dce0f47cbf01b7f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000302c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49c900000000490d7695b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7131010000006a70fccb6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3530200000083b835ff0348a0981000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a3387c8cc3e39", "prevouts": ["26b8d00500000000225120dd05ddfa12186922f66a8ec41dca157ada848c6ac616648cd66825a343daf907", "9de56f050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "d6195a050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_60", "final": true, "success": {"scriptSig": "", "witness": ["2078ac8cc369525acd795020e87bfedc9985ff0362ab6961a61289bd627eb7d1", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["a07676eef442947f88b082043b6e4bd06ac667fb788e5a7ab7923e9601a47fccf6a446c5f30c99c0b334b0a4d50d7fdbc989f45ec3f2053a4721dbaa", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "01000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d31500000000aa0eab80636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b9c01000000fda3bbbe01b9c57405000000001600140276cd59f2bc98ad777ccf7057f574395bd24302c7020000", "prevouts": ["b9035d0500000000225120336d28a50923071cc316b2cb0f5c22c25228121e5d381afa657eae99f1ec790c", "2d44c4050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_20", "final": true, "success": {"scriptSig": "", "witness": ["ff7a4d28312932f68ee1fa7d6426e5c26fe9edc6d70b92766597790d22ca9502", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["e91e6a72b30c9fa07d2f8c7d905e64be1700239d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "02000000016a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3c7000000006d45f2d301776e7905000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88aca6960351", "prevouts": ["7fc49c050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_17", "success": {"scriptSig": "", "witness": ["6f48550a58cea4d2d0465bdcfb2e1cbd8d7e65ca57f236d3b60d849590e5be53", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50f1da3d61c31da509e4bc704a57ac25a5fc"]}, "failure": {"scriptSig": "", "witness": ["cfc797ee009dad086b50e1543fccc5156591047a840af737cf59293f53a871d3", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50f1da3d61c31da509e4bc704a57ac25a5fc"]}}, {"tx": "0200000003636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b2500000000d22993e502c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf497f000000005112c1bd636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b86010000008ccbbba702da98a31000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388accc34dd24", "prevouts": ["85548d0500000000225120763885cf750d2d0a7655727575291a596a6683531378a214a148a3e1bc60cbae", "9bb243050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "253ad5050000000017a9146055e93810b082b4ed1a78beca939cff2ea6692587"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_53", "final": true, "success": {"scriptSig": "", "witness": ["b0cf7c30a692c649dd6f1e1caf906bab7c64d09c6ed04f969cfdb6617631ad10", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["f84c135a2814a4b58c830eceb9a722de555b0b04306dada79d66ff251116700cc06f4ea7beebbd1310cab34328db8670acaa27695d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c2e000000001af46bbf636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b6301000000086875e602c98e6e090000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208758020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac77399058", "prevouts": ["8ff8ce040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "2c8fa2040000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_158", "final": true, "success": {"scriptSig": "", "witness": ["9429dff64420e97001b141db2b2615800e98a11d14e80cd6abf8b56f189c36a2", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["a40a898c88edfcfaa7bb29697ea5eba76faf0433a2c1700d75cf4b4e86511b70b5504452c8bdf1933bf978730adef4a22dcb94be44313b130e23c1f99a1c9415deaf6ddbdb014d8754c63e7c0ea4d3ef2889f0a3b5061bb06cdb53d3ded10713e2b3ef96d9b1e50ea790448d671e16c33e8d70703188391bc699654c10f848ea172e0eec5af4e3010c36c73d3a82dfddf74247991c8c8cc33979aa906c64", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bd90000000065f5bf52636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b1601000000f31e64730463d2d909000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac5802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b58020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd2430249010000", "prevouts": ["2396b0040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "5c352b0500000000232102d5889fd2d3c0e58e6c4c003e38c5d0a0d170ddc33accc5a3ac3585329eeb0473ac"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_31", "final": true, "success": {"scriptSig": "", "witness": ["718b7595c744726b5da97c292ff774cf2fb4d50f331e0e47123b6186580ff04b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["1a387224def12e73bbadf525dddf7973bd5f963d68435eaae62fd3ff757ab6", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "82107cb503df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cb700000000a33948a2df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c1302000000707ba6cd6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d374010000009499aba403306f9010000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb875802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e9462d961", "prevouts": ["a008e0040000000022002085979fac9dd1a0ebaa6528ac118e6f3c489cab4019bb673e80e9070a73070003", "2a2711060000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "3760a1050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "compat/noth", "final": true, "success": {"scriptSig": "", "witness": ["", "63ce6851"]}, "failure": {"scriptSig": "", "witness": ["01", "63ce6851"]}}, {"tx": "0200000003b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d710a00000000499f67a9df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c5401000000e91b5ae202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49d800000000312d09e20337c4341000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac58020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac9c040000", "prevouts": ["97ee220500000000225120b13ba20c4fd1dd8dc29c377d0abc896efec7957488ae9de03e92174b33c94e8c", "9ee250050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "50dec3050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_28", "success": {"scriptSig": "", "witness": ["3ca13d7eaf5433f42d97b6bffc01fc5d07caed0cc5ced02050467a395252944b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50ecd42dab865c6f8b7edc9a39ed4957b3653ae6b475406a997838895f"]}, "failure": {"scriptSig": "", "witness": ["b882266ec5dd8134ec09f22160a6a441a8fae1d81842702ea5694f6ecce79a03", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50ecd42dab865c6f8b7edc9a39ed4957b3653ae6b475406a997838895f"]}}, {"tx": "0200000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cc9010000004894ac8fb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71de010000005b1623b202a5741d0b000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd243023d070000", "prevouts": ["dfd040050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "d294df050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_112", "final": true, "success": {"scriptSig": "", "witness": ["a8ef424f3e6f5d652be0be5704263a04094d9fbbc38a59d824c49570b383a856", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["026f52670ddcccfb1c480e8bdb195e5d470b574f25f239b6a0753de439bfc37da9866cf9509606d2b918eba9dd0739f995c174f27822c02d509272c8eeff1961116a4f5e62e29eb870e16dab8eb791486ed1363c13e837b025f96385f2e6535303af7db60b33abe9b06cdec39c2e722c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d716d01000000312081f3b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71b00000000035c2caf5025eb9060a000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac5802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e0a090000", "prevouts": ["efbd3305000000002251201596bdaaa4f12ba1eb41adf96afe3cdb2a693d593434e9871eef564ff3125210", "783cd5040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_255", "final": true, "success": {"scriptSig": "", "witness": ["f4b9a11d855600aacd77ea78b6a8078d3c89ad324bddf9d540bb3e64080ee803", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["c8acf6c8834e64562780eb6d9a4b0bf9f082bcf99827f7d0117de10fd1c5031afa00526f511fb0d1448b7d89468ed68960f4f4c76b6c675b99779db6c4a8b07365f9bffdce5e6f04f3943803a9edc7ee208506b18cc4081af3bc41bf1fe9f1a08789536e2fae9b2ddea6f28c3e6b1673c44b3bf87eb7bb1edd043eb148b1c047416050d4928ff8c7a36b13525c07e90b00431edeee0d17bb6d9fdfb32453c94539d870cf3e6f634eec294de05a7009e7ce5c47b7e7e94e39feecb07d77c9d0606e67db6e4f67c0267e74718187c9bdf04df8dc2189d5ec4dc2d56b67c8b48a47cdf41a748c0292739496ee6fe8f5b141c2916dccd6b2633db0796a713e2ad4", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000003636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b1902000000a8c3008802c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf493a02000000641dd0846a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3e0010000006192a2c804c8292c0f000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac5802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd24302c1010000", "prevouts": ["fc08e5040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "7c91b30400000000225120a6ee9fe2ffc739f132f18d35a0cba95efa5a60abb6c27b2a53975e649aa427de", "ae9d95050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_29", "success": {"scriptSig": "", "witness": ["f348018322d8422b67a584940129d52247de57e6d59251238d8a370a6057c898", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50520f6146b673e6f8f4adbebc3cb26087f1595ed6f9e588479a23fb1a98"]}, "failure": {"scriptSig": "", "witness": ["2853ed77dff570c6fd051d959af784a10c18eb2f534bf01850b8486889375e6a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50520f6146b673e6f8f4adbebc3cb26087f1595ed6f9e588479a23fb1a98"]}}, {"tx": "0100000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b7801000000bab6e613b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d710a0200000068063903020e3fe8090000000017a91460db42f735e17b0d826006ad8d411b7445b1ec2087580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338757030000", "prevouts": ["d586b2040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "883138050000000022512017482d0d7bb44c8063eaa9ad5e8ff4b0636c623b7941bbfbeb9a290f824dc167"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_1", "final": true, "success": {"scriptSig": "", "witness": ["c849a07603d268793652a35a3b924ebc1774e773d1acee5ca70ba7947e37cd17", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["c5", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "9ab6643302b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7168000000001ff528b2636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bf50000000086f0cef1048555250b000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208758020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac7312c957", "prevouts": ["bd92fb0500000000225120f3fc65468bbc9fa3490dc9d1ec97183844986c91e8fbb61228bc5e5b500e189f", "5da22c050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_157", "final": true, "success": {"scriptSig": "", "witness": ["782f97b88dab0bbcbd33e08d76c4309531347e52b8b2c83c5143e8b7e6a72531", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["0406ebf0dc738331f1b9d3d9a8ab9bae8f36aa66817c0b93eae72686036607da95f83ac9be53d5978cff6cb4c3ebb5257652690d568ec4a9cdb3f4cf458274b52332d6b8d3359ef8debcb9a3dd10f1e8480c674f2d48b5a3e95d78453026841044495040b495380d8fcc343496573603f658ebf8ad9653aa2d3a48e3edee3cd8897a64a314722ed6933cb693b6cb4a8d8379cd2a04e1e0a8d723c70934", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c3c020000000094917bb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71cb00000000ef08497202574a3d0b0000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb875802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e718ae32e", "prevouts": ["e6324f050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "9a1df1050000000022512079cf66d0f744299f8698723106dfe92d941a0207f397e35626f3041039547227"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_197", "final": true, "success": {"scriptSig": "", "witness": ["9aa37d563856e35db8d97d94b877c242b15d18a020d4581a2b70a9ec0e7dd1b7", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["f36921357cc8942cd478fd7fd83a652890d54ac609640a8a64658ca02bafa0e53de1be7400adbc1b645be9846149abdc651e6035816e4f97cfb9c184fca9de112d0318e78a324dbc7c2638756db95d5d7a06f8038a8df9a4d03de4239cdc93e90bcf602877ca8734f4478c810f5cb42300611aaee2d0e018660a2ecbd355438548819710d64834dcf5456bd70cccf77be1dfd09c93b50f0262b39b06796c09d3b5f319348869938e215d78fbc92129cbf2b2afcc57bb8d9b269bfccd41e0d720dcc4f0cd22", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "010000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf494a00000000ba291865b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d715a000000006c05949503476f270a000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001600145e89b76f270f5a3384e042389be8f4c10402492658020000000000001600140276cd59f2bc98ad777ccf7057f574395bd243027d0b0000", "prevouts": ["1e0f5205000000002251207fa8784aaffdf8334156b37341025d4eb46234dcbd6b296da620073693af2aba", "072cd7040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_86", "final": true, "success": {"scriptSig": "", "witness": ["9fc6185f75b1509f13e2d1b5ee0acdb9b29d2b20adbdcd8bb2dcc5aec3caa8f1", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["14e631728614e7b7ed43412c4f3512a495651bcd8557ef3499ffcfd29234d07c5859548352480fe281e08c956b40416fae66165aabce094b6f0f8933d5806fad5539198c679ad6774bb473fdee54d6ac0c230124db29", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "b8f160970202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49b700000000ab5e5ac9df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cf800000000f5bec7a20486b8fb0a0000000017a9144657010e5cf55af6acb627784c227caeaa0f0a3387580200000000000016001486053ceaa6b6ea601bdda3b6220dc7510448595858020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888acc93bc833", "prevouts": ["590dec050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "de9011050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_172", "final": true, "success": {"scriptSig": "", "witness": ["713ebb624aed475ba0c5472dd8bb431ec2f118e9e673f94236bd275782c63ba2", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["05f28865758404d27835449ef62863685ad62092295ded8c5db4213442d09eedfeb02ebb3e044c9e05c7845356d9d5f6136468b3ed09094cbdb4bb22bc51d60b7a5d23aafd2aacb9467de00a8a49c88f96e3c27c0b151b4472b863a314db84c41de7424b6fd41766e0d130c443cb21128d3107f1f959194eebaa3c7e82694cc0d644c9a184a947a2787d52ebd7bde0e753eb354b8d32658d89fc29b7f190ee9b21dc4f12480f889a09af7d81", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "01000000026ff4d0597576f422f7e67d21fbd66fdc0f38e238b7013ec87f4c2e8256f275527e0100000008ef3ba36ff4d0597576f422f7e67d21fbd66fdc0f38e238b7013ec87f4c2e8256f2755299000000007310e27f0237d6d3000000000016001465adf9aaca6e26145b30616a57f580c1969dcc52580200000000000016001406bba02abe3c0a51d850edab7a2f26cc4ba9cd4a05000000", "prevouts": ["8b31700000000000225120fe21dc8a3031c7820ac95088d5a593578e2343e6b1e4bbb911124751495a82d0", "dd6765000000000017a9144f7eda758017258735bb84dc62ef86d79caf147c87"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT", "comment": "compat/noth", "final": true, "success": {"scriptSig": "22002085979fac9dd1a0ebaa6528ac118e6f3c489cab4019bb673e80e9070a73070003", "witness": ["", "63ce6851"]}, "failure": {"scriptSig": "22002085979fac9dd1a0ebaa6528ac118e6f3c489cab4019bb673e80e9070a73070003", "witness": ["01", "63ce6851"]}}, {"tx": "5563573e02df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cf1000000008e7047c1636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bf4010000000a7c8aed03455dbb0b000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208765f51761", "prevouts": ["c0c727060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "88199605000000002251200b7800d759a549d669ff8d5f924b2686a825278fb22236a72624d19d8d1e1620"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_15", "final": true, "success": {"scriptSig": "", "witness": ["27b75532a439b114cbc272d6bede01f36bea245dbb1e1e30181d8f701a8d986b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["4475c6c461d14b23af0914cb4605f2689a1ca029377e6252cf552b56d4cd778d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "a9cde2cf02b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71e80100000052630f99636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b8a00000000637209a0023863ed0a000000001600145e89b76f270f5a3384e042389be8f4c104024926580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec20870d8a4c20", "prevouts": ["f3ccc3050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "9bf52b0500000000225120237801be654a7f50ac4ab4d1f4f481765ee82301a4b9aaf17f9f67a5853288e8"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_26", "success": {"scriptSig": "", "witness": ["2f93109f719faf996d141fcf5318b04925490484f9f88ce10677ec591d2a1eff", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50cdc8aad12c52bf72619f8312393eb6afb6772c57bfda9437aab4"]}, "failure": {"scriptSig": "", "witness": ["fb5fa1376ef434a606ae96dc1d64124011b8a66073f92ce1a11e6df9d18e0f53", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50cdc8aad12c52bf72619f8312393eb6afb6772c57bfda9437aab4"]}}, {"tx": "ae4963d10302c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49da01000000957604dedf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5ce800000000076d18d2df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cfa00000000c75d0f9e04fa7ab7100000000017a9144657010e5cf55af6acb627784c227caeaa0f0a3387580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a33875802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b580200000000000016001486053ceaa6b6ea601bdda3b6220dc7510448595862040000", "prevouts": ["9da72e0600000000225120a576f86cec4c2394974d9e1c31b93aed490a73a505154a58f81fd67a489c02a0", "38b8b5040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "269bd50500000000225120348e2be7446b82700fd8b5317793c40ff5d97863329e9960884d3c06e543e644"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_230", "final": true, "success": {"scriptSig": "", "witness": ["2d6d48ebffded6983ea02ddec15a5af3757f965a06c0d1fbea63f7254557517d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["0d23e147e09f01d2922777c1c612f6b9cf5c48b4b1a2fcbd6175f166a808f27fb802e727e62635ceec7fbf6f13c721d723876f9d88825a805720fdfd0f88b8de616021be0cf352ea7565d280a1c4af98da5c433c4806b07a0360afd7dd15d5bbbb6dae8cd0080f6672a184ec57f5a169fbd5c55c3a6a20ce30f9e2226a01af4a0d41dfab9a0540ee73b1261fe5e83103523bc29ea4d98b8eb749c5906b74b32f8bc0785a3ebdb010a610d6619aa5fcfd5a0b8904835ae3d0b3625d50557cf3c09a84727ceba31b812bcd48a35a31e2fd05e9b1f23c056fe90e7b87b97cb58095e90f750ec16f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b870100000098e312cc636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bc200000000ad5890d404ab27390b00000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac5802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988acac080000", "prevouts": ["c3d50b060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "4d642f0500000000225120d066dac2bb55679bd17f2e4b852d68e6819bacc38abd54d0260cf561412a308f"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_0", "final": true, "success": {"scriptSig": "", "witness": ["a06e6f3503eb5e076bf4ed5cba3495f2783961557ff5f9bffba707e5cea13e39", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "9633a4160202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49090200000031d105a86a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d390000000007389c7bd03102e7c0a0000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338758020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac580200000000000016001486053ceaa6b6ea601bdda3b6220dc75104485958e35e6a2b", "prevouts": ["07687d05000000002251203f7a511564086ee7f86e7429dc1a548c041e4983874b1ee1b6cd2d818656576b", "cd9b01050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_7", "success": {"scriptSig": "", "witness": ["bd8b9f5097301eab559f64a907dfc6b7fc24a2a7d4d6a704e77a03780c5b39ea", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "5023fde64dd85dcb"]}, "failure": {"scriptSig": "", "witness": ["3310969c5f1eb63f843a27d386e4f662bae05a7bcb6f32b987b4799149a9e169", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "5023fde64dd85dcb"]}}, {"tx": "0100000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bb900000000a8ff84b8b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71d501000000eee5af3304d728a80900000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac58020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac58020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac38fbba5e", "prevouts": ["a1f5fb040000000017a9147ea0b4bf3c3053d912d2c4e6a8dd82eb668d9d6487", "6f0faf040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_188", "final": true, "success": {"scriptSig": "", "witness": ["f42bdb566582e7bb4c98d17913fad103f85fba3494320a7ce234964a6eb212ec", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["02de793fbb7a4e17f753b1c41eef14b9d887b76e32924014d36b63ccf80556e9c4bfcae8302352ba11677f3dc4ac5bfee3cae5fbcf2537084340d4eb2fa6b28ad3e9ba02005803a1621b9901919bb0baa4eac18ca777a69b09a3365c9fdb729bc427aff1f56d9971845bb96df9d4459b67efd158ca7195a7d6482d1387d9fb1b857186283581c08fbbd6d2fce617788993bd4692291e6766bbeaf5c819aa8fd38649a921bc6dff13af928406fc182e2104b119e30a8869d06742d943", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "00712d6e02636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b4a000000006a88c0c7b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71c1010000002139cbdd04a5ae7e09000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec2087eb010000", "prevouts": ["6dd4d8040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "a930a8040000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_210", "final": true, "success": {"scriptSig": "", "witness": ["0fb5ae7a2ac41a378bef2dcfb379f58df1ee65a9c9184ff37bc314ba24771abe", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["0c2ce6e7be38781419fb16ec0517fba8f636babc9d44a83ca818b190c553f33975b44955e4a604bcff82a61843288a3cd61a6499774a5a106a5a05ff53ae8f789297581dc166f0c1827869918d1f9ab8593b7f71994209af11672ba68e9a2828d0dfc8bc984c0a5899244e8f8c1b45394a65a29dc665bc8cf51abddd0df000ae42b419010f60e4bc3143c12d49d7a49ddc8126d3a2155f5f1987f9313c59ad4a28697768286c84133f1b12f04d5028e4a1e818d5c882c099b9f5e4f9859d10368dae008f4d02ac2a3ffab401d7d7dfc4f626", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "02000000016a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d32b0100000024e07ea403ce1cde04000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac58020000000000001600145e89b76f270f5a3384e042389be8f4c10402492658020000000000001600145e89b76f270f5a3384e042389be8f4c1040249261ecf0345", "prevouts": ["1bc5e0040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_226", "final": true, "success": {"scriptSig": "", "witness": ["b30ee3ae9ef69ab73275c1f97af120e0176cde0997b50b4fa2836e84ba3d7a0e", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["d5d514bf3ed6f99d0b26e7f283b2e75a1ab02072c06a833f01fdc076e789a212c7fe44d66a3789a9ecfe7c99f846182124859aabda9858c437b1522457f501835f2d3634677da63382a9850abd3c8b32387695a14c23f43f3b2b7bdeb2ce5bc87a70fe99bec363f0fbd9f0f020008b4dd9aee99e0a590845cf313d2546904a95cc56a5d26279f89dab4947e4d64981b498bd7ba934a655b1e875408a1879619cd1a73b261607e658cce0e4fc9cd37c50fb40ba97485a3921e29f97cd859a5f59c4e9fb0eccb41797aadce55058602b81c39af56426795ba108cb12655439c5ea69fa", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d717d0000000096a1a88b636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b210100000033225bb104275af5090000000017a91460db42f735e17b0d826006ad8d411b7445b1ec2087580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb8758020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb87fe040000", "prevouts": ["b90e01050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "3e3ff7040000000022512018bc9b7bb5cc5fbb2eb02aa0decfb057631f529487e64aea5d15e307678a72af"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_223", "final": true, "success": {"scriptSig": "", "witness": ["041f8a4dba9f1fd8972e6cd2ecbad5e177b3f511d71547ddf90a11ae77e0c7bd", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["991ac0ad4f7a634080c2b3cc8b3834e04a39c19a4d0cdd1ad0b4e9ecb1682153170d51375d47eb4e99d4c798ee6aaf93ee6d5bb286845aa36cd744191d1e131e4f5427d04775992d269b58db0c27a0f541d10b3a502eef88edf77f91b56b23693672386c64ef76226b702e7d8f529ad057d13936289b4f0c87c7a925649637583d1828012b554cb44387ba94a691db44136a2062adb559eda6e79e65a181e5042b46efbab4a16faf3a398d4ef8f5cbdb3e9d77ec4cc1d2e298ee5225b82bda4bbfc9612bf832b3b9af12045103311a58e323abe6f12933553aa72de6ac9a08", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71130100000023635edf02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49cd00000000faf29aac021e18f609000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac580200000000000016001486053ceaa6b6ea601bdda3b6220dc7510448595823030000", "prevouts": ["589748050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "cf54af040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_149", "final": true, "success": {"scriptSig": "", "witness": ["036d8c3c0a3d52ea1f9f43d9b511a1e629efdf94119181016ca18e6b9cc6ed1b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["db230242e7de2f6e4f0eefa98b9f1f9bff15e1657c26dfcc823235811e9dbfba71cf8de5a578340199124cc9094414d2cf35b3187e725433f29b75b14db4a538cfa684d8aa8ebacaaa85fc563022645ec2fd47b961bb8aafc6e67923c9c4e33e1ef61cbbc305cfd1ba37f1c876c62ab2fcf1339ff264a1f121e2cf51d821239a14fa076586ffc976072de1820e284a53843ca4df2f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49f4000000002c0897976a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d39a00000000ad6450cb01f75aba02000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388accef93e39", "prevouts": ["6f3d73050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "2bdf4e0500000000225120ffb624054c4f53a52e47c0a854c2fe8aaf203538c5f8f21e4b5f1a8bfcdb13c7"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_98", "final": true, "success": {"scriptSig": "", "witness": ["144fb823a8af896eee14d9ed60bb26500f1c475401dc643cdbed21953a281fc7", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["f61b351c9226390dc25542a196b8514b542e486fae0bd669ac11885487c64db9683588a6761a87e85fbeea34b94e947c4c8de297fdc403cbc01296dddff2a7e58eeed024f2b548d1991f9d3b34dfe9c3f75c8c1e2c30e617ff97839c5bc9054217a0", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "235fa326026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d36801000000f80920f06a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d30e010000006e054aa6047ff5f90a0000000017a9144657010e5cf55af6acb627784c227caeaa0f0a3387580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb87580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec2087580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb874333e22a", "prevouts": ["2994f0040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "0e060b060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_12", "final": true, "success": {"scriptSig": "", "witness": ["34fbca45b1dbd0562d5864e60937e7c1a0186fa659ffea422ece059df59eccd1", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["2229a84d8c30cc525189aa23", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "01000000036a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d351000000007e7f777f636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b9800000000ca4b3f1c6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3a60100000058ec228904a711f510000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac58020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac4b070000", "prevouts": ["063a1a060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "ae8daf050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "5ecb2d05000000002251204ece5efeb89c10ad768cd17f1f6d47cea667c7afd6e5e63475669c949ae02ff2"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_48", "final": true, "success": {"scriptSig": "", "witness": ["d3febb5ca8c0554b68a6f9ed0139b70405b7c81cf9f6d015836186953bfe0905", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["35545a7ba05a65cf8e43d6e25e7fb26c5f6bd840b80a4be75c2ea0f26938c65584e4dc84285b92fb1389b156eac7692a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf493801000000be9d97d6df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c26000000001699eddb0261667e0b00000000160014c327e70d62d692d5959c72b3411fee2ca31c546b58020000000000001600145e89b76f270f5a3384e042389be8f4c104024926674c554b", "prevouts": ["9ede18060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "d2f0670500000000225120801f5e577a4c45dae865648a93d9d1e894a3e982d52a2769a193af4e39416b69"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_25", "success": {"scriptSig": "", "witness": ["e25f719d569e5bdfff48346dd3e53b1f1b22f8c50763a0b1568ffbdb429c8b0d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50d6f388cf516c025392cf11d0eb2908e7ea69b9b9d853dee51e"]}, "failure": {"scriptSig": "", "witness": ["8d6b38c348bec32ca11da5b8e3bdf590f3c6fc4a520b32e4a7d94cc8427cab4a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50d6f388cf516c025392cf11d0eb2908e7ea69b9b9d853dee51e"]}}, {"tx": "3b264c560202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49a301000000366664b66a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d359020000008baf91c50248f4f80a000000001600140276cd59f2bc98ad777ccf7057f574395bd2430258020000000000001600145e89b76f270f5a3384e042389be8f4c10402492600010000", "prevouts": ["87db96050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "e5a163050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_23", "final": true, "success": {"scriptSig": "", "witness": ["b1e5acf715f076dc59bc91ac8a8301f704bdbacd5f99973d6d90c9dbeeff5074", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["577c15096629eb1794892a1bb5b26eb473978cec6467c62ada97eaafe7024152", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c0401000000e4cb62d16a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d30c010000009e0853e801444d4f0600000000160014c327e70d62d692d5959c72b3411fee2ca31c546bf8997b5a", "prevouts": ["fc31ef050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "a91091050000000017a9146c174aefe7ab213b29eb08b5e659e0e69fa1441187"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_11", "final": true, "success": {"scriptSig": "", "witness": ["2c380aeb62ef7362481d5b5ae789179d0e02cc86782fd5d84326cca96740e3a5", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["17c28fbbdf18433e70d6d2", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49c1010000009ba994c302c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49d10000000073af89e8034879930a000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac58020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac5802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92eb1030000", "prevouts": ["5f609a050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "aa33fb0400000000225120b1506aa4329db2887d1ed0a45d3c37911478b8aa9c3721f1d253b0b4d515965c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_146", "final": true, "success": {"scriptSig": "", "witness": ["4de1b13610064e59829890fa80ba264769696acd35ac0ffc6bb2399dad12cf46", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["2547aa7ea2caa428dbf722ef0175f69328e62c9baabf5c997e29c8de5f16d4ede1eb08a2c09fbe8143598d59566f2940d1d7ff14e967be8e249227922b25b36fcb36800a6d8462766b9e4b3b1880b246c1e9a48637345eb2e0b1c4d8a683b5b161b26aa5639febb0cd44501a4975b077f0d2b77e0ce352fe4ba9ec37e0624aff62523bfc61fdc7a9b383224f03eea86770d5", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "02000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d35201000000a35f25a0df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c4501000000707713a80407dbaf0a000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac58020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd2430258020000000000001600140276cd59f2bc98ad777ccf7057f574395bd2430292a3e451", "prevouts": ["2e51e5050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "c8ffcc040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_6", "final": true, "success": {"scriptSig": "", "witness": ["3706d0ba97b68555399dc5701f991d719a5ceeffbd37bfb22135fb5f3d6170a1", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["54e09ff9a7a500b5879020593f477674f861a0b9ea412b4f771b595809311f95", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "b37f163c026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d311010000006edaba9302c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf494702000000fa9b3edb048db3740a000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac58020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001600145e89b76f270f5a3384e042389be8f4c104024926580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338726060000", "prevouts": ["272c1005000000002251202bb55e232082b4f433b3f726fd80dfea5cc63ca82934fddaf9e37e8dbebe3d53", "7b6566050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_6", "final": true, "success": {"scriptSig": "", "witness": ["82a4335446f9c18546cf4653bd6ea9e6bc984f49484d82b03dbc3509a5e6f36c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["aada26454889", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "c8a58618026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3e701000000077f29d202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4965010000006fba6aa001bddb080a00000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92ee3020000", "prevouts": ["bf5f9805000000002251205a737f8fbfd304390e3758884cf1b13006675a4b94e013e215517e38e26275c4", "a0f729050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_167", "final": true, "success": {"scriptSig": "", "witness": ["a79ee41efd8f3c786ec7223c06f76cef7af7e239e32b15e89bf31deb9af4d9ae", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["ac86813989384d403bc662a21610301ce6454cc6cc2038c9f231322def9449773d537e20a684e9eef6d0813a1e0ad69f05ba0689a0707e77f6d5ca342dc3d90d7a03e0d1d7534cb537ac9725e0f41384959c63cd22c80aa88731be33d891dc60e3ddc4b17c95a12fb62e5d3d2ae680de0575423c58838e55e09806b471e5c67508e43fd1d20f40e27c7fdd8d0043c36c4cb106e92c538bf39dd34f18709dbe4934f9663ee7f2f6", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "eb5ec8c902b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d715400000000a43886e8636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b5d0200000069da21890281be670b00000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888acddb1ee28", "prevouts": ["00640d060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "3ff95c05000000002251200b66297b7265244014d46c530fa475b06f09c4947276fc5dc57f05fd168e320c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_37", "final": true, "success": {"scriptSig": "", "witness": ["1d73cd5087d0ee046367ef62b62ed0310d3ca167212dd8f20efbe5d35988cf60", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["d2fb7f3d44ad243ab5a3c8fd5a7f91ea26b6e65c86af2deb3f5cb316896418925e3f90d2cb", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000003df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c3402000000a60c02c46a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d31202000000500d7ba6df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c0b01000000728e5ddd039c5a810f000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988acc536d660", "prevouts": ["39d6000500000000225120d106cf5e6ad03585a207a919e464f8a1c6eebc0cf441f046b13720689b665b00", "c835b7040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "7995cb050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/2stack", "final": true, "success": {"scriptSig": "", "witness": ["ce", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd38a6a253592f3bc89560b38ca138fd38c9f706c809a5fcc553f3d89fcf45aecb0eb7a24b98f8b4d99cce3fe406d5b51bc68ef5ae97d2c5bebc358d8b5b5b78b2b"]}, "failure": {"scriptSig": "", "witness": ["ce51", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3388974fa00476bc2026bc8ba6f0f9171492b509dad14a30458e3f8263ff1955a8cdeb0de8daf44e986d19e114a7b8ed70d46e74ed21bd6c6e785c2a6747f82ddeb7a24b98f8b4d99cce3fe406d5b51bc68ef5ae97d2c5bebc358d8b5b5b78b2b"]}}, {"tx": "010000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49a9000000004900bbbadf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c1f01000000dad73c1401db362e0200000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e33337344", "prevouts": ["54afa004000000002251205a737f8fbfd304390e3758884cf1b13006675a4b94e013e215517e38e26275c4", "0f726f050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_115", "final": true, "success": {"scriptSig": "", "witness": ["4d2d7c2f7918cb0ea8ae556a9c44f619f579702a8eb52d726e0b030934c89931", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["90933c9dc236d16e89852a9482b39d182cd2ffd0a69c9ac5db23e59dc2476a3f2376e29d5554e163c1ec12f4acaf55963fd56097f1193a77bc05496cafc1d2cd2da11605b68884bc09ea06bea4a0c7af768792c6f769fffcb33684bec5a11a2341bc18666c9148b8fdcdc6b739408cba392a20", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "010000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf497900000000380d0b906a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d384000000003dadcc3004e7abdf09000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88acf1416d4b", "prevouts": ["c60d4e05000000002251207a99fad2158ab896dfdd1bda9274e723bedaad64424960b37793582808a28286", "f67193040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_169", "final": true, "success": {"scriptSig": "", "witness": ["e44e208cbabc0b01c11ef81960283b81db26f3cccea7f522de2fd13ba43f796d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["6bc30e901e20623ad37e2ec9994793507e51b0c6d094afe51be2d6919773a94a4c9f7fd5dc6cd7b47741ede854e97947299b2d16ec8f74ed3006367e13898787c7ce73224225d121e4db9b19bab99c520367685409d7450e1b0fcb39aa65c155aab64b5182e3692c256cc467e46f0c6a6a873b0005869db0647fddca4a8b039ae1b04912a0618fb9adca497538255a26880664b6312337cc8476cd4c43e1cd9381d9f22e86d7b70371", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000003b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71040000000040fa444fb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d718101000000d1c4432b636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b5a02000000d37d6cd0037a000d0f0000000016001486053ceaa6b6ea601bdda3b6220dc75104485958580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb8758020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88acdf020000", "prevouts": ["4fe4cc040000000021541fd8103542fd26eef79006879e481ff31a67ad980b893420b2253e9541a0d656", "88faac040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "5fdd950500000000225120f6d66a5151cb272d2a950a44c4d5f00386b88f54efa02e0424ff1dc59fd47d98"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_185", "final": true, "success": {"scriptSig": "", "witness": ["77e35fc09b2334c601ecfc73eb37d3f38a5742af56f079225c275c039718fbae", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["b2e20d3fdf6ad52bb083c30fe91cbb5bf75269afba5d2347b1dbdf7ee21733a83af79c52c76811efe5991f76e341eee1a17d35730abc49978f273cf228118ac7f62e878c3a20edb118a29406d1bf21a9cf98e6d8123764ed7d23ddaee3186fb89b580501dcf9ea373182f811a15a858d309385dce85ffd2774cee3b6d0869ac92b8e5deacf76b43aa1123e793d451dfdd40035ae7ae6afba4f82341618595b869b0a2d458b5c7401234eba32ccff6f03149199f3107042bbd3", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "36d53aa6026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d34f010000002cdd38e6df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c20010000005a15a0f204ddcb7d0a000000001600140276cd59f2bc98ad777ccf7057f574395bd2430258020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac580200000000000016001486053ceaa6b6ea601bdda3b6220dc7510448595858020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88acc4030000", "prevouts": ["e61451050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "b7bd2f0500000000225120e83b1050ee9fcd2a3da4b8b214c20b8d9e84964d497f4b9caa00a7856fe6b84a"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_27", "success": {"scriptSig": "", "witness": ["c0af38a99f19aa143135eed8f70ba68968bfd1b38f7f54e3046fc2f02752d3c8", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50d811ff8e46acd1ca40ae487879eb208d786401300492ef4b2765eb"]}, "failure": {"scriptSig": "", "witness": ["35dcca4072e13cd40c77b8cfbeee829994caea1a2420bcffb657026c07db3cdf", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50d811ff8e46acd1ca40ae487879eb208d786401300492ef4b2765eb"]}}, {"tx": "0100000003b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d713a0000000049657ebe02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49ba00000000eb5531fd6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3d3000000009a93449502c006ef1000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88aca552f83e", "prevouts": ["9b00d7050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "d9b63e050000000022512018bc9b7bb5cc5fbb2eb02aa0decfb057631f529487e64aea5d15e307678a72af", "8f54db050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_24", "success": {"scriptSig": "", "witness": ["2294cbb25eafcda4ff956bbbe2a5d3efdb2756df732088046e4c77b48dbb4298", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50952ae0df81e32961f00099ca26850cee19a06aea50fd8f2d"]}, "failure": {"scriptSig": "", "witness": ["1c5c03c92160d12d1d9a6584861e5f969a4b3c33cb2dbc8e5beaad07ffa6ad82", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50952ae0df81e32961f00099ca26850cee19a06aea50fd8f2d"]}}, {"tx": "0200000003636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b1c02000000ec7f63ef02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf499d0100000081acf2d66a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d38e00000000cf8806e501fdd312040000000017a91460db42f735e17b0d826006ad8d411b7445b1ec20872f070000", "prevouts": ["4cc525050000000022512001c264a1fa02a047a60c79866cfd2cdd3b88d2f5a43691a8bb58b721a577664b", "d987b8050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "1eecc6050000000022512042af4e3a04a7b653bd844b863b33bc5a24c28e189e4b9da3cd7350fd65f1b04a"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_0", "final": true, "success": {"scriptSig": "", "witness": ["98dd7e78f93bb307d3283278246d20222ec47bc3b88f773a13bffc9e765ec638", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["98dd7e78f93bb307d3283278246da0222ec47bc3b88f773a13bffc9e765ec638", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c0402000000d11469acb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7128020000005a5157ee04d675ea0a000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac5c849022", "prevouts": ["2cc9f5050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "0a3ef704000000002251202d59d680ca15a822d37a83977023cdf2c04104ebfd3fcf001a48bb4bfedad9e3"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_236", "final": true, "success": {"scriptSig": "", "witness": ["0804ef6e08eb066095fb8d8476a89f88d42b126c7edd35f708b5339353756420", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["99321f874026779588f1044789e53396aa0492919145bd53b23beca7923ea0e17a12ec29e6987c4b05bc661deb7b9129b2738070cacab13d9d87a389f913a015b267ffba2da1e9de089a33cbaf5658a60d8d62f6ea2396557e5ec8a8f66b9eb92c2a271f4643a2d2e3ca550c311e25459b147875816a51e02df6422268aed163c571d0182c7320ff7b5c9f9e9d6b19d6cc3ef21450d5e450b90335fc56197bbe3b291433f7a58f8c59267a8cecc1ab82b330ad926634dfcf0dd62af04a7551584250357cc7196800aeb2bd303dc678e617ae9e86d3bdc88256a936de48a73fb6fd99bac998c813ad62fc1a74", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "010000000302c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf494200000000e547a36902c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49a300000000bd367bed636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b5202000000659b30860270c1e10f00000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac020d0000", "prevouts": ["14cc3f050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "177b7e050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "a786250500000000225120afa0fe079509d1744d6514417770d9ea2611b6145e3af6dc87b5922364d330d7"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_87", "final": true, "success": {"scriptSig": "", "witness": ["2357642d1c5788c59f1b6f9f75507a2846ab5d631a3300ab6128afdbff3ea459", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["2d82038439473f7cba21c73cdb327d887fe3ab01150069de8c6927515e31e458bf306c662c349c1aca7cb6a5000846b322f3e757ad46cea06e300158f066613bffebe77e61260c4e74f777770e0e0f2000c5cfaf1c8cc4", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "01000000036a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d36400000000e2955d8e636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b5b000000003aaed91ab8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d718b0100000048a100250429282110000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec2087580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec20875120a24e", "prevouts": ["a44b420500000000225120f5f3acf55fd26b380ff20cb536c6c27d6647735fcb5e3ffb5f223137ff5ccc8e", "263510060000000022512032d44607d188bac8023bf2497dc88c591ec428c3b255753f92d9bf189871c9cc", "7ca6d0040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_125", "final": true, "success": {"scriptSig": "", "witness": ["eaaf5f8aea036a0c7731236b0497ea5373eafb814fb566774809c98fd32c01ba", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["9730ec375ae41d891f69b712df264f68cb75f5ad7947eece17f7b1a6843c6bc209e20232a25013b73c9e9d01b2563cf742e1c6a3a5e34652fb67b5af7f39387843ae513201dbb7a55266e69885a136501d7886044add8d95a649835139c075c153936ede3d1ab24204aa8b2be98f5f3c3374d8aa1bc43c972ad5e8e5b2", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000102c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49ec01000000a50d1dc601d9ec7c02000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac81c8a75f", "prevouts": ["a480cb050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_27", "final": true, "success": {"scriptSig": "", "witness": ["122173e819bb7e917813d4e1026d2c4a775bf7904f95c9c121eb4d00294628a3", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["3c460e99aea31cbce29d5bac261efdc5255640e5d23fa041bca9bac19ffd5f8f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000003636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bed01000000b4dd1ebcdf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5ce30100000055a159226a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d31c00000000f818c404043135c810000000001600145e89b76f270f5a3384e042389be8f4c10402492658020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001600145e89b76f270f5a3384e042389be8f4c10402492636030000", "prevouts": ["29794e050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "c6b7180600000000225120f27e681b8b32fd2022ac513a42cbcf6ddf97feb3f43867339ae71c50f20d79bd", "43936205000000002251200b7800d759a549d669ff8d5f924b2686a825278fb22236a72624d19d8d1e1620"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_52", "final": true, "success": {"scriptSig": "", "witness": ["0dfd29d0bf698ad555fbaa74630349b16540b839a285ced4faaedbf8455f69d4", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["3e8c342a480fad28d60291d519625c8c7ae3d0e2809f9a5c825bb6a89fe6ac9883262f8a06b672e8e40a45cb56da56d575fe0456", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "77edff4b02b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71c50100000071272ebbb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71450000000069f00a9302e20eac0b0000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208758020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac13f46e4a", "prevouts": ["22749f050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "652a0f06000000002251205e8b0e8f2228c19620c6ff3c4081751bd5de4f9369c8c6823061f3bca17c246d"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_142", "final": true, "success": {"scriptSig": "", "witness": ["9f816e66ff2f60c809820e20f59bda3ac507c5f897041a9540c3e3f6098b1b17", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["3a47c174173d4cb74e1e8d0ae792eefe933e9a2d55816e24181308ea233b8d543bb7cc93d4336b9a3f07db82f6f40e378fd70575e802b366f910e91767300340b6a98bad3afa239089ed72a483d5de71945dabf72b01101740a6b69664577449ad0aef964b412bf5bd497862321e1ff23c57fb3402ffdecdd941eb33f9eacb8610e420a030729f892e4765e4db9e", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "100d4b2f03df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cfd00000000533fb296b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d719e000000006b5b6781df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c2302000000d149b3bb0396708611000000001600145e89b76f270f5a3384e042389be8f4c10402492658020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac58020000000000001600145e89b76f270f5a3384e042389be8f4c104024926602fab43", "prevouts": ["cb70e2050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "078e89050000000017a9143a1e995df662c803b3c07d8d0827810262428a4987", "3db01c060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_11", "success": {"scriptSig": "", "witness": ["b3f19c186701179142617ec8cd7b7dac167e1139f223b8b9ae27aa95e7f53c4c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "5094758f88fba5e5a0107f0b"]}, "failure": {"scriptSig": "", "witness": ["4a3a1ecbfce7d2f3774e8da231e6154f7a34ef03e02c201a91ecb64d86926953", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "5094758f88fba5e5a0107f0b"]}}, {"tx": "6523ccae0202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4922020000007d7ba999636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b3802000000c3d122f20135b30602000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88acb0040000", "prevouts": ["da5ba2050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "2687a7050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_89", "final": true, "success": {"scriptSig": "", "witness": ["8747d3b0d8b2830bed0c430676add723e001a8576ce778ee0e46167331ddb260", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["516edc919a15455f3e76ba584985e1ce3beb9cf9e19824248e7864f7f772ea51305d28efaeea8a6636daab4c62bb7de241018b1884cde258eb97754cbd0e8cdfedc2a7e0e96bf46099420779d2a3398dff2e6661232d6797aa", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000302c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4943010000000fdee4c4df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cd401000000ee733bfedf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c52020000006e03688004c2900e10000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac58020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac5c000000", "prevouts": ["f5b893050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "c300260500000000225120d33ad765e02bdf21bbaf0b8ca54e6b419e435d4cf966141cd41b8bdec287061f", "46115705000000002251206ab9867a908845eeecbfa0b13f413fb370bdce83e23460aad55d4127b9e79133"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_0", "success": {"scriptSig": "", "witness": ["587948d6bde341008280ff5b18edcf7fd8ec396a3212735a5493e22c2c35cd39", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50"]}, "failure": {"scriptSig": "", "witness": ["fac21979308ac8d4d6b8f0344f8149bfa3212f405cb86d3196f0e95cb5246875", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50"]}}, {"tx": "020000000302c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49c900000000490d7695b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7131010000006a70fccb6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3530200000083b835ff0348a0981000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a3387c8cc3e39", "prevouts": ["26b8d00500000000225120dd05ddfa12186922f66a8ec41dca157ada848c6ac616648cd66825a343daf907", "9de56f050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "d6195a050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_72", "final": true, "success": {"scriptSig": "", "witness": ["c6c40bdf1dd70b85b1fe80e654e6790443755ac3ae71badc536bb9c87e26963b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["a82e07ab5764e920ba870f67418b31410ecf610cb574707f0bdc43b6adb848303420c90332790648e26d05004c0f81a89f82a105b15b8679d67ecc40130662095a28106f1bfb775c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0e58661102df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c2a02000000ce15328fdf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c160100000053ceda97043176160b0000000016001486053ceaa6b6ea601bdda3b6220dc75104485958580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb8758020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac580200000000000016001486053ceaa6b6ea601bdda3b6220dc7510448595870060000", "prevouts": ["55c40e0600000000225120763885cf750d2d0a7655727575291a596a6683531378a214a148a3e1bc60cbae", "ac6b09050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_33", "final": true, "success": {"scriptSig": "", "witness": ["5995e47001c978979e5e91a6557368043cb124cbb5aed1eb1a06f780aba2b23d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["e9d670577e4861f6d3fbb7431d6925eb9249b68a0a8f5cad295efa229a6b100cb4", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000003636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b5a0100000037e77cd8df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c5e020000000b58c44f02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf492e00000000f7edc323028c880c100000000016001486053ceaa6b6ea601bdda3b6220dc75104485958580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb87a20a0000", "prevouts": ["3f852d050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "9e13b8050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "7aa0280500000000225120b97b125092319d98b0ad739d9949a21e0745e3bbed230b66a8fb230706ba1962"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_166", "final": true, "success": {"scriptSig": "", "witness": ["1550edd8d87c054ff5dfb6df1bf9b5a0316e82b8a344ba4230c5df2f22da4df3", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["9971c779929e1c50dbddf5652e243fd0e072a7dc4e709eb12feb12bf84407d61a679f457052d9a3768242f4394ff6f1cef39a3ccc3985b6f08551e498a75b42f9481f1ef2e44818a232be7b5cc2a8fca65c50935af447048cb1a9fa3caeb53d7a7701e5fe2215f5b7bd3e52c7842196a3b3daece70545bfecbbdf6feb3d70dde8072421b85a941583ecce72eb049d1f9dd2742ddab6d384e54665045db4077bf2ec194c0052a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "93fcea08026ff4d0597576f422f7e67d21fbd66fdc0f38e238b7013ec87f4c2e8256f275527d010000002daf54998c6c55631e4cb829cd3c646b968b46ab28dae0631080ac27ba973f5b6c0b0589dc00000000939039c304c12893000000000017a914d03ef35ffe5d2d795347b95deeee902c5a11f2f1875802000000000000160014c6cecc4a03c68370e1987867816b8ff45c2aeaed5802000000000000160014266067d4010918a57950df4fde1354439745aa8258020000000000001600146f4a80043d70c971a209eab0abf54aaa344fbd64383b0364", "prevouts": ["fa32730000000000225120c14cf1537c8ff49c45a4d5b2bfa8cb8e4c24587eaa495dd07876b39ef31f0996", "dadc21000000000022002085979fac9dd1a0ebaa6528ac118e6f3c489cab4019bb673e80e9070a73070003"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT", "comment": "compat/noth", "final": true, "success": {"scriptSig": "", "witness": ["", "63ce6851"]}, "failure": {"scriptSig": "", "witness": ["01", "63ce6851"]}}, {"tx": "01000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d339010000008e9bbe4adf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c6900000000a63fbe0104fb9a7d0b000000001600145e89b76f270f5a3384e042389be8f4c104024926580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec20875802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac0a5af864", "prevouts": ["809115060000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "e0fd6a050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_132", "final": true, "success": {"scriptSig": "", "witness": ["0bb34ad383b31d83b4f53463fdb04aa56e3177f1b335b25da1c9abd0e6a72595", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["07722f70da03b68e79392d321dc1095a6234e4ba74744acd373c204996c0702033e44611b716b89c63747a7f5da0bfe0b2bb043e0fa19f915b2f4f66cdf261d76e3b26b08891309b18206cf29c9253a919528656749267fb08ff84da609666a20f833cb3e66d56c02a2e678f96e8d01d7e3229ec2f11d25dbffc6153972b37e94a19d8ad", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000001636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bd801000000e1da24c501d0800902000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac38f31a53", "prevouts": ["ea7bce050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_94", "final": true, "success": {"scriptSig": "", "witness": ["d71c1864a96152e5534b4ef1aac79941c8d130f0de62c1354466088efeb35e14", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["13c1604e5df427619a703a5fc0b85b22f23b4078dcaff0f0c624f5411f50fe79e98c057326d128f25b0c9653a084a4cf1ceef772de11c69e95996637e4a2598e9f6b573e3583c7620b95dd4d340607872acb97c3b801cca72a0763096074", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "ebb09c2802b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71a00000000053f4efb6b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d711a000000008267b1d702f4ea550b000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac80080000", "prevouts": ["e51f6e0500000000225120b3c272f449b16a54f4fcc57208cd2bcf8d0823e6a64b770449565b033c36b180", "7e89e9050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_191", "final": true, "success": {"scriptSig": "", "witness": ["102158cba4a2d74d7d493b71f5b9e383a5fcbedb947bc4684d7d97478dab00da", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["1ec278402813765869e465f7b1111eaae0d7e2205b9b7624361e0ee8f8fa4b1e29667396472cc547ded469c8099a10ba6e12eb4e50b5f10444ae238ae7f6f3d0b86f16d6f9f6d2543dd4c05efed4cf5e9e4e9aabe01e3f3f6d64dec678687e9df837d62a0a6304e460405c99735a727e3d6f7bc671d6923edd9b32b6a2d6fc9d598fac02093feda63f7a50f81382bac3f6604c1a0130bda4bdea64947d1058f56c931a3cde70feed20e0d435795a2530ee4b8cc9b349cf5308461c354e1903", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b1301000000aab54239df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c290000000063d6d00402dbd4580a000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac9b2eea3b", "prevouts": ["18bddc0400000000225120d65e92da0ef658a4db1ad73c022666508f5b3c7113c9df2be119a6939253bef6", "891b7f050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_164", "final": true, "success": {"scriptSig": "", "witness": ["cff19b3b8b9ed4e6f2a971ebc367ea35d85e387c5e6289ceac27e4bfe7aa2e1c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["1c236af5613e5f5281b06301874843197f5b94b2c4c4bd497702813909a062de8e5a8b4d296ae2d462feaa206e7c244dd5f5f31d9904d550acae0a3a68327e207dab50266683fc623e8838f30836104eeb488098ca476c44b28a30d913fb0ab7b718bf37aaf50b3d56a06996cc1427377d20ea17628e40f45982f624f046cec588038110d99a1d008e7eadb3120f3b3dab084a39a4976096a7697674a1ebdbcfd5ff79ab", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "624efce80202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49c600000000570f44ecdf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c8301000000b7d653a502956b530a00000000160014c327e70d62d692d5959c72b3411fee2ca31c546b5802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b61010000", "prevouts": ["7ee451050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "97a203050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_2", "final": true, "success": {"scriptSig": "", "witness": ["b400e5cbaf072d654ac8a5034b07abf4e1b9fa66ffea99dd756e9155d764ba34", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["b400e5cbaf072d654ac8a5034b07abf4e1b9fa66ffea99dd756e9155d764ba3400", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "02000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3ce0000000055c315b402c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf495e0200000069efe7fc014da36b00000000001600145e89b76f270f5a3384e042389be8f4c104024926d617381f", "prevouts": ["aa06da050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "f7cc15050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_10", "final": true, "success": {"scriptSig": "", "witness": ["8edc05ab852ee78bf233698a7b345711a0fbcb426fb0f9dba331302f20ffce37", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["df154255db32683334368fcc8bfdd2ed75e6e1411609f7671c9dba3e3845254f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c87010000008b7d4cdab8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d711001000000f13fd7cb048747430b0000000017a91460db42f735e17b0d826006ad8d411b7445b1ec20875802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338758020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac49138231", "prevouts": ["c11417050000000022512018bc9b7bb5cc5fbb2eb02aa0decfb057631f529487e64aea5d15e307678a72af", "9cf72d060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_79", "final": true, "success": {"scriptSig": "", "witness": ["a54fc5f9f4acbe0bd2db34a7661710d028eb69a51c1cb3e1330d9428c24e14d0", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["6db7863e35904d3be50d0dc6e875d93d67269bc6c4afc5da0e71292b4f0abec638ab60e9e4046787bc860e8ca0dea5f2433167f20a40ace25fdf5d858c94a65977e9bba691ae97647e35661c9496a8", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71db0100000058b25dbcdf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5ce1010000008206deb4026db4810a000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac58020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac51000000", "prevouts": ["5e74ea050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "17e099040000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_43", "final": true, "success": {"scriptSig": "", "witness": ["a97cb45380255421cb28c12b239898f4a22225dce421bd2f1b96d01eeb17dff1", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["ed731ff01be356b5432f256f49bff3b21c614fe0ed7adbf9b3e0a679397b55c84bd55d7a23cc82252e1ca6", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "00c7eff502636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b7900000000a09f2484636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b8e00000000132c82c20385edd20a000000001600145e89b76f270f5a3384e042389be8f4c104024926580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208758020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac8c020000", "prevouts": ["cc5c30050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "079ca405000000002251209f9391a1a1cbad70e9458e6ddd6a6f3c48e46fea8e5133e3d665ab1e3fd1ee29"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_18", "success": {"scriptSig": "", "witness": ["daa044ca37df3f79ee3783828c041038513a1d70ec7aba7ba03f479154b46daa", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50a46def85d9bee3a808b9c50582162a8cba95"]}, "failure": {"scriptSig": "", "witness": ["63c241a1db5a7c8e382aae6e50f51ba870db7efa7942da20e5a394ddf433a4bb", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50a46def85d9bee3a808b9c50582162a8cba95"]}}, {"tx": "0100000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b4b01000000778e6eea636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bc600000000293e5553033d1b690a0000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb87580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208758020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac8d050000", "prevouts": ["31d44105000000002251202b3e592132d47f4d2d3e51edb33e9164cded46eb146b86b12a068fe5729a7f7c", "64e329050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_238", "final": true, "success": {"scriptSig": "", "witness": ["de1ecc47e98d3d12c25647f8fb46934a49b779f64e0598d6383f64aff4a43843", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["320242a0d22f5dcdae5099eef3900a664e54f99f1319e972c1275376903ca6c5e30da26f3e0ebdf9a81fcc23199d06a163b42018cc877b8c0cb63dfe80fd82a3547d02f154b99e5cba4f3b9f0df1039660c4843eb5734dd036d445767a6ba2dd315f4045514a8ecfe85dd7ee530fb1c73f2ec972966a627c42c7c93f4c62a811855663ebeb6e84ddd50b1f811afe418a6da10836b6e0b80cb8600062b24163cdb414bcb042c343cd4dde152eda4f4da26a02b21530a2b8fa9476e690305155070a406a8288f36b6b3416f94667d9f40a30965d725d68d49b2aa6634c5ddc71ad93333ff25227bf8c9f767e34d3f0", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c3f010000002f38fd3102c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf497b01000000e7fc04410371c1be0900000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a33875802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546bb8060000", "prevouts": ["deda1a050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "ba77a50400000000225120455d087aac2eca7f00d15273d04cd048cee95099ba82cb7a2b84ac0654860cc7"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_187", "final": true, "success": {"scriptSig": "", "witness": ["784e9b3b44ba3d302969872981de4c027f588096a1bdf70b7bb1a9dcc900ddf5", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["cf6bf57d2ed8f8449e842a903d743e3f6531f07e3a5c2a749a59942f6a4f0cec72fea06b570155a9f5bb547a67ef5d11d586b3785cd0a5ccc244ce219fc41dd70fb8063f7197a34be0e0a28006a6c42c2c06b769a6e561e2d85b501bdb62792492ab6bed6f64b7ef51e8033bfd4d07a83e3260ccec0091f7fc87990c117e0495c12d4154fbc40543eb61999b739dad1c45734568fe7b9fb1e7ad6076edcebb0e148ec7be2a1c6139cde830b00e9954f7b33c6f88dd85a895719a2d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "676d69450202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49aa00000000a1540ce0df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cb4000000004b10f0f6021b20db0a0000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338758020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac8a77b22d", "prevouts": ["52c342050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "ddfc99050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_57", "final": true, "success": {"scriptSig": "", "witness": ["2185f6986a277cbaba81680c93618814f1ac9f0ffb5f32c4f593e020dda32570", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["e277545cc963ca6b1147dd53fb01732419398e27cc4415851ca6995d236dd637ae3649e3c7fb80cd2e32bac8f8c1d632e60c12439e19410a4b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "e3f55165026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3dd00000000ae6e519402c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49e901000000e076d5c603d2f7d60a000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb87a91f7029", "prevouts": ["d68c82050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "bba556050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_151", "final": true, "success": {"scriptSig": "", "witness": ["e1c7d7e0bc82ed1dbf1595b74e3d3acfff9d36888a21a1c0009ca9776b29cd71", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["3349f4db8496ae817a12841eca3d0175ce64f3e458b62175593cecca1cda938aa353c7ae8b98fe52039b473e5a534e9029afa7ed9fcaa0dcce4fb6d1c6d60bdafc27b1d076dbd4e05e7bdb76990c39f743323718a9c8dcbb4ead7164755efd10dabbbafddc9978d1b509c866262a2559381a4358499b5cf0f5ff6ff03c452e2e9bb218931a3a5703ba4445a7b4239f0473267ab2ebce75", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000003df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cd2010000001c2f358bb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d714c010000008a8b82fb02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4955020000004e511eea03cb018a110000000016001486053ceaa6b6ea601bdda3b6220dc7510448595858020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac0b030000", "prevouts": ["3d4260050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "3da517060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "622814060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_168", "final": true, "success": {"scriptSig": "", "witness": ["cb8c3e7cf9c2318c638726778f74a032badb99c3787e13d4cd2bdc9cd2975fab", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["d3c42b51966e60f2e7a7b74257cdc0bf54c344892932fa754022edd2d1df736ae3c97fa1e2db5214273bddad830b18e1482957d247f666d61cce95b644a21ca7bb33a3e29cb26d485d467176785d270f30e00041fbfc41fbcf80ec755ba1b0858ea58363c6a50be4cd374f5890b3559f9b852f38afdc1d46b4f79a39ddb8b0c8f68e837311ca629373fb0ef8f8c2db6072a20edd9be9ef3f2cec612299b438d48280eeaedf89272f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d714b010000000fcd9197df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c4a02000000c84c049d04b241a4090000000016001486053ceaa6b6ea601bdda3b6220dc7510448595858020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a3387c3000000", "prevouts": ["90cf0205000000002251201d06129f09c7aa4a4a55408ff2475680cdce0d6db2cd5e55ece26df1cb43dadb", "0c92a3040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_147", "final": true, "success": {"scriptSig": "", "witness": ["4f9ee7d2aabdd9236eef1d2e958ad12509177c0b55ce29cec595df10b954973d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["bef288a0c890ab9fc9e10b7b58552126a2bf3a75c2a84e85c2ba725696769a7d03a2ddf77c16e54fd7e299728965d3a339c73d565d273f5b593765205f2c90d9e28c0be7e4707e170e3d592b0ec61c46e8ec915a762a6b13e41b0942d8b3a36e938b9bfca9c9bb62fd12554998d4e3739263fbba39d7e84844799a44091dabf2b6938d47395fc52cd284a38684686b23177c8d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "e3565d10026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d30d00000000a97f8696636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b6201000000d99380e6011d265e0700000000160014c327e70d62d692d5959c72b3411fee2ca31c546bbc020000", "prevouts": ["8de9a8050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "a4e9e8040000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_198", "final": true, "success": {"scriptSig": "", "witness": ["c175cdbb450df230569cd443346e46f128e5be8b7429d7fa9d536a65aa2d5bc2", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["a40a0e9a05348ec8e03644e482c01bf5a4cee90c8803f5204d7e8e22e787a6bb11eadff53bf232cee80e9f04bac4cb5c788b5e83501a4805ae22e357f810f4b21d41e905e5bed2d8ee004de7ed873c58cc42928ee24d593e2cea305ea75f9171a2a1295d40c1836b417240a028610e9546a5d3895f02381ab1827c89ff6047b87977ff051e341da35feb5382efae4bde6b5b18b9df9f64e4a1396feb27524dcec5ded7e558a8451dae918d7602aadba0cb4a761e5f194bc16ac9d3080db59f07a094ae40be5f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "a169a8760202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49fc00000000fc742289b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d713f01000000bcfbe1c702194a9a0b00000000160014c327e70d62d692d5959c72b3411fee2ca31c546b58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac7e040000", "prevouts": ["c5f3fd050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "edee9d050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_109", "final": true, "success": {"scriptSig": "", "witness": ["e4ef99dcf141d4608d1edaeb29ed4969be3a100b5e82dfce521bfdf797c2d109", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["afebd3c81540e5090a55db32a9a8e4f7396987be0138984220f96890b19c94e2849e62e427a80e92d86349c58d4f722587dc5a50d35fa0bc70b6baddaaf6e00a24a4d1c341638b0336e3e34879a943c85bf8ce6274eaed11a9bb13397701fac93578ae8d43eadad53033692cac", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "02000000036a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d32e010000003a1140d402c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf493902000000ed9678c16a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d341010000005a7208cb036560eb0f000000001600145e89b76f270f5a3384e042389be8f4c104024926580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338758020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac19030000", "prevouts": ["e884af040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "528a5a05000000002251205f359b0c56fb94cc824c7891579f1c80f5cfbafb82628b3b456b347920082c7c", "c89ce3050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_136", "final": true, "success": {"scriptSig": "", "witness": ["54ac0515a0a00abcf4d37826cc0fb8b6fdb9f0a0d75d1ccc17bd289fe2c5882a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["2860756e6ae88cb0e5ae64a48da1e330c6a255853ea02a91ea6d71411211f8bdccca38ae0d7945f4ebd8063e344e0bcd971ca53a036850f408113430e8d613fa359b3d3e26f7e9d50917288a6a54465fe80d91b142ad3fe556cdf2da5c2c08730d4d839bd1cc2f44638d806b75f578aff7a4d7523246cf8859c53b3bcdee971ec5ba2de1755d2133", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "61f5b5be026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d31100000000fe1459dcb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71e700000000796fc38702e407fd0a000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208711040000", "prevouts": ["bcd8c5040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "9d33390600000000225120763885cf750d2d0a7655727575291a596a6683531378a214a148a3e1bc60cbae"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_22", "success": {"scriptSig": "", "witness": ["4aa2c4ad2dfcfa8ca79a11a0987dc644dd93e2d78e0acc890392753b3bc3ec1b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50b8d4f91ba3ec123ff64ce33b47ff4115a80d405e7dfe"]}, "failure": {"scriptSig": "", "witness": ["e50ac436230d59269525eef93b8f1dd3c36e95a8b6826f971b71e3387a4c257d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50b8d4f91ba3ec123ff64ce33b47ff4115a80d405e7dfe"]}}, {"tx": "02000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d36702000000b7445da102c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49080200000049c6e9820346571f0a0000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338758020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a33878f5f1860", "prevouts": ["8a2362050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "3b18bf04000000002251208afca9529fc2a84b5340cb811b38efd391132ec270d8475a881deee3f9b08b8c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_29", "final": true, "success": {"scriptSig": "", "witness": ["7788b8b26ddd8c06a6b51171371ef538f60fcc0af774f51e324c42e84bae5a7b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["5964b6df310d88b7421dc2f807c71790864595859250cc1a84d0cd60cc", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "c2d3e76b0202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49960100000015d46ccd6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d31e01000000f6b89c9a03cea8800a0000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338758020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb8794050000", "prevouts": ["11a7fc040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "3082860500000000225120c139e54392c7cef91a1aca835f95c261d08f93152f54be164a62ff27db2f2848"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_26", "success": {"scriptSig": "", "witness": ["50c068cbb8a56c670c3d6fa30132dab11d49a9ac5a897570bf6d5b4d64e6e657", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50224c33072f947f084b94dfc6932c14544d72abf4de7b4985432c"]}, "failure": {"scriptSig": "", "witness": ["48464645fa22fd0dd0d086b53ffc1fd3bf26c1e03f98011839261998c454b5bc", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50224c33072f947f084b94dfc6932c14544d72abf4de7b4985432c"]}}, {"tx": "0100000003636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b3d02000000911b19c8df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5ce401000000f4c91369b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71bc000000000fb3e16804ec038f10000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac58020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88acb2060000", "prevouts": ["e41d7c050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "2bc524060000000021601fd8103542fd26eef79006879e481ff31a67ad980b893420b2253e9541a0d656", "d528f1040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_10", "success": {"scriptSig": "", "witness": ["66db843f28dcf129e8779bcf2cc9e364d1a35ab239c8dada3cd7c8ea5763b407", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "508550c7858746f6641ebf"]}, "failure": {"scriptSig": "", "witness": ["c33ac4287086d1aa86f8fa2489a1decc4d99ccb22fd244aba4a199eebb20d7cf", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "508550c7858746f6641ebf"]}}, {"tx": "010000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4948020000009ab08fc5b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71220000000030774f900411b1250b000000001600145e89b76f270f5a3384e042389be8f4c10402492658020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac5802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b94010000", "prevouts": ["9753e9050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "eaf73d0500000000225120ca58f6a304c5cd63d86ba78be28dbc391cd8fae0b685008aa0e65966a5d84cc7"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_19", "final": true, "success": {"scriptSig": "", "witness": ["37684b747aaf2c8cc94c9b8ce13341b41960c523661e6e84984aacd0235f5d69", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["a457682055d78a7b86266d0dbec46041cd5a789da4d3f6b7058be5b566c40ef3", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "010000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf496802000000e216cdb8b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d717700000000c9892fb4041f521c0c0000000016001486053ceaa6b6ea601bdda3b6220dc7510448595858020000000000001600140276cd59f2bc98ad777ccf7057f574395bd2430258020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb8732210641", "prevouts": ["03e21106000000002251206e87dcaf3daaa6e56eb77ea83b41d7af8b071b90bdee4350c52b56349714da58", "67710d060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_148", "final": true, "success": {"scriptSig": "", "witness": ["3f26f0c5b34281b0fe08ac324a1694d90d9d07c010447496607837b64e6ca333", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["61176731b46db2ee6701708fac5ce567c927052e9aaa3e108c978d6da67588922406fd37c2c83437c3b382c34cfb4b5c975363fef8854d2c33750cf55c3c863699c6039e68d8f851a0d61fe60276c9c567e27a06eb364580429dd4e4921f273495665f18e4aeb5c0e6f6ef2086c73e392a138d06022f9c56c2574e901caaeefd89af403472c9482fb59a6525bac3fd76670fc3a1", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000302c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49ac00000000ca7100bc6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3ca01000000637cd5c6df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c11010000005ce10e9104174d7b0f000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec2087580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208758020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88acd1090000", "prevouts": ["e87981050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "c31ae1040000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "66a21a050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_19", "success": {"scriptSig": "", "witness": ["97415d12655fe2f93ac06db16d017e3cfd3c9e6d3b43864e7e7b9944ec6a4b3b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "502482252e34138f24c43df4b3dd1b92f234338b"]}, "failure": {"scriptSig": "", "witness": ["401ed3ddd64b9d7c787ae59333c7e7faeafed2add42ec6de1561fdff3cf755f3", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "502482252e34138f24c43df4b3dd1b92f234338b"]}}, {"tx": "020000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf493802000000c7df27906a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d34600000000e02e4f9601bbe3b509000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac9e89c15b", "prevouts": ["c7cd5b050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "417601050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_144", "final": true, "success": {"scriptSig": "", "witness": ["bdfecdad6b91bfd063871cadd3cf811709a726503986a71b6d1c51b092ff008e", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["a9d7aaf138e2e17f38a4c6cc1d482f62ab4a1951b657493a10dc5d3c17458375ef3604cd38953c8b358b9f6acc3ae879ba724c2dbaf2dc4cb104cb131c21018fb6474c46656ee0390acd2cd76b0f1b1a6d06f00d854e7c6071c92d7ac3743947abd42ee5a6280d9fa92031d67fa31aa1852789f630b96b3a43659ddabf22235961177aa9238005f669f124381b6611bd", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "010000000302c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf494200000000e547a36902c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49a300000000bd367bed636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b5202000000659b30860270c1e10f00000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac020d0000", "prevouts": ["14cc3f050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "177b7e050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "a786250500000000225120afa0fe079509d1744d6514417770d9ea2611b6145e3af6dc87b5922364d330d7"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_20", "final": true, "success": {"scriptSig": "", "witness": ["6c8b7516f31be422b570de6a0e7448546005c3acb7aa79912deae9e6834084c3", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["704e375d49e92f43858de99af0557f09265a56a0a995935c3b52b8cccc008fdb", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "010000000302c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf490301000000ccf436cb6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d340010000006f0ffafdb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71b700000000492d03c204d91fc410000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb8758020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208761727164", "prevouts": ["91d926060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "1468fe0500000000225120ca58f6a304c5cd63d86ba78be28dbc391cd8fae0b685008aa0e65966a5d84cc7", "9cd0a10400000000225120d7a254f78b483243b22196edc1adc3dac40fb25549ffc09e07eacaed594eae99"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_237", "final": true, "success": {"scriptSig": "", "witness": ["98fe21422ebfcb25cbee2ee522e2c16c82a8b2ad27170da560f4e595951f76e2", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["2d5384172e5c589a8af709fd8507b5edb68336cda8ae108b26230a183a6d74375cfe9c55812ce94ceb980c89bca47b59218e7ae763a91890f26a88db31fef13f1f8bd27e6e18aad5046a104d933d9b07f1c189a7db0b4e687b388b3763cdc8026c4a864d95b48d2fed81260d9e4e89db984aa6610d3b38f331e3c8afdf580ec5edd22331df14dc6243199ce6ab74e1f2b7ee346c55dbbec09f0cdde6260d43e8bfbc2293dd3a10abc6a7246c67dbef93175a5cd8fc457f9bdcbe3b1412ec04b91c33caf4618f4b5512a8cc69fca7262800ea853d639c84df13408e74e5e13a83b7eac6d19067088f69806fa175", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000003df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cd701000000c6471f04636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b3401000000f878f1b66a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d37801000000c66a8483020053890e0000000016001486053ceaa6b6ea601bdda3b6220dc7510448595858020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac4cdbc224", "prevouts": ["9a0f650500000000225120a44c74e9e8cb0527d829597b8f2c7c7aac5a6c24435ce6277c07246c1337e2a5", "9ca79504000000002251200207652292ee2a53c7d2af195672632029943dde6223ca51d2fd67bb1d50feac", "8fe690040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_159", "final": true, "success": {"scriptSig": "", "witness": ["0d65224fd8cc01870d002565a466257b8a83dc2e727df7e04d5f9dc597574e1a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["10eb4dfc0a5d0f7c66a2675365ae94dcc65846d03c01e30a22993425369bfa6b3e84cbee8432b34fa62940c65143886fcc83d90a6e6adf88bed78dee0f7700eb323ac342fd0b3d5ae6572df04fa78f7cf25e3d3f3a958727752e49f1ba8cc1efd68c9588346e902d5b1dcf2439dfcb868a4ba76ea6c928b1abaaa1cbd88fa4413c861568ce8447f147384833a8e8fbb0df01e2af82f35eb4254e14f8db3f23", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5ca0000000004ef2d6aeb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7103010000003ed85d8c0321d08c0a000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac5802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e64040000", "prevouts": ["0a4ae10400000000225120f0bcc43fa9db21de60c35165920a8db0a207709cc766839b90f47b274d1e03ff", "97dcad050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_47", "final": true, "success": {"scriptSig": "", "witness": ["124f3d2fe741ec5d1f2e9414b30c046a857ffa37199717672bd5b20df69c76e5", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["cfa14c24439880d766079bb1694546e0a6de02b1835bf3a1e8e53e858a3b0ee17cf087ca5644bc8192431eef144fc5", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "02000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d37c010000005545a2fb6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d37800000000e904eeab036d20210a0000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb8758020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac58020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388acb854f953", "prevouts": ["6e0a57050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "a44ecc040000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_17", "final": true, "success": {"scriptSig": "", "witness": ["bd02f215f0ea8e6e04473d66954e33e8563ec73a346cda69901e17c0eba82830", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["0f0d82d90b0aeeeab26b573d6a71abc5eb", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "3574d82c02636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bc50000000018474bd0636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b1b02000000fd742cd702948ff00a0000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb8758020000000000001600140276cd59f2bc98ad777ccf7057f574395bd243020d070000", "prevouts": ["f9ced70500000000225120444577651e37fdb7a210d2cde3a2cade95ffda3c149246dba0d617bb4880d3ba", "838d1a050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_92", "final": true, "success": {"scriptSig": "", "witness": ["e792cb15b2500b7c0add342b93aeec3786527ebe23f72b5b9c1f57975bc0a0ae", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["3871519b0e91f53c8e94b20a00a1defdbdc44da646f91c37ab1201b68ea77e9be89ae512fb08622aa6b2498ea3a298ec669b290a1055545dbf585e15b468b0a1a91829346143a5314972aec841e34c0b4189a0a510c647ad3ee8dde0", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "2d79350b026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d30b0000000025ceebff636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b00000000003c322bb103a6e3c409000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac58020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac5802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92ea6e9b750", "prevouts": ["856f2b05000000002251207aaa88bffd58a856df2da76c3be5ab8c694d7606a7a914201058d818c3dd2140", "54509c040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_177", "final": true, "success": {"scriptSig": "", "witness": ["8703790b4724059cfc694478bc130401bfa635b4c0d991bab2074d9adb421dbf", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["1eb8a2842a2e4850b0fea7670b9b0a1a3fc02e5954990a1bc3c607dd5a204e10d0f114db164f24223928e469005bcd45e712227077d152f5a9462852cf4bf2317702e1f0be55df02b5eae52392108ba9b9d94a16d219e5cd22c2d2d8eb1ed558e04b9043d84b0d91682fdbc23b97121723ba08cf4cfff20d6475441a32ca6de0d24e51ebc7c60397b75218889ecae9b57babd87fb184a941ae10f2a1003faa10f2bc8686017c2fde32b524502d9a3e335c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b10010000008409e09b02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4969010000009340fd8b027af0f00a0000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208758020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac26070000", "prevouts": ["8ea6b40500000000225120da09873d8fce7038f3312428d7d0c8cd978fcf54a6b59cd28cdc533d57b47db8", "aed33d050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_27", "final": true, "success": {"scriptSig": "", "witness": ["346e5f59dcce53782f03d96ad929067ec5aecdf6371d7a2527ffb6e28653411a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["8cb6f4dbc40cbd6d603f3fe92dd2d2188e3d6c301355389eb874a9", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5be300000000bd6634d3636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b51010000009ad34ff0017c9a45050000000017a9144657010e5cf55af6acb627784c227caeaa0f0a3387dd8aea4e", "prevouts": ["aa40dc050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "be51140600000000225120d106cf5e6ad03585a207a919e464f8a1c6eebc0cf441f046b13720689b665b00"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_25", "success": {"scriptSig": "", "witness": ["bf7d7b1709c753d28ece46dc313fd52d52c08d812d69d0c0e92aa8c60b1890ab", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "508fee65abf112515a177589a1970a71a25d1c5ea5d980cfdc32"]}, "failure": {"scriptSig": "", "witness": ["2ae10c85a89e0a0bb11034387b42c3c8135bcaa16b841a6aee53efae3565051a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "508fee65abf112515a177589a1970a71a25d1c5ea5d980cfdc32"]}}, {"tx": "010000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49eb01000000b2b6b2896a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d37d01000000bd0e3e3a0153b7aa070000000016001486053ceaa6b6ea601bdda3b6220dc751044859585d030000", "prevouts": ["012ee20500000000225120d65e92da0ef658a4db1ad73c022666508f5b3c7113c9df2be119a6939253bef6", "5b5217060000000017a914e38dc88d88006690cc72040432afff31ec4cc2d787"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "compat/noth", "final": true, "success": {"scriptSig": "000463ce6851", "witness": []}, "failure": {"scriptSig": "01010463ce6851", "witness": []}}, {"tx": "020000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4903000000008caf989402c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf495f00000000f547cc9701fb091e060000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb871a0c0000", "prevouts": ["12570f050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "ee0269050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_85", "final": true, "success": {"scriptSig": "", "witness": ["2f6c2d6485272a7b43b6c9a26c6b7530317f793b0cb9ae1cb1d69e7c6bac9b5d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["33f053f4772bd3924218e43550a62e49743434dbae620467e89721cb3128a93c92944a48dba62c6de9aac529696f3712ef0c05b0870ba766954b434b2230e284f3af471395488ffcbfe696b4514032886e4a2d0b56", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "02000000038a241fda3ab03fe2f04af98e319a0e5528353222af7cf0c8ce101792b0c746620000000000145743868b8a8e3b30ceeefee1e4e48b73d8c77dcd7e9990957c54ae82852719e96e3fa1000000000052d98cb98b8a8e3b30ceeefee1e4e48b73d8c77dcd7e9990957c54ae82852719e96e3fa10100000000c13bcf9804ad30d4222000000016001495ac79ff2ea7a9285771021da5181761a06965625802000000000000160014a19555480a42900bfe46d7c2b6fee02b239f40df580200000000000016001495ac79ff2ea7a9285771021da5181761a06965625802000000000000160014d0b4a64c173703a4137b52a32ec050664267eb745c020000", "prevouts": ["faaeb2310c0000002251202458cdf8f6855b9994354789eb4d16047d14d9e98d5cf947e122981294b84c18", "6ad8a96f0a000000225120c8fca798f6db05732136f92fb7c8c1c45587befa6ed8eaa267ff78889e288109", "0a6e7a8109000000225120c8fca798f6db05732136f92fb7c8c1c45587befa6ed8eaa267ff78889e288109"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT", "comment": "discouraged_template/basic", "success": {"scriptSig": "", "witness": ["ce", "c17787c4346a2348830203d75461a997cb3aba4b0c94368711f4a176bd0caae638388974fa00476bc2026bc8ba6f0f9171492b509dad14a30458e3f8263ff1955a"]}}, {"tx": "9590809503b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d717300000000b9b7f3d402c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf491200000000fce81ecbdf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c270100000033b2a1a001718862040000000017a91460db42f735e17b0d826006ad8d411b7445b1ec2087a6000000", "prevouts": ["736646050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "18e1db0500000000225120dbca3d60aa077317bcf96d9bbfc91ad8395b21f4135a99245cf89bc341b7de80", "0772f2040000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_78", "final": true, "success": {"scriptSig": "", "witness": ["85a26e9e3bcb204f7700cb039758a9c176afe9dfa5602aeca3f8b316dc77b54a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["f983104e30d5900f9633ba5ff5602e853141121962c70cfee77bcde37149f80d2a618118f0d1ea7faf59c7a0986190398a4c3ea74071c3223be65d20155869b95225cc74e94d4bd928b247c61bf3", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5caf010000002a7c9fa202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49e50100000081b798cc04590d650b000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac5802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e9957ba35", "prevouts": ["651e5d050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "277909060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_75", "final": true, "success": {"scriptSig": "", "witness": ["6b60927fb7bdb671d8ab7be781cb7f57d9e8d82ac9e2b6be5663a7df796ab444", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["86d774fe54cf197e162c4ff5876eca7d5eeaaf015e980799aff338748488bd823a0a608697cae8d80adb5530d065fce5c0989c4b64a3c8e895e1734452b819a5a63a68e6d70681ba5cbee1", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000003636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bbe010000006dcec48b6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3f2010000002f979df4636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b550200000057d91ed00108b2c50c0000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208706080000", "prevouts": ["4d9ea0040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "c15b3c050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "a93e29050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_31", "success": {"scriptSig": "", "witness": ["bffa35d6d31dcc2e65fb0d75a6457e682aefa3d4e40b6d0480eec3db69d6661f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "503af10e1d44e1d9acd8e90132a35e79c1b4ed9fac09978262f54de0d544947a"]}, "failure": {"scriptSig": "", "witness": ["e9aa5401204c592283a2c6fe7a9d6cde192b4417e48de4ff97047127910ef3ff", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "503af10e1d44e1d9acd8e90132a35e79c1b4ed9fac09978262f54de0d544947a"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71b4010000001e396fd8df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c33000000003984079604450b240a00000000160014c327e70d62d692d5959c72b3411fee2ca31c546b58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac5802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec20872b414b40", "prevouts": ["b0eafa040000000022512042af4e3a04a7b653bd844b863b33bc5a24c28e189e4b9da3cd7350fd65f1b04a", "59df2b050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_173", "final": true, "success": {"scriptSig": "", "witness": ["edf3a3b579b492ede959e9444767e4662391033e0776ae714a53692b004f7176", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["0591950d31319b35c6ec379b452f7348d265bd39f2862bb5298264733c5aaabd03dc5cc9aa317d6b8c23063d4c54b39754db00b8471684572ef85ab9a8f7a5e1d680f19c47eabd4cf74d5212531b08a15e8c0f17988cc78e1ab1abd73bf01e7cc914d5cd4c25a8734ae61769f7275a44e1a6508a4bd9de0b86cb01abb52dfbe70746b9fd7fe0e3928a611f21ce3fa6e62a35ae8f21f0181c6cdd0aecddc209a71be24d8937b0c6e1f93be2fcc3", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "02000000036a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d31400000000c9edb8c102c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4972010000002c1e17a5636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bc100000000b0b0feee0189886110000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac0b030000", "prevouts": ["a57a78050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "7aa103060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "007c72050000000022512025092df578254c31fe4066670eb3d98c4d225346a54b6d19a6a55eeeed80dd2f"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_49", "final": true, "success": {"scriptSig": "", "witness": ["c6dde9bcbd99d53e77eb49adf7814a21918d1af1d263c253f5c0c46d0ce2ee87", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["4c6fa0bcff8b417853ee0bea8abd88b482a859d9b1d53d9ed3129503211f619fb2285bc05bd1f3e20e7925d8db0e0079d6", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c4202000000686844d5b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7184000000004a5696d20187ebf202000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88acc7090000", "prevouts": ["3000ea050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "79c961050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_117", "final": true, "success": {"scriptSig": "", "witness": ["5459ee1b7b5d16b3e33fd362a939f3664463ea9078bcbddf1de1e778c4ccc10a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["cca8c087b870b32982ba6621174f008bcf30620aa09583004dae60acaf9931368adbea81cd8f3a4f3eddf0d5f662ad5abc6d13ec1ad7bac21fe0bf33c1f9811dab57e317e2a4e258509b26fc251664dbe5d0f284fbb4278305d18772f16ada5758df688abc83e4d7835a9aef0efa29616b734385d8", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49ac0100000008e8d2fa636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b88010000002b5ea1da02d272760b000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac58020000000000001600145e89b76f270f5a3384e042389be8f4c1040249260a16d438", "prevouts": ["367cfb050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "25da7c0500000000225120ba313323fbd6be5c1c89c77a4de927172d3267deb511e93e5b9a92425ca91000"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_99", "final": true, "success": {"scriptSig": "", "witness": ["12a52544e94579586f20e47261b276978b969f853e5f33f52583462d66c600d8", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["6225ffffd79bba358ff755ff31c7f5f96c8976900797ab67b0f466f7e21ff572be4eed81f979caa40606f8571838213a316800a401ae197625c53c2d3c24f2b4be7ea3e2c0b1a1e2ce8d83a07e4836c550803d3923a7e914b724b4bffc1f16c1a3828c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "b2d84710026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d36a01000000f59f588a02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf494801000000129f26ba038f39f20a000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd243025802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546bf9b2ed4a", "prevouts": ["3b3311060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "f1ace3040000000022512016419205b4c696a5dbb724624e42c25f49dd7de83fd616bddae2dc9c34c91fc0"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_24", "success": {"scriptSig": "", "witness": ["1e65e39aa8408a82e1e32ac22a9a3540c9975c36cd787144d70e198b232d5ee4", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "507ac15f05ff7d305765845ce4ec18bbcbede98b2f2f54ab5b"]}, "failure": {"scriptSig": "", "witness": ["04198696d7cc76065f160417da2aee5b26df306d7933cdcc53f0e7746d0a59f4", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "507ac15f05ff7d305765845ce4ec18bbcbede98b2f2f54ab5b"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d710401000000d760e8e2df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cef000000006be50fdd029b62030a000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb878a020000", "prevouts": ["29046e050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "eeea970400000000225120cf313f48ebb31eaf11e1061844714c85ecce85ab24d306e5c1ac97ef087620a7"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_19", "success": {"scriptSig": "", "witness": ["4b2a2c5a883fb124af7912740d48e4fc4ea41c5b3c1fbc0fa65c951825c7be43", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "5047fc75c7d808fe638a1a57b10c11a8433de0a4"]}, "failure": {"scriptSig": "", "witness": ["ff7fa24b052e1601c56c04925ff4ba59566f178594afbb632749f549147cb279", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "5047fc75c7d808fe638a1a57b10c11a8433de0a4"]}}, {"tx": "020000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49b4000000008e806388b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d710e00000000ccd9f9ba03c3cac509000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac58020000000000001600145e89b76f270f5a3384e042389be8f4c104024926580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208776000000", "prevouts": ["d28cf9040000000017a91492f22468171cec977b71247122c4506f2a75662987", "7332ce040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_83", "final": true, "success": {"scriptSig": "", "witness": ["2f2eacb6a022dc02ac4f10cdf4ed8fa59eadf1a81800fe2db1bc1bb675c34c15", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["4af0438c5f09fd563a91b9baca22f32c2c369ea8b7eacf7bcc2c5128e9bdd5fef1d41280527a6708daf3a052ab88c0ce1474d8c5c793f51f7f6701c649452ca96331c2ca2be48b26ede5009714ecda1b72b1e2", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bcf01000000a72a01c0636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b6c01000000677869380127d5180b000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac4473ca4c", "prevouts": ["faf9b7050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "23bc990500000000225920d8103542fd26eef79006879e481ff31a67ad980b893420b2253e9541a0d656c6"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_46", "final": true, "success": {"scriptSig": "", "witness": ["f1cded3c373193d9bdd0a4b93dcd02fb75487c3a4f967fad96d4adfdf5c4363d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["2a4471365854f6bf8093279d8a67a5783cf7a613ecf8ad205dfd51ed4728a3b76500a1cc4ae340c617a027fc1cde", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000003b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d715501000000116be491df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c9001000000fee3148bdf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c9d01000000775c4bf5016fcb150c000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac9f000000", "prevouts": ["4e8f9d050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "018c29060000000017a914448ac9b0278ed0c7cee35a566ad909ae9d95760b87", "5166e50400000000225120a27a4722800bee09af9967ce66bb095129c320e4466c12883ec2f3b9e1ebfe58"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_4", "success": {"scriptSig": "", "witness": ["b9400c4a24492ead69c24b5f244e0068c14dcb3f56183dce2cec57b87e352b1b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "5035fa843f"]}, "failure": {"scriptSig": "", "witness": ["6b316643176311e74b88eea5fc0ee22615c6c792389428ed54976ed36477796a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "5035fa843f"]}}, {"tx": "0100000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5caf00000000ee9a5c77636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5be600000000b5d815c702cde5f40a00000000160014c327e70d62d692d5959c72b3411fee2ca31c546b58020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac14020000", "prevouts": ["0b555a0500000000225120ca1e416ca31036a2b6bd1dae19378d2a8621b36d7e60bde9edfc0bc8e692a2ec", "cc9b9d050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_124", "final": true, "success": {"scriptSig": "", "witness": ["cc221d67322f625ecb330d986f8412d6a4be701979b1af1ac4d447f29517c9fb", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["c5f04b830876c303de16b0032272f422c323976214a006ea6cec077837db6e20892a8451b63acabada4d81b85b915253125ea5172dd3ddcf51d45490b7e62773c2ae2e081e75dedfbc20ac67ddb12a51eed47571566798866139982ec68e0131d25607ed78f91d49329b0bf71dc28dd32a02b74940cad9e587e6858d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "02000000016a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d33b000000002a33d98c011fd33400000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88acd4000000", "prevouts": ["76fb30050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_235", "final": true, "success": {"scriptSig": "", "witness": ["970c6f841f2fba62cf501efcb35f37f086ea6e2d74d106e63b7c008a2690e6c4", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["793d3d0aa8e59520a6ec6d141afa646fb88d0bc78e04d6a5b3750040601e6e69c3ed52121c1bfa5484eed76b247c9d097c17bc4992ed4ed8a652a479fa94019d4f39f26ffd8bf93587bc22dc44cf3abfb6024878ae9233753e27b0e4444edf8d14f4eff9a473a4ef66f471f04b725a88abe21e80b4229f7d950a75e7a6af903da10e43b12ba6329ef74411b95b0e43581d5affe9dca9336b33ef1c7fb327fa44677c1ba819b867617046d340c59498c7be1861d474d442d6258ed82874bb48513112f071aa295b5154eda3c973999ed976158cb5cb42ee82ccca64b97140740cd943f4899ece1224f39ce7", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "d5a5cb3502df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c7a00000000e711b18c02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49a801000000df1141ab012dc6da0500000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92ee70a0000", "prevouts": ["a86fcb040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "843fe10400000000225120715c82a34e576967291dd9788042439caa2b713298d1e5eb663b1ae916247246"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_35", "final": true, "success": {"scriptSig": "", "witness": ["36dfaec5fc076a58abf93a55ae0401bf04dfddc65411bbeecf708a2a3cced6bd", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["e438be115aeeebc345d566bdaa6c82233ee3eef3f2fbc3e08bc5a99bffc420d2fa0f6a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000003df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cd2010000001c2f358bb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d714c010000008a8b82fb02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4955020000004e511eea03cb018a110000000016001486053ceaa6b6ea601bdda3b6220dc7510448595858020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac0b030000", "prevouts": ["3d4260050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "3da517060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "622814060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_130", "final": true, "success": {"scriptSig": "", "witness": ["aeb4ddcaff9da6defcbca48175aef8a65caf93d5a213e63bcd086ee27f150ee0", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["39caefcd349bfa84a3fe1b53e937f5079b327cca6312cec5cf87609c53c11c34c2b93a7b5c99f62ab825dbe50c0ae7590485902072c89e63247bd4e8a6bd5fb076afccb38ce5454242b218c9a1141bf93e20d231227491f9897acef1389d6ea4bec83b88d67860803edb9c16ede20c0eebe311863b264bd1f0b024b61fa7cbc4152c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "01000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d38b010000005ecfb62902c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf490f0000000020b3ebfe025b45c10a0000000017a91460db42f735e17b0d826006ad8d411b7445b1ec2087580200000000000016001486053ceaa6b6ea601bdda3b6220dc75104485958e9982d5b", "prevouts": ["4d0bd7040000000017a9146055e93810b082b4ed1a78beca939cff2ea6692587", "f797ec050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_34", "final": true, "success": {"scriptSig": "", "witness": ["6ad240aa6ddf8b730c504bdaba928e86d255a088c19c348f4b21246e74207ff3", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["1c76ba027aaec718fcb228bd047867686b08928dc0a82692b2dc3192e2647abf2758", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "85415e1102df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c4e000000009dc075a06a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d35601000000a4d9d1fe04f035a509000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338758020000000000001600140276cd59f2bc98ad777ccf7057f574395bd243022f85fa33", "prevouts": ["024001050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "1762a604000000002251209abf540d02a006d2085839f8596eb3248d80bc1112c39d0ac585f29f0fc44790"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_212", "final": true, "success": {"scriptSig": "", "witness": ["a7a01ac6535b2c5117bdb802c9e4dd5d7deddc0c198b742be69a754ce00d580c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["2a4f5ff9c0193690e89026a269cb1bd8777a764f4af97b55e7b85b500c7a0cd4f82720f84c1d857eedac05782ba02b0a3abaca6547b0cf5ea8416511b8f2b477139ce92927253d80913ec7977326add8e3789c971c36aa551c4e09690d02c8bb59a622002694ad4cd62682f1ffc682b155bb746394fa85dffa49035b650253efa863366dd6b9014ad3b4944b44fd37deb7592e6e5ef9bf26822da484db4b75c99de52a65dcca258eab54ea050fdf5e2d0b4ccf306eec5c8cbd8c6df63044421fbb85e0f30db2b38f5a6def3593de6cf15705849f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "7ba413c901df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c8800000000a1e3a5c502927f3605000000001600145e89b76f270f5a3384e042389be8f4c10402492658020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88aca771e21e", "prevouts": ["fb1839050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_176", "final": true, "success": {"scriptSig": "", "witness": ["235229e60a2c3b9ef7cb34fd652b516e1c94aeb90375bcc423057d9a6108c291", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["44bf81b0b67bdf7c7bb3550ce9d832d3a4fda97fa803c31b38438c6efb9d3d10ef074b581b7da5405d75da1014497f03ebbad0029343a06c5f66549b3286aa85eda67202fc0e26e5e57122cd2cec4cebcb34c4a487b7ae9f85772bca85a3b8c3e8f379df1bb0217cce0a39f91177622c2ddd116e7b65244a443464efd6adaae3085944116e448203c47261443be8b282350f91d7d8474f373443c538c7a5f3c67733c1f4e1c10eb9f597550b964f0989", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b1b00000000cbf64469636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b590100000007b5016d0239cbc20a0000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb8758020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac06070000", "prevouts": ["c8c43805000000002251204b2a100c1d89b9bb6ff7a65ea661a8806e84265c4fc3703eef183ccf52c90362", "dd0b8c050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_209", "final": true, "success": {"scriptSig": "", "witness": ["b950d5a15fb72f652882455331dc7d935481d2e70f06922b2a141f81267b908b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["576be200ba825608eb0da53b8ac6134ba2cfb88d723219fccc7ac4f31c513129189da908a51eae14140803ea5cdaddf3f4b1d229e759d3ff9a1698eae92e59540296d9f83cb5f52cc9d9f81e79d23d49e92ad0b1dcf89a45f129cd5eebc379608837e36a31bfec12fa4b8136f2c38459494bb0a6ab1e604751dfeea7abe4ea8ea7c56983ce829ba88ddaf9619cf001a4a2797cb555dbb2181130dc357ed1613c0cb85d620806a7cd211c4bf3019958fb4b808ab66ceb316a0037d6e874bb98d8eddadf448f411826690273437629182820", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "ebd9ad4d03636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b490200000070bb87db02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf495e000000002640d28eb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d712d0200000082cc45a60153fda7040000000016001486053ceaa6b6ea601bdda3b6220dc7510448595895010000", "prevouts": ["d59593050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "ff27110500000000225120a27a4722800bee09af9967ce66bb095129c320e4466c12883ec2f3b9e1ebfe58", "92c22c0500000000225120d80c4d77af017c242f67199413362fc6f538a6600f5e6728263300c370cfd1fc"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_205", "final": true, "success": {"scriptSig": "", "witness": ["3c4c47de0c0376c82e1a404a1d261a124f7e560602caf7183d4f8128dbab889a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["345a0bd717d2d2377b71b9c1b3b952205e8dd4c97dce9249874dcb9e3444ac51d004fd0687afb81faaa025aebe3926521af6274de53d089f60eb71c54cf32bae42ca5d56e4f7ca5430a7093120cef9d384e187ecaec361f37fc604cd5a5a8555a7f03de751337183a642458a4d21263083f5ef47cf7e74aef4775b0b66721e54d514d5458e44da0b6db9b857620a2b2f0359cd36a99b221586b1ed7590b9746cc43d414ab44934cad38a9d5014958a59c6fea286629084e3fb7fc855f8be0fe09aa73c56b46d28760afad13646", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "01000000036a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d34f0200000044a8d55802c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49a10000000009bcf705df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cf200000000c4bed6c70398e33411000000001600145e89b76f270f5a3384e042389be8f4c104024926580200000000000016001486053ceaa6b6ea601bdda3b6220dc75104485958580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a3387ef020000", "prevouts": ["17da72050000000022512019fe6744b3d763ac154055cdaee0a9f831b2ffbeef5666f7b5dbabffbc8d3f13", "424e1f0600000000225120e83b1050ee9fcd2a3da4b8b214c20b8d9e84964d497f4b9caa00a7856fe6b84a", "8c9da4050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_74", "final": true, "success": {"scriptSig": "", "witness": ["5fbc64ed968dd1e68c214ba95cde1bc02661170d88020b7d75637f3770ba5e70", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["3dd0449e88c00c73822bb5eeefb0a46ed30fcf5749677ed66c61f31f49cb3e9d78d280f84a29ce5db65e2c04addd00bae65500790a073355f5d68fcd17cd4e0ae2e0dd5bba83bc16ba5f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "b5ffc06402b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71ce000000002acd5eec02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf492d020000002ffc54d1037b2fec09000000001600145e89b76f270f5a3384e042389be8f4c10402492658020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd24302a4010000", "prevouts": ["b558c8040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "c32b26050000000022512090bbfe0215597481aa954f7bd70bd281f8a97f33ba923ad2fd4063dd4a04c780"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_2", "success": {"scriptSig": "", "witness": ["a613bc9a9620f2a0dbb7e8b6c7bbcf1518b38db0c0a641f761adf7b0790ccbd7", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "5043a1"]}, "failure": {"scriptSig": "", "witness": ["3e8150b206395ff3f7cabf27745cbd74913acc2be1dca6dfad63c65fc6d5ce61", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "5043a1"]}}, {"tx": "0200000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5ba400000000fd5961ea636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b15000000007b4213db04c3cbde09000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a3387b3d82f32", "prevouts": ["d64814050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "de39cc040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_225", "final": true, "success": {"scriptSig": "", "witness": ["5b2b66fec9d02832b681d1011b7d2ace407a63e6baac12fd451e132afb4c530c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["8a9906e61c4f70e7efa09a46a5a375bce95c624589fc34d1fb2543f7382b93b1726039751ce9b1d05f11bd4aa80f693d5e030d4916f0dbe78ccd55087a135544620b969ef3c97a12d7565fa2b802c3551b30ad6245ae27ed07722e1e9001651a2bccc924a1577f332ed61a84b34c4e6e0633375e5620d21d63a5bd8d15e19e8a029c297b70e2e8fcfe932fea91cc69c1eb9777f3b85e7f22690663802b0a439b66abdd2819db84bd42b8196869268ebf7ea41f4138e318310ac225f2eb28a8f42b859c6d79684d106ae00e8df9204f030a729cd85c64a7716d5a537f88c010358f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "02000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3910100000009a7c7b402c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49a5010000003a5d5efb04430d030c000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd2430258020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888acf9a7855a", "prevouts": ["cc3ec4050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "87c940060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_133", "final": true, "success": {"scriptSig": "", "witness": ["9492df50373578bd0d6bd667eaf88f7d9d3bbcf58ff772fe076814070485ea72", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["59ff939649013d8a5fececc4391719111131a210b97bc0f97d4c228ae90780bd46ce0b09663d255e56d430dd9992155ab25a64bfa090346c005c2d83389be3021d127fc0ee415c63db58a51a0bfa8eb7808e3a3f72f0af70a88dda56961c7e94140d0ff8ec5110934eedb2a3d56fec3d01d21aa740f1fe9f6a87139962ae371b23c1195623", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "010000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4938000000008fdc1efedf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cb800000000b9dd88b20388a79709000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac580200000000000016001486053ceaa6b6ea601bdda3b6220dc75104485958580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a33875114f82f", "prevouts": ["b52ccb0400000000225120f429379794d9addc587a2a1fe5311faf96ad71c55796a74e587fce7f17630cae", "0a2ace040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_4", "success": {"scriptSig": "", "witness": ["144754858801e2e723d93e9c601b1cc468c5bbc33ad26e656ac924b3383c02a5", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "500ea19f6f"]}, "failure": {"scriptSig": "", "witness": ["f017212152f67f79b463f1b02af391f9fe756ebaf97179205ab59930896ee4a0", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "500ea19f6f"]}}, {"tx": "0200000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b9600000000360f628c02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf494502000000cd7d4f80048340d909000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac4275085d", "prevouts": ["2f7bc8040000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "300113050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_213", "final": true, "success": {"scriptSig": "", "witness": ["cb700f42fc945e4daa9be2b7aab99b5675d4fcaa2c043f4c6e558afc4ac5ee3b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["df7543748f81abca946ca850a8527be85c11bb046a41ec3a8f1ba08e2bf1fed1a65f2cc3c34d18a2414196ba67a478bd0ed4044e3ba20b9f8b154dd7a98aa8f49f6f317596b7ed0c66248ad45216ae907558ecd2aa87c7f09749f6da76757ab12ec4fadb0682bf55c1ca24d925477dde1ff5342300d95b364629d598fdd3f3e87a7c54b5ea31716063ed396984a6e0101433a4946b9a07b5a06c48857b3fb76c558627aa6a4f9ab1da4b78e7c7006503899bb3e316ae717726c8f602dbc70bd5f27fcf3bf44361e6cd38daaa60399ba8c7d24bb362", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "01000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d328000000001900bd60b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71940100000034a66fb201a1676e09000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ace89e0f40", "prevouts": ["f7fe39050000000016001449c097b3056aef802f64eac4cb5fc1287c6001b8", "f4666b050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_5", "final": true, "success": {"scriptSig": "", "witness": ["b4a50c7020fa56933d8c90dc8bcba568ea62d4b52fb1c6923541d7a63f49adb0", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["ef941a10ad2ad2b0402e60fbd6b22de66a8df0834ae447ac579d600917273fed", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf497200000000845b4f83df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c0502000000b0780b9901243b6608000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac962e2c2f", "prevouts": ["277eb6040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "c726b005000000002251202d59d680ca15a822d37a83977023cdf2c04104ebfd3fcf001a48bb4bfedad9e3"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_203", "final": true, "success": {"scriptSig": "", "witness": ["884eec5de52f95d212e4c7a8ff7d0d9ff77d8ea10afb928c893080420b0c0abf", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["2d4743ce2ef05428923fcc122952d6ee9c28eb9646257be7ddb77dce73f3b861bcc650301e386198c9036268b7a09b540c558c8c08485f5ce750a249820da1bd4b5f355c3fa67a526ca6d8f76d712c80bf8346411ec0d9334bcc22493f74664aff93149c666532d7ba813523b03fe2e87674c952b0c93be0f733862bfdb331a8123807351f9d7d461b811fab894f7c1f155f3b9b199584576c132148e7863eefd52717e66cba770e644fd5ea12e687befaa84ca23c2426e2a0179f514e6e4ac2eb1d41100f0805c9d023ac", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "364df15f026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3ce010000008a9d8cb6df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cde010000000d6c7aef03758e1a0a000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac7fc0e151", "prevouts": ["a5bbab040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "a09a710500000000225120418d73c6bf8f444183c700c7ae5bac26c3885d7e615de196bd1913b9f0027126"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_13", "final": true, "success": {"scriptSig": "", "witness": ["283054b71abea7e5ff4dd3a5535c446ca02d14780833711cdf93bbae60416ce1", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["4b7420c9a1bdd048bb7ead5b89", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "02000000027ab117a2c2de2455cdd9193e79e62dfc25e25af2afaaeae0ae2fad20ef71b27a84000000009b6988c1b5eac25153f86bb5e4f49e5dea90b7c524090003df0b7f5033c6b56bd7c8ea397701000000e7948bc302d658d8000000000017a9149de8222a13691cc2b988d686549a6e3e312ee4648758020000000000001976a91423b827ffd52d1d3e18aafbbc8c7b56fd6458151c88acbb010000", "prevouts": ["5c4d9400000000002251201f8ee8b6ed5374077128a09db82b33b9e29b50e40e4ef3e1dd0eb5543696cbce", "ae144700000000000463ce6851"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT", "comment": "compat/noth", "success": {"scriptSig": "00", "witness": []}, "failure": {"scriptSig": "0101", "witness": []}}, {"tx": "0100000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cdd0100000095d14d1c02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf490700000000424f54b8041854700b00000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac58020000000000001600145e89b76f270f5a3384e042389be8f4c10402492658020000000000001600140276cd59f2bc98ad777ccf7057f574395bd24302ae060000", "prevouts": ["0c99be05000000001976a914ab1f96d7e62361183a69d20eb1060ecf60c061e788ac", "68fbb3050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_3", "success": {"scriptSig": "", "witness": ["0a7c894d7ea1a9baf41d45f508b73c6c166e08243f7f9b5a5355a3abeea28a65", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "503a07ec"]}, "failure": {"scriptSig": "", "witness": ["8d0727d34e54f297819b4a651bae2e4db60fe03e2da909bc24d36c2da44e2a74", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "503a07ec"]}}, {"tx": "0100000003df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c9c0000000011f7e58b6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3f101000000c0ba0f73b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7150000000002877ed24036c926511000000001600145e89b76f270f5a3384e042389be8f4c104024926580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a33875802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92ea3010000", "prevouts": ["038315060000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "16b685050000000022512020f87ad80e2594f1c1791f1e4bba1aa296bb996597ffa0ecd13ddf7fd686d2fc", "c776cc05000000000463ce6851"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "compat/noth", "success": {"scriptSig": "00", "witness": []}, "failure": {"scriptSig": "0101", "witness": []}}, {"tx": "0200000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b3f00000000fee5acedb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7137020000004fe9479b02c8bd5d0b000000001600145e89b76f270f5a3384e042389be8f4c104024926580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a3387f5050000", "prevouts": ["ee0541050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "631d1f06000000002251202630a74615e8f77b200aa7f36f21efda4b827bab2a2877b79da46b0bc2937b03"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_56", "final": true, "success": {"scriptSig": "", "witness": ["1d58c4bc22c0d97bb58e0f3052675a14ab0d88daa157487bae2bb548964f00e0", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["a7464323916e3d0e49eecd677479065b00e5f2e5bebd950a549563672a882d9464af0336bc96c2926e5ecfe5e65a10277c0f04a9a4a85360", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "02000000038a241fda3ab03fe2f04af98e319a0e5528353222af7cf0c8ce101792b0c746620000000000145743868b8a8e3b30ceeefee1e4e48b73d8c77dcd7e9990957c54ae82852719e96e3fa1000000000052d98cb98b8a8e3b30ceeefee1e4e48b73d8c77dcd7e9990957c54ae82852719e96e3fa10100000000c13bcf9804ad30d4222000000016001495ac79ff2ea7a9285771021da5181761a06965625802000000000000160014a19555480a42900bfe46d7c2b6fee02b239f40df580200000000000016001495ac79ff2ea7a9285771021da5181761a06965625802000000000000160014d0b4a64c173703a4137b52a32ec050664267eb745c020000", "prevouts": ["faaeb2310c0000002251202458cdf8f6855b9994354789eb4d16047d14d9e98d5cf947e122981294b84c18", "6ad8a96f0a000000225120c8fca798f6db05732136f92fb7c8c1c45587befa6ed8eaa267ff78889e288109", "0a6e7a8109000000225120c8fca798f6db05732136f92fb7c8c1c45587befa6ed8eaa267ff78889e288109"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT", "comment": "discouraged_template/emptystack", "success": {"scriptSig": "", "witness": ["ce75", "c17787c4346a2348830203d75461a997cb3aba4b0c94368711f4a176bd0caae6388cdeb0de8daf44e986d19e114a7b8ed70d46e74ed21bd6c6e785c2a6747f82dd"]}}, {"tx": "0100000001bc7bcc5aa051508888f61229926769abec8541eb3981ca65fcdabdaaa00d48f600000000004a1754620411a0e7dc050000001976a914001ab88085e18cafc158818ee31fe7a878a6d87c88ac580200000000000017a914d5b9cb0101be92ab1f53a401a2d8e15656cfb6a88758020000000000001976a9143914131373d4bc79f37d80ef681d40e718b6889888ac580200000000000017a914e793238ddd61b38f03a12806f251588c5da34419877adf4b33", "prevouts": ["883de9dc05000000225120c8fca798f6db05732136f92fb7c8c1c45587befa6ed8eaa267ff78889e288109"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT", "comment": "discouraged_template/basic", "success": {"scriptSig": "", "witness": ["ce", "c17787c4346a2348830203d75461a997cb3aba4b0c94368711f4a176bd0caae638388974fa00476bc2026bc8ba6f0f9171492b509dad14a30458e3f8263ff1955a"]}}, {"tx": "0100000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5ce0010000002f889a5402c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf492701000000e11c573001b5656e080000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb87af070000", "prevouts": ["f1031c05000000002251205e8b0e8f2228c19620c6ff3c4081751bd5de4f9369c8c6823061f3bca17c246d", "510edc040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_170", "final": true, "success": {"scriptSig": "", "witness": ["65f06cbc50c71f127fe492190d65de32428366fdff5e215d9569ef726249ebbe", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["b1f4d83560ae958423e2d4bfc8368d504b00a47e6f1ec7173c1b9867f97e5545b4c4bfe78d7fbc08c381c9bb7f96ef249a4e69a809028a7750440f0891a2a806e6f4a5e92538663905f2740633d60ce6b1517b9c34b063c336f0034826251ae3267d93f7581559924d6c7780113ab252c0d89472e19d70fa72288b72c59be475d2299fd3ccfa215be3b902f37a7bf7c81d883ae36d332ab0a3233622a2b35413a1bf9f48ce046f8e1aa4", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002080b626bc545b9af1080dd771acebd9e69167f34d1a040bd9ba4ed32550827859e00000000596bc0f0080b626bc545b9af1080dd771acebd9e69167f34d1a040bd9ba4ed32550827853f01000000fe45b5c702cd275b00000000001600146f4a80043d70c971a209eab0abf54aaa344fbd6458020000000000001600146f4a80043d70c971a209eab0abf54aaa344fbd64b3df212c", "prevouts": ["a3742e0000000000225120e1205ee8d93c1546df2be29f235e6fa52f9ec8a0e44f99c6dba04fdfdc16b97e", "75642e000000000017a914e38dc88d88006690cc72040432afff31ec4cc2d787"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT", "comment": "compat/noth", "final": true, "success": {"scriptSig": "000463ce6851", "witness": []}, "failure": {"scriptSig": "01010463ce6851", "witness": []}}, {"tx": "6768ab8b02b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71cf000000009f5e5ecfb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7110000000001da198cd02632cb00a0000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb8758020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88aca6090000", "prevouts": ["c3d0f3040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "ff42bf0500000000225120740bc2480d724525103615d68be701d65b71691a22e691ed47439afb163c3df1"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_65", "final": true, "success": {"scriptSig": "", "witness": ["00865fac13cb22e967a9b187b41ce54305e338db64fcbd9504f75a0c592f8f92", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["8a710782f8a0ef90921bc87acd1f07228ab8c4c3c0e4ce203af9984c2b8a5bffe2bc780138fd0a647e9239cb3e3c42f22136047cbedcfb9e4637ae11c46a25ef5a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "01000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d33600000000bed015ccb8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d715500000000cb0beed304f5c9ee0b000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac58020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac58020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac5802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e3a661d3f", "prevouts": ["4c8413060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "a4c8dd0500000000225120b13ba20c4fd1dd8dc29c377d0abc896efec7957488ae9de03e92174b33c94e8c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_190", "final": true, "success": {"scriptSig": "", "witness": ["d860dea20a873a51594d8502a57912b30acb753e3db37b85a058eed6a86c52de", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["ae086f2afba55cded3b8dd95a6536320183a2742084f07ecaef2a665e6c897b8328c0c49b1d409d653bd51bda401dd8331ced353d4c3c03f27a37684e4147c41ec80189107b00e937d920075f1c62905aa4cb0172abafe38505c31acb36d7435d97a9e4efc5ede02368f05baa44b1f5ba5c3fd84b0c1e82dd17cec9814d01d615d1613b211a4d7ebf3965095f35cfceb7dd99630caad58d25922e0aa42715e12b8b8521772bb861c04727d7f963de73ed958dcff9ca23058960d8be1177f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7146000000005396c0d26a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d30f0000000020c762cd04e4ab200b0000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338758020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd2430258020000000000001600145e89b76f270f5a3384e042389be8f4c1040249269a040000", "prevouts": ["2a734f050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "04c8d305000000002251205f359b0c56fb94cc824c7891579f1c80f5cfbafb82628b3b456b347920082c7c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_218", "final": true, "success": {"scriptSig": "", "witness": ["361a9feb73b5d7db9094607c8d684526300a23e02c4660869cc67c5e671fbb99", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["93353c66d42a67daf9d1037edd7fa9c815f557103b680ce8310ad62fc12b605c43c841bee8cbcbf8b79e643e9ff5195a65baeda8730105f1ebac438c66f2dc1833f54c00bafc5da5ba0893e4e2216f5d03b7dd0f2b870fe3c425b613c13a3fecbe6757281338ef4c7af78a1e3a0bd08a60c79281f3b0e9e56daab40ef2338be168b5e9de5ab42c6712e1efee109a8568ab35b6f081f37b877e8c5f51379a542645e7aad06c4e556b284069dd89b6a00bd9bb1fca84c5b3056259f71568404f1bf57cba136714f4c8dbfb1f21e7dae201f491ee0b3e2161180317", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "22454dbd0202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf491602000000b0c22ec86a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3f4010000001d240cb6014db6d7000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a33877c000000", "prevouts": ["241bcc040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "a00896040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_84", "final": true, "success": {"scriptSig": "", "witness": ["f0bece49f9b5d6c527a4edc1d41973dae211ee9754fd47fdd3548718a98eefe8", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["597a43ecacd28e79397c29f2a88abe118c5c1a3f677506b3467e7b4ae5d174892d4532a8e208f18b97afa4f5b4fcbc872feeddbde977b78e4c9c05703522be510bd4526f2c858db6e6e92d00979904ef1bbca4d2", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "39ea2200026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3a3010000001b57fc82b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7116000000002530e2b10192b52007000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac298cd444", "prevouts": ["b74eae040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "21949d040000000022512041e83a6ce1fe58d5624d3309506c6ac97bb88a0e0cc6adada0a8c79fc6f4855b"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_6", "success": {"scriptSig": "", "witness": ["e34780d48d5173cf6c8c9b5fcaac07e8e4faabb7706b6493566b98fd958b5f05", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "503d69419812ef"]}, "failure": {"scriptSig": "", "witness": ["bdf7dc4a290ab5e7ab6518e5858887462ea861ce79f2f6e9df126d17d74a6d28", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "503d69419812ef"]}}, {"tx": "010000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4990000000006ddd194ddf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c6101000000d3f2020b01753de004000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac73d8935a", "prevouts": ["6a0738060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "ce3b4705000000002251203a07aac2e51d2a33e31d2769c77d72bbd2da3c7375a743014bd6f831b835abe0"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_100", "final": true, "success": {"scriptSig": "", "witness": ["371f0fbb5afeee0334201f231a627320e439fb9fa02d86f5514dbeeb7d8538a9", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["df718a3819c7e4e9564aa59337b1579416ab33f05be867af8865bd241ecd8286550fd27679142e5d3ecc0b538807798bff13bd4fd981c0ee5d8c069b738bb33236c361371311e10ed82931b003041c23c51009861dea4cc3936deaf6e0e9ba137c411b42", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "75baa9870202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf490601000000be7887fbdf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c5802000000f4b6f6b9036297ef0a0000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338758020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd2430269020000", "prevouts": ["03f2f704000000002251202630a74615e8f77b200aa7f36f21efda4b827bab2a2877b79da46b0bc2937b03", "414ffa050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_7", "final": true, "success": {"scriptSig": "", "witness": ["ee44bc1e2682658fd88ad89c8c1546e01964909a1302cd6df8a75d127ec7643e", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["d1cb0eb0fc1f768dad810ccebf496417794658a112d9c8c409003448a04d4354", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "c21f0528026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d34d000000001fed29b16a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d314020000006e10c49204078c7b0b000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac58020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac580200000000000016001486053ceaa6b6ea601bdda3b6220dc7510448595844050000", "prevouts": ["28fbc7050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "0ea9b5050000000017a914e5fa33516d725583dff8c561ad783a1a7296c80587"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_101", "final": true, "success": {"scriptSig": "", "witness": ["d8815275f15c3fc5fe44d1cdbd7fb2686f566289349d930c5942d57ff82f6c1e", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["245663036726b97889fb006f8692b66a70d22b31bfadca6907f0532f9dfe805215964dd605deb69300fe62edc4712ca014be8fb41db0e94692053f864210891726e3e9a00bcfadf39d82d3168238196d31c2515cb6c9636f206f036b22fea61434dff01797", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0fca066702636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b9c000000005a909ba0df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c5e01000000d44be9be0319bb710a000000001600140276cd59f2bc98ad777ccf7057f574395bd2430258020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd2430288070000", "prevouts": ["eb0d68050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "f7620b050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_4", "final": true, "success": {"scriptSig": "", "witness": ["9c62c3a4dbbb67f9ee474170164e8812b926b0d2d96dbc299d8a2bbba92d2bec", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["d6de983d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "07bd9d4e01df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cee00000000114379d203f355880500000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb875802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b85050000", "prevouts": ["2a018a050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_11", "final": true, "success": {"scriptSig": "", "witness": ["80919139ab81b409f03b0a8d45ccbab3fdc0c22fee15368739e166fe67384515", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["333dc3351820ed847ac79e37295d49f6ab85c65f6cfc411ca6a1c28a099a9c86", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000302c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49d300000000f86558946a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d31a02000000c275cfb16a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3580100000032d458a701b1e43d05000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac08030000", "prevouts": ["7476160500000000225120c983e27b5bf9d93903dee318ffc9d6fbeb524d90969475b1515c66bc40021293", "4f118e050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "fb1587050000000016001449c097b3056aef802f64eac4cb5fc1287c6001b8"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_240", "final": true, "success": {"scriptSig": "", "witness": ["9a8e6a40a470a1edc5f44b7fcb746a42812cb1d049ed4d3328e48596650e8e38", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["1d94e1246a138769f651d4747ab4f7fcedf4e2c4af40ad04f8fe4ab2d0b85d25f3406d2024dd3cf30aa77ea08dd9fcd2d624bf9abed4652dbad8101886190748aec42083c189e7a0b8909deaf0e97622781fa69a548f3cd86efefb5d4faa412a62774d9f15ed693dbd6606ee94311563fbcccc3fb3fdb9938a131710854422e75cbf8dd9c5529d10d9839fc4156694281847286bc1a5ee134c638fff404c37438e1b757f07b83e171da3eb6b62e5b7a0e15f7e674ed89f8bd18aea7dc6a678de47a5997498ffb4764cfd85506cdbdfe526a418b331c2c3f952401f571be6742a2dc109ac1d9bf58b0fb537bb45f84ed9", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "01000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d389000000008cd60cb6b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7100010000008b05696c02f1bd190b0000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb8758020000000000001600145e89b76f270f5a3384e042389be8f4c1040249269c030000", "prevouts": ["4d5c56050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "af5ac5050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_41", "final": true, "success": {"scriptSig": "", "witness": ["fdba5bc80eac4905393217784e42d26472a0f52978834cc49e4b0f54a793cbcb", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["5e4149c6d201786d94eeb094f39029b880a73ae734cb95891503defafe05560f6fd0c4ab59124d887d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "01000000016a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d30202000000305fd90504955d0d050000000017a9144657010e5cf55af6acb627784c227caeaa0f0a3387580200000000000016001486053ceaa6b6ea601bdda3b6220dc7510448595858020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac4bc0c364", "prevouts": ["b04a0f050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_189", "final": true, "success": {"scriptSig": "", "witness": ["14e1e2493c2341a413af02b59e82d329440701ca5f670ee91ee9fdd74c49be06", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["2043349318d74963c2341df7b66f92a249cb66da92ed6fda720f8e8b04f3f033b28931ce6bfd9aced69deb19be79fff16eb23517fcf28224ad87698f85a4b3aa7c0116edc4e016980b7e814619d3a63384d76fcf640f6d4d99a5cc1d0e6f35123a47e1e1fbb8ad9b427008d2651c92c89e99a1ed013387fe093cc7c4a36b7690c670c65ec012fc178b820380263df69ca00780c0adcbc772c7dde172f6758594a7ac64e507a409929b13c278ee18ec3a6d2915ceefebff1fcfb05fbb15", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000003636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b21000000003955aedcdf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c3b020000009e8101dedf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c80000000001e5bbaae01beaafe08000000001976a9141c428f4958c47293549411153bb54f9c0588618f88acb06cf922", "prevouts": ["96f2ac050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "df355a050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "4f89e704000000002251205839fcabdde300f30bb3136a6942e7e1978c418011f8aa978422b1d983a09497"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_254", "final": true, "success": {"scriptSig": "", "witness": ["234dd9758057863b84bf4d9761693bfaec5fb2b1ce60a78a90128fa6c3c867e9", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["257a0a44756843e9daee503d494329af059ecafb53f4799e06d20c309f51fc686dffab5a4170ee7004e25a4c92ff435caf718775b572aaeddd216075c19a61162af3cf2e01061bad2adfe816e5632c97f7467c5c77515e56225e594b305faaa436c25e5c1fe5ac91b69f9ef73d3e9d80484d6cc3cb6ba968b788e52f2a4a05ebe842cbd15e718fb47e5b8855ab993447838f1895d1b83b78f8caa45588ee61ef7a494e562291c66a5eb8a17ea72a8360512abc4da0ed861afb100477453cd3c809d130d126faf145809d94c52ab2a4bbcf09916aab1279d4a1104e22ac0c885119e2a31f0a49cd561576c95bf62942b415a2cdaf7a3a3b673f2f966a8d65", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000003636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b0100000000533c57d5df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5ce9010000009515bb73636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b750000000068ae99810382a2f90f0000000017a91460db42f735e17b0d826006ad8d411b7445b1ec20875802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e5802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546bfd020000", "prevouts": ["3cee4b0500000000225120888234ca5411be779d2dee188f05cb1257ce2abcd752b2365d5c0bc78310a8c6", "1ffa4f05000000002251204f7dc7ac5edca563e9f85142a4cc48adda095307601bae6dae05a2f3e7e26a00", "e73a60050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_153", "final": true, "success": {"scriptSig": "", "witness": ["41d852d3b1ed3ee5732630db49ec2c9b38f056e4dcbf304182e9c8fcfbc6b4fe", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["0501815d6f2e43caf200477aa76d80a12a9e10297b5c3738d320bfb9b59b552873c064c89fc4ac2cca68d5c997cdd1d780702cef43cf51f7b2649f9d923d9ec75c1055f0b80e1cfc36281b494c5d58153aea311709f344eb441c3d4eba5e753ffc2263cbc7b9f5a78af50a6a08eb71ee071a85eb165f16af205f3901a5731a43e57b4df759be918780df226727e17ec4e22105e1cd2424950f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf495b00000000eb4f9b9db8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d718501000000a06d3ff70245b1fb0a000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac8c090000", "prevouts": ["89b88605000000002251207e04690435483de7aa7b27f36091ebce5bc4d5aba66604e4c1aa9ff745104f76", "d88077050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_2", "final": true, "success": {"scriptSig": "", "witness": ["617c3eb69e12653bc7b14bf3367fa42f42bf2d1add52fa3fd1bda4a44c074b4f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["3ca0", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "02000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d33201000000cf2af8b5b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71640100000015a29484046d3b4f0b000000001600145e89b76f270f5a3384e042389be8f4c10402492658020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338758020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac31aa9945", "prevouts": ["3f93e1050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "c4cd6f050000000017a914d005833d09f3ca8722c64ddbdda5b936d94f704f87"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_9", "success": {"scriptSig": "", "witness": ["9b9d2f890c36b4e80a22984887b1cc79aa99dc941c9145a1ca93765914af1718", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "5005503799719e6c4f8d"]}, "failure": {"scriptSig": "", "witness": ["87220e70c5db87d90efffc123226d00c3e607f47f3a1d7f9252f97103d144073", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "5005503799719e6c4f8d"]}}, {"tx": "3ada98b403b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d712202000000ca1042dc02c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf498b01000000b61f72ba636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b4001000000ae1da98101370c3d080000000016001486053ceaa6b6ea601bdda3b6220dc7510448595824020000", "prevouts": ["3c01f805000000002251208aa1b928071fdb3aa32fd8f2c9eb36c278e237c81ad0b54da1e3dc20b2bf63e1", "f725fb050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "35df9f040000000022512023e79411159902f985de82643864e65e64a47b20a7346a34ebb9ab35dc637af5"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_none_3", "final": true, "success": {"scriptSig": "", "witness": ["7d9e6854d4b98fcbc55f71ed9670497c0d4cf1714672d9e715dcf8ff9a0310d3", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["726cabf5f680cb85d2ce506407c5e01e19528379d012881ba14711f4bc7d4b5c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b71000000004168d0b2b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7166010000004fc5fee0024e69430a000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd24302c6000000", "prevouts": ["e2222305000000002251204af5a8d65c66d384812c4ba198602c1e347ea7791f0ce288b422d8726f35cef5", "596a22050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_184", "final": true, "success": {"scriptSig": "", "witness": ["46f1dd0b08d2e86939038753beff4a39c909b46889cc4ee8f7193338a098cc16", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["a216f5faa696926f9728d81ebedde32012fb83d8f70cac6feb9fa83c1aa49eff027fea7f05b815ff28d69ff87ae0b46551e7d0c32ceae81b18418abda9fd6160993dadffe26fdab1b13c1cd4ce39576d2e4f223afc860a6aa4e7fe39c468c47a4128b0329f53479ecad71b2f3d68a257ea60a7ac970d4b01b4e1ff61fe2d24a8e806a019b79458fdcfb1f33c07d8e176ca2c53d2d76ef5f22f90dbfc1d703c52afec5319730e0a741613e92756301ba231b0629d7127ac48", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "02000000016a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d39f0000000040a6a5f4023b505405000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac13080000", "prevouts": ["d1e255050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_14", "final": true, "success": {"scriptSig": "", "witness": ["a9624e3dfdc3fbc0ad3b24d23539fb70d72c34e3533458f1386b5f2c13104a23", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["f02b6e5ceb6adb963e543740bab9", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5beb0100000086a05b2902c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf49c00000000044e985e9032223ad0a000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac5802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e25cc2f55", "prevouts": ["085bcd050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "cb80e2040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_16", "success": {"scriptSig": "", "witness": ["2e80ae8f11a82f104d957aed0a389fd7dc472cddbe8258917ff5738e70fe991d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50464abcf58d002500622138ac2911d10f"]}, "failure": {"scriptSig": "", "witness": ["7deca85e7e182a6502bcc1159ac07756c37bfe80f37b30ef4cbdd9f7c97897d0", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50464abcf58d002500622138ac2911d10f"]}}, {"tx": "0200000003df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cd5010000000f7fd4efdf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cf701000000c7dfadb06a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d361010000005db718ae043786f30f000000001600145e89b76f270f5a3384e042389be8f4c10402492658020000000000001600145e89b76f270f5a3384e042389be8f4c10402492658020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec2087bcdac143", "prevouts": ["28518e050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "332dd9050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "fb918d0400000000225120444577651e37fdb7a210d2cde3a2cade95ffda3c149246dba0d617bb4880d3ba"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_122", "final": true, "success": {"scriptSig": "", "witness": ["7aab29e35806e3fe0f8bc82f8a3f51468e527337bcd3e22ab59ebd5743707b17", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["b5072c2ab45b94694baa1722cef79b4608c97f464e6110e6f1967777447753a61fb4448a5d00b51755aa95f2c26d37586e73fa1076bfa012817b6ecd62deaa5139fe4171754b7e902b835a967c8b0b88c722e7c949e7898aa64d6bf6c199fefe267862a14d43d8a7ac7257520f4e23faf1456876c5a0a0aad95e", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "e881333f02df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c0c0100000075cc4ad002c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf493601000000fbb012ef0185d7e6080000000017a91460db42f735e17b0d826006ad8d411b7445b1ec2087ca88cb47", "prevouts": ["29ddff05000000002251204441836ee1e1c83240e5b0e9af5caa9b8c274259c10b5494a10dd2f3fadfba29", "aa7370050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_202", "final": true, "success": {"scriptSig": "", "witness": ["c845ccca89224dff3bcca232313c3baa8162bc4fb162b6627b496b7d02ecfad3", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["12d0759133b91435415029762063e99039af4089299596d53e7098856672b49a835a3dc3ce7a536db2b4d00e18f2241e55f1cac0bf31feab077c7e11bff24ad467bebf3a3d303871d4abb96601c41bae421448ec40e9cc3c5c13e999256ce8e79ae417914361483911528dc0f53ae50a18bc741a5a135a722a26e08292aace2cbdf324a47c30367012adbd233dc17356e16abd8530bfd78e3750c92b95eedb58fa7b53ff17530b99ea9b38cda076606852d03755c9dfe78408c1d2e225901426624e7b712cca109f9647", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "020000000202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf496102000000c73ab6bf6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3450000000091a2c5d904a22e4e0b00000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac58020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88acbb020000", "prevouts": ["30f73e050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "c13f12060000000022512016419205b4c696a5dbb724624e42c25f49dd7de83fd616bddae2dc9c34c91fc0"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_161", "final": true, "success": {"scriptSig": "", "witness": ["70cd374546cf519f917937419362caad736611bc42a33be040ff8f600fc5f809", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["6e440bb84048999723ea4523079888e0cda2593b49b5f3be9e003719ec7fc153807e5b49c0c2df11ed19964d2fb18d54e316fc47d0993755c49026271067e5f1d5b94377e0bfc8ba2efec1c5e31f283fed1ff6808f928b6c4e8980aacec63c4107a9ead6c3ff40e11e3df3d11e8d16284b3b962169af0f5daaa4d4c9737d4813a08b7da1d455da7beae98873f901bd9b0366ff354fbea817747a337f561f34be55", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c15010000000f12c903636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b6d01000000fd89479d02aa86950b000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a3387690c0000", "prevouts": ["e687ca050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "cec5cd050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_1", "success": {"scriptSig": "", "witness": ["ff9dbb56ef53ba2216921a2dd3f35594688cfec41f60d1bb777f65f73199eff6", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "5091"]}, "failure": {"scriptSig": "", "witness": ["739669e26fa669de11ce8287035c2ecacbb90a4fdaac374e154c7823680de2bc", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "5091"]}}, {"tx": "0100000003df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c37020000002eb9422602c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf490d0000000083879f67df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c4d01000000dce7cbac04ab7d720f00000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd2430237070000", "prevouts": ["ac32b1040000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "a546f0050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "36f1d2040000000017a914e3d068e25a4057bb0963b5808ba5ecd2ffa3c44f87"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_21", "final": true, "success": {"scriptSig": "", "witness": ["d7a7dfedf266e2e2c86d7836c84807875005e7125590374ce628b05bb9265eaf", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["3fefb535d46d7baf682fb5e910677735ec346e6b51", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "872af75b02b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d712002000000affd929802c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf491501000000204866e502f4998309000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac3d080000", "prevouts": ["b3a893040000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "3a2ff2040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_140", "final": true, "success": {"scriptSig": "", "witness": ["b88f6b6b612886b19db0bc4e302aacdcea2a134225c317c1c2b37c237e52da30", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["1fce879dc7ee7cebac6c6d92ec386220d632f235b9fce4251b446532394d52c6bf5093a632aba52c882342430f1254146b0edb1a2be317e0ce019fd637af72901fbfbe2e25dc1d522b67ffbdbf03a0ac0b2a4cb327e9de6b026ddbe00bcc90df84cd228736c2a13291807907195dd5e624f19eba0d8e4ec33fbc64e5d8dd84cd04ef8d6298a75814ea432167", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000003636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b15020000007a2edabddf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c080200000023a0f7aa636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b0802000000ad7662ef0144fe8c0a0000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338789a9bb28", "prevouts": ["96b5ac04000000002251201d06129f09c7aa4a4a55408ff2475680cdce0d6db2cd5e55ece26df1cb43dadb", "ae73ed050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "93f0a00500000000225120e372be687b6d745c76d126c977ec4e32f9f61b9f678b873ce4d2a154eeb8524e"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_8", "success": {"scriptSig": "", "witness": ["6b425768da8eeb2581aeaef321d0d114b006b8684cda8629e85424a9f7e6a577", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "501a1e42c52282480a"]}, "failure": {"scriptSig": "", "witness": ["1d7b939427df05ff6f5d6c47e4889462bb2f57ec62bd0a1718eb639832bbbbf3", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "501a1e42c52282480a"]}}, {"tx": "02000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d32a0200000015bd029a6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3f6010000001f34abda037fccdb0a000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac5802000000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92edfe17345", "prevouts": ["f7b4ec040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "75e5f00500000000225120298972734e68cccaabbc4fce3a790eb7d4a6ec05a497b5f4abfa76a3ba310eee"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_59", "final": true, "success": {"scriptSig": "", "witness": ["1b30f0d0831297968b2d39f45f2a24d8552c628283c35609c0d2ee97283e04b3", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["b22db6205d97fe9d9d29c3b439f106c22886e8695fffd95726d15e38affd9b7f1f5f162029999ddb3fe56ce38d7281ef71051ee2def098a0a73796", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c160000000009ea1ea86a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3f701000000a54a8cd9047453c80a000000001600145e89b76f270f5a3384e042389be8f4c10402492658020000000000001976a914e32b67d481533f90793c78e8bc61c031e12e339f88ac580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a3387580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb874a060000", "prevouts": ["310b7b050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "33db4e05000000002251205a737f8fbfd304390e3758884cf1b13006675a4b94e013e215517e38e26275c4"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_143", "final": true, "success": {"scriptSig": "", "witness": ["0acb6bf91880f7126e936ee6eb0ef59fb832cac53df09b599993cce9d0b63b29", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["45ed4cf6e5c351384bc0b6f449ffa24efcceec5bc3bb7c68bbc50a4378b5c65d8ffa920d500a3689e279499f28c2276802b702cb94d223c588273de0cd936a7a7d22fa4691f1e16958889e5f101aed181667c1ca30c3fcffc7db444baa4303200a715babc8b30da0fffbef702fa40028a1ab253705aa332889b733a6ab413f8e135a1223ffc7eab6f9c312bfa36df8", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000001636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b0601000000cc45602404b9e2ce0400000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac580200000000000016001486053ceaa6b6ea601bdda3b6220dc7510448595874859462", "prevouts": ["c378d0040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_165", "final": true, "success": {"scriptSig": "", "witness": ["7c051f97f9027b74548ad18c6a24f7bcf98ecbe5e7818711fcbfc0f184d7cc16", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["e70f855bb66ffb922d5c3ba1eda084c399b25f67b04a257f7a842f89cb2a1982e5d1f9fb036e845c85764e3f30364f79e6902df6c75f23d279f0e48d5820124440411c3404cb49733296696b8ed1c7726275e88ca44090295535aac4aa53a27e42eb86df8ec1dad04a15d118cd8fb9711803fabaab6b2a9628f49e8af192651fda31937de2e25cc7851aec6e9fe2c9554f6c8ee03ecdfb77f37fb5b599b929cc7587572bbe", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "01000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d38c000000002e02db78df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cc401000000f3fa0ab0044e40d70b000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac580200000000000016001486053ceaa6b6ea601bdda3b6220dc7510448595858020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac4f060000", "prevouts": ["9bbbd40500000000225120888234ca5411be779d2dee188f05cb1257ce2abcd752b2365d5c0bc78310a8c6", "8c0f05060000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_63", "final": true, "success": {"scriptSig": "", "witness": ["3611349fcaa1a490ab04a9743d1b82e5c0ca952991be4a81b3109cee1dafbadc", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["1a95116cc60b99082c565b6616e4a24021fd3d520769af44cde39516b59b7284dfbdcb944b1e135530c87eaa208b9cef5936f8c6cc2926bced925d7fc49b7c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000003636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b890100000059347e1202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf491b0200000058f7a638636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b04000000002b7caaa101a5cdeb04000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac0a02143c", "prevouts": ["d7c8d0040000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "637574050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "331b36050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_12", "success": {"scriptSig": "", "witness": ["5703a144a43009225b6a4536e33755a3f6bcf4abf8ebafc9e4bb289751bf3c4f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50fd03489f92a247da293948bb"]}, "failure": {"scriptSig": "", "witness": ["48fc3e8ea48a409533d84133e797c51f522c9380d238324622637861bf0cb869", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50fd03489f92a247da293948bb"]}}, {"tx": "0100000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c4a000000006ffb65e3636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bc30100000081e10a8702307f090b0000000016001486053ceaa6b6ea601bdda3b6220dc7510448595858020000000000001600145e89b76f270f5a3384e042389be8f4c104024926ca23ee48", "prevouts": ["c46497050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "9bfb74050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_24", "final": true, "success": {"scriptSig": "", "witness": ["e4bf35d32a8c5e4542b170cd442b86713aaa6097d0b01c5c560701a9048bf4db", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["a97fc3dcc380df42e24e88c8182df7b542a4e1da8967ee1f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000001b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71ab01000000422d052b0330b4e604000000001600140276cd59f2bc98ad777ccf7057f574395bd2430258020000000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988ac58020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88acce494347", "prevouts": ["ea10e9040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_192", "final": true, "success": {"scriptSig": "", "witness": ["6e99e24e55d7915991bae6508851a109c67c228684b5cccc6972de630bf2ff61", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["ad741773a091f382584ccc7b92ff88eb4e60c40186577e4539a1e12e43615c74bcb9c68f877376999eae2f1f4700c36cfc194441e159b2cedbb824c44139f086e827fa21b9ae3eb3d69a26f491b2495b7ba28ce07f76fa6491222a6d9e1e5f759ce7fca7ff3a690c68baed77ce13e43c4f850fbb8325d5bf818321fce637ede6ab6a52e75065abd11582d708a66978592ae62c850a462801c9009ee1fb8a91e4f9d7b244eae70f92dfe3febee316e97e2a481d9adfe3eb5e85e1de5c05e72820", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000003636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bbe010000006dcec48b6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3f2010000002f979df4636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b550200000057d91ed00108b2c50c0000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208706080000", "prevouts": ["4d9ea0040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "c15b3c050000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "a93e29050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_mismatch_1", "success": {"scriptSig": "", "witness": ["2ba3f319f3655233b438cd7392163905baeb6a92f0c8d052b91efb69f25f178e", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "5014"]}, "failure": {"scriptSig": "", "witness": ["9115a9d2b572f97fa467088ac64e50549cee9008d0a8acb5875bce54213cc630", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "5014"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d716a01000000252602dedf41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5ce2010000009b6a76fa032d87d20a000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac58020000000000001976a914dfb830a3ca5c6a5d975d009188cc47acd2581ff888ac5802000000000000160014c327e70d62d692d5959c72b3411fee2ca31c546b97bcc023", "prevouts": ["4af032060000000022512063182a74dd4ddac17f6e9f8dc644ca00f7fd5eb312ce9861aeef9559e7ec3d3c", "94a8a1040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_186", "final": true, "success": {"scriptSig": "", "witness": ["418d222b92fa0f24434d0866c18c7dea782e38c2053f3d281ea48fbd18051e3f", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["afbc7a38c13eeac2074abdf6caa5dab320e20ebadea2b70d28ce4cd2dc1f3b06507e09bc1e39539783f21f1b4f1073e9c78421274cc10fcea9a7a5298a1bfee0e7d118926985255b5c208c9b511bfd4b935594e658176ab627f27bb51652696f1829239663e6467bc0b9e39a53212baeb16d1022f13c7be7a14100d15a17896db91ac5ea34730662a86b1b4965747146af0201acc9d75cce0826db2e0e1918917e5f8f0de94265d68e47cdb1bfdc92398a84ff6b32597f229dae", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c200000000054f65ff7df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cba0000000032155e9d0181d32806000000001976a91463b0567d7e3116c9a021cf3a865f69939447181988acab22da65", "prevouts": ["78b8230600000000225120f429379794d9addc587a2a1fe5311faf96ad71c55796a74e587fce7f17630cae", "e4f30f050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_141", "final": true, "success": {"scriptSig": "", "witness": ["05a9fa3f085e70dcfbe01cd1c16a1b3e94495f13273bc327b7808c6db09cbbaa", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["c0b281d0ebab94f968ea4dcdecd85652f5e8a82fbd3aee067ad17f8547593548754ee40b4f89c44621850a929b7d9076e329ba4859272caa79ba9b290d263e83dac19e81e992e4f7023a60b349bf59d1edc748afe4f59fc62b67346ccd70abfb600cad4cb3620b4e3af197460d9b96ff2b8fc1c9bd6b8ebc05f41c4922366467c453fe663c63c35912d7dfdbc5", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0100000002636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5bb30000000070847bd66a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3210200000063c07c6703d0a7010a000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88acdd050000", "prevouts": ["25ba33050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "9d7ad00400000000225120198323e493a016f9cc2cb3a1e7cb72209c9dd89ab18a96456d1f3c2981298183"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_119", "final": true, "success": {"scriptSig": "", "witness": ["583780a0c36b5e8a0dcdff06a566d7b924ff354e9a37f8e8c50c58f4f88ec660", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["9fdccb0bcb523e52280179c7a8d771b0eb0282e7bb570063af5a80df4ce935140346bced835dd5d7d8558d1f574aa791f38bf91bfad1e4038954d36592f522b35c2cae9eab221ee125587f03e7408952deed05c9a8c5ed9a14c23b5fbb5ffbe44101a0fe4867f08dab8e4f42ae7f8c546cc31ad594b255", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "02000000036a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d32e010000003a1140d402c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf493902000000ed9678c16a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d341010000005a7208cb036560eb0f000000001600145e89b76f270f5a3384e042389be8f4c104024926580200000000000017a9144657010e5cf55af6acb627784c227caeaa0f0a338758020000000000001976a914312123c9167690e4c172a7c502a42e5ffa3e442a88ac19030000", "prevouts": ["e884af040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "528a5a05000000002251205f359b0c56fb94cc824c7891579f1c80f5cfbafb82628b3b456b347920082c7c", "c89ce3050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 2, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_8", "final": true, "success": {"scriptSig": "", "witness": ["c7996a372ebb7c1f8b06d26240340fcc9138ac65fbaf2ff034a6a183b8c3c61d", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["b1d80fab76f7dc3b", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "61da43790202c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf4959020000000dbaf6d1df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c5300000000a81bfc9c01af304601000000001600145e89b76f270f5a3384e042389be8f4c1040249263b86a22b", "prevouts": ["672cbd050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "53ed7405000000002251201281bf2ff5cf94b38a0ae6a5cf9fca373380dcc91f581c346912d8c70d94f563"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_215", "final": true, "success": {"scriptSig": "", "witness": ["bc39196e5d60f6e6c6a341d73ac2a1aa8095a1d3218f7c43d0fb8c08c1f4ddc0", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["d85a8ce41ad839a3629369eb822eb77d1b73d1c1f27d507b62f7938e4ab43013feff3f38906072222e4896d81a33faa71b26b9ddaa431dcbb31845e2d40ef8cacf7cc5a9794ec8ef50edc5895f87696ecfe818997ac9d39f5c99d010f4c6a734283c966d4d24bc3718184e898f3511f4072ad41a82ba98d8e0fa040ab6878ecde179858de9cb91a301037b2143c65382ebd4448c50d8a4692f229c2905cbf9b67d21d2faea688362fa2985428e13c23181185b4f9ae8c681aa026b9100123cde3e8ef6019f96b938f79ca4121c447d970044ced986833c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "645d664e03b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d71b300000000f5adf28a6a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d35f0100000048ab9ab3df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cca000000009e575b8903d851611000000000160014f1fb0f9ee9e43f501bc49cffc693566e082cc92e58020000000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208785030000", "prevouts": ["b694c4040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "ccb90506000000002251200be538ebf2ba640046dfb17a21757a6cf07353700b054b36d166606227015f8a", "b8a69805000000002251205b8b48b429d3707df5bcc86dfde72372228bad9ebf329df0c01d544f1b4c05f2"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_145", "final": true, "success": {"scriptSig": "", "witness": ["c08cde509f4ebc8601e7a24c6738a0570221acf4ac1c6ecae5643e55d81af29e", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["993f44d87c0a6b94217aa7382b147b0c44315ac21ac97a0b44099e71ee8988560f8b537df4efcf7dfd913bfc32432e054421411cffed76dda867dd2a37e3cd658674cf3c6f14153f2eadb079d8501e06dd93e6567fd6263f00b02e5c83741b811e666ef62d40df07d46c52eb8414769bc0062a7b51ee4a119c9e9ff531e8e2448f901cfee4c1524bbf2725727cb8424c37", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "02000000016a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d3b101000000028d7ae301ca403500000000001600140276cd59f2bc98ad777ccf7057f574395bd243021067d136", "prevouts": ["c8f900050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_195", "final": true, "success": {"scriptSig": "", "witness": ["8ea2c3770fbd9b8f8ff21b7f14c7bcbc7d6aa29726119ce4f8197b2cd1249e55", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["25f7fba6295b3218dacc12caecd0b35cebc698658a88a426bc0dd98aa69956b19d412f0eccc251d48fcd2d8144a743a2ec5a4d0a7137db28cbac1825fd9174cdd18e4fe7775431ab207614663250d1f0bae7ed0d8a97c0b1be4955fc0e0e9a4fb22dc1a959ce81d45c80df34ddf4242e707710e165ccce6ead7a4bc5566d853b2f3dd4dcd035d56e003e3da8f1bc5201525f771d91e662ce56a571c9742db6a9feaea5d8ed50a8988e4036f26943e14a6ba6758385fc36330ce0326888e72b466221a4", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000001636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b740100000094c980900490736c05000000001976a9141c428f4958c47293549411153bb54f9c0588618f88ac580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208758020000000000001600145e89b76f270f5a3384e042389be8f4c104024926580200000000000016001486053ceaa6b6ea601bdda3b6220dc7510448595816281327", "prevouts": ["9abe6e050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_108", "final": true, "success": {"scriptSig": "", "witness": ["5ac2894fb7269b80ecb1fca98f19998439052b196fc749a1029b6feff8a46ea7", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["d29b6d6c9eb08eed56ade8d9afd2c456d147930d338a4549008fd3fb20ec843b0249f43e5b33520c37ec8eaf4122bdff58359c9be6b70f4fc6be42f41e654c15b453ad2ded8f5d52a386de7c88c55c2503dd1585dbefe06f037a2c0dfc7ba4adbef717d78c111bf4d0863a8a", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "0200000002b8ca91eb06a85214e394064042aebd3a8d7c36ce7f008fdaa2b4344e62b74d7166020000002e0a01f702c7e23a6bc0121956038a43e8df3dcaca3dcf8cd2cd25e0633540f2430baf498800000000bc6fb2d901a75afc060000000017a91460db42f735e17b0d826006ad8d411b7445b1ec2087ac69b04d", "prevouts": ["d791bb04000000002251204af5a8d65c66d384812c4ba198602c1e347ea7791f0ce288b422d8726f35cef5", "5115d5050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_15", "success": {"scriptSig": "", "witness": ["e2c6ecf112c7a6b258f176b32b6a101e772f036fbb34137f3e5594de1e1e2dae", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50bfc70d177963277a72d456b9c05db3"]}, "failure": {"scriptSig": "", "witness": ["c176cb8e286d4c89994a9817a26fa843b36bc91660a56d6dc8913c5ef1963ed9", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50bfc70d177963277a72d456b9c05db3"]}}, {"tx": "02000000026a90b71c8b3bf5f7faa17eeba3401b96ee1192a1b8f7bb9c95343937989c47d35201000000a35f25a0df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c4501000000707713a80407dbaf0a000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac58020000000000001976a9144881e6a73d711dfaa9dea76995d65ebdfe993c6388ac58020000000000001600140276cd59f2bc98ad777ccf7057f574395bd2430258020000000000001600140276cd59f2bc98ad777ccf7057f574395bd2430292a3e451", "prevouts": ["2e51e5050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007", "c8ffcc040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_annex_30", "success": {"scriptSig": "", "witness": ["aafa2d67509600f02d3e34fe4f31621545ccaef5b3cbec67a7241d053c3121e1", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50627fd3854c76cae7e13deea3bc714d4dcdb444e8246238b3d6809010fd2f"]}, "failure": {"scriptSig": "", "witness": ["01eb6807b9ad275917a2085772d93d0792a13d16534bc2a1a5d731241cca0bbb", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c", "50627fd3854c76cae7e13deea3bc714d4dcdb444e8246238b3d6809010fd2f"]}}, {"tx": "0100000002df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5cd900000000184c5017636c1166381dc81c3e560c5b7a625df0b9e305d287be5710b07f5ad82eab9b5b4c02000000e82099be031417450a00000000160014c327e70d62d692d5959c72b3411fee2ca31c546b58020000000000001976a914a1a1d26776c8f13790d26e4e1d0c3bca51e3652b88ac580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb87e94b6b47", "prevouts": ["74ac90050000000022512001999c48bcbcdf26630cb8b21c8208fbedc2afd1fb521d8b7153d3acdd9b1a4a", "e29bb6040000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 1, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_25", "final": true, "success": {"scriptSig": "", "witness": ["c362388a87f54469b7bc6b81ff2fc4fc92d0c2d0a48fce7e2c291cc11ad9fa3c", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["a7a4c45e0e2d35817de4af0258f21234a98ab5c127eb4c54fb", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, {"tx": "b2407f6101df41dbb76806968f252eb113c3f2edf4a9c64e31940fa608d727bf59724cbf5c5d01000000781c81a004f849f105000000001976a914921dd2c9e5574e2bf4a174b4f19dde711f6a3e7c88ac580200000000000017a914d0ea02ec79b2617113bea67956d4b03ec7ebf6eb87580200000000000017a91460db42f735e17b0d826006ad8d411b7445b1ec208758020000000000001600140276cd59f2bc98ad777ccf7057f574395bd24302418ac739", "prevouts": ["016af3050000000022512048b7a6ac553c6670309ce08661031cc64428fe65160b3057548f11264425b007"], "index": 0, "flags": "P2SH,DERSIG,CHECKLOCKTIMEVERIFY,CHECKSEQUENCEVERIFY,WITNESS,NULLDUMMY,TAPROOT,TEMPLATEHASH", "comment": "template/equality_rand_97", "final": true, "success": {"scriptSig": "", "witness": ["afbaba6a45b44fe381ac2c4cadec08f7fa8723af756f17c0b8231a8a02f45692", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}, "failure": {"scriptSig": "", "witness": ["ecaf67fd79155ff9c23f56261be38447d72fefcd540311cb015a20a8ecbf1273e0111bed16bd1c8f3ecaf3f30cc1a3fa81e8c3f4652d2ce7536c40c4a7c6854aa21a9b32714d75a51502f2208b346013e49b683ceaab16df45a9742804d37bff11", "ce87", "c01cc2a102f97fbec67ac9043aa12935ae2d5c3c6c0739d485c982475198b6ebd3c2111f03b04a063283ddcfd09b3dc59b4fd028c08e61ae7e8af0c14d483812a1ed77f77bc36becf797fa61b620c613639d739fd8dba5397a565b93ce6c70f0c188656b571841de54427958afea74a63afa549fe057dbcc086c8200d5278a201c"]}}, ] ================================================ FILE: bip-0446.md ================================================ ``` BIP: 446 Layer: Consensus (soft fork) Title: OP_TEMPLATEHASH Authors: Gregory Sanders Antoine Poinsot Steven Roose Status: Draft Type: Specification Assigned: 2026-02-06 License: CC0-1.0 ``` ## Abstract This document proposes a new operation for [Tapscript][tapscript-bip]: `OP_TEMPLATEHASH`. It introduces the ability to push on the stack a hash of the transaction spending an output. ## Motivation `OP_TEMPLATEHASH` can be used to commit to the transaction spending an output[^commit-exact-tx]. This capability can replace the use of pre-signed transactions in second-layer protocols. By reducing interactivity it makes such protocols simpler, safer, and sometimes notably more efficient. For instance it can remove the need to share HTLC signatures in the Lightning Network protocol's [`commitment_signed` message][ln-commit-signed][^ln-second-stage], make receiving an Ark "VTXO" [non-interactive][ark-case-ctv], and [reduces roundtrips][symmetric-greg] in the implementation of LN-Symmetry. It is also a [significant optimisation][fournier-ctv-dlcs] for [Discreet Log Contracts][optech-dlcs]. ## Specification `OP_TEMPLATEHASH` redefines `OP_SUCCESS206` (0xce) in the Tapscript execution context with further restrictions. Upon execution of the opcode, the template hash of the transaction in context is pushed onto the stack as defined below, and script execution continues. The template hash uses a tagged hash as introduced by [BIP340][schnorr-bip] and [BIP341][taproot-bip]. We use a new tag for this purpose: *TemplateHash*. The template hash re-uses the *sha_sequences*, *sha_outputs* and *sha_annex* pre-computed transaction data introduced in BIP341. Numerical values in 4-byte are encoded in little-endian. The template hash is the *hashTemplateHash* of the following transaction fields concatenated: - Transaction data: - *nVersion* (4): the version of the transaction. - *nLockTime* (4): the locktime of the transaction. - *sha_sequences* (32): the SHA256 of the serialization of all input sequence, as per BIP341. - *sha_outputs* (32): the SHA256 of the serialization of all outputs in `CTxOut` format, as per BIP341. - Data about this input: - *annex_present* (1): as defined in BIP341 (0 if no annex is present, or 1 otherwise). - *input_index* (4): index of this input in the transaction input vector. Index of the first input is 0. - If an annex is present: - *sha_annex* (32): the SHA256 of the annex, as per BIP341. ## Rationale The template hash follows BIP341's signature message format, with minimal necessary deviations. This reuses a tried-and-proven approach to hashed messages, and importantly makes it possible to reuse the pre-computed subfields introduced by BIP341 to prevent quadratic hashing. Besides the hash tags, this results in at most 109 bytes being hashed upon execution of the operation[^hashed-msg-max-size]. This is strictly less hashing than is necessary for other existing operations. The specific fields from the BIP341 signature message that are ommitted when computing the template hash are the following: - *hash_type*: refers to the sighash type identifier in the context of BIP341 signatures. The input for `OP_TEMPLATEHASH` is fixed, so there is no need for a mechanism to modify the hash composition. - *spend_type*: this value is defined by BIP341 as *2\*ext_flag + annex_present*. Since no extension is appended to the signature message, *ext_flag* is set to 0. Therefore we commit directly to *annex_present*. - *sha_prevouts* / *sha_scriptpubkeys*: committing to these fields as is would introduce a hash cycle when the hash is committed in the output itself. Committing to all other prevouts or scriptpubkeys would introduce hashing a quantity of data quadratic in the number of inputs. It would also prevent spending two coins encumbered by a template hash check in the same transaction. Finally, the flexibility of not committing to the specific coins spent is also desirable to recover from mistakes[^no-commit-other-coins]. - *sha_amounts*: the BIP341 rationale for committing to the amounts of all spent coins is to be able to prove to an offline signer the fees of a transaction. Although `OP_TEMPLATEHASH` can be used as a building block for rebindable signatures, the utility of committing to spent amounts but not spent scriptpubkeys [is limited][greg-attack-input-ownership]. Still for rebindable signatures, committing to spent amounts can be justified as defense-in-depth against implementation mistakes[^commit-spent-amounts]. However, the lack of flexibility this introduces also makes it harder to recover from a mistake in committing to the next transaction[^no-commit-other-coins]. Furthermore, committing to all spent amounts also makes overcommitting funds to such a script result in the output being forever unspendable instead of the excess just going to fees at spend time. The design of `OP_TEMPLATEHASH` was inspired by the design of [BIP119][ctv-bip] `OP_CHECKTEMPLATEVERIFY` but differs in several important ways. First of all, `OP_TEMPLATEHASH` is only defined for Tapscript, as modifying legacy Script comes with an unnecessarily increased risk surface. In addition, sticking to Tapscript allows leveraging more powerful upgrade hooks (`OP_SUCCESS`s instead of `OP_NOP`s) which make it possible to push the template hash on the stack instead of being constrained to strict assertions with no stack modification. Pushing the template hash on the stack substantially improves the efficiency of using `OP_TEMPLATEHASH` as a building block for rebindable signatures. Unlike `OP_TEMPLATEHASH`, `OP_CHECKTEMPLATEVERIFY` also commits to the scriptSig of all inputs of the spending transaction. `OP_CHECKTEMPLATEVERIFY` gives txid stability when the committed spending transaction has a single input, and when the scriptSig of this single input has been committed by the hash. Taproot scriptSigs must be empty and therefore under the single input case `OP_TEMPLATEHASH` has no requirement to commit to scriptSigs to achieve txid stability. Finally, BIP119 `OP_CHECKTEMPLATEVERIFY` does not commit to the Taproot annex (or its absence). `OP_TEMPLATEHASH` does. Deviating from other operations which do commit to the annex would be unnecessary and surprising. Committing to the annex also makes usage of `OP_TEMPLATEHASH` forward compatible with potential future meaning that it could be given. Not committing to it would also prevent using `OP_TEMPLATEHASH` in conjunction with annex-based proof of publication techniques unless additional signatures are included, as used for instance [in the LN-Symmetry demo][symmetry-annex-publication]. Programmable transaction introspection capabilities have been proposed as an alternative to a primitive which only allows committing to the exact next transaction. It remains to be shown that these more flexible capabilities do enable important use cases which justify each proposed change's specific semantics and implementation complexity. It has been suggested that the new primitive should have its own upgrade hook from which to softfork in additional consensus meaning for more flexible introspection at some future point. We have not done so due to the fact that Taproot and Tapscript already presents plentiful upgrade hooks for the future. ## Backward compatibility This document proposes to give meaning to a Tapscript `OP_SUCCESS` operation. The presence of an `OP_SUCCESS` in a Tapscript would previously make it unconditionally succeed. This proposal therefore only tightens the block validation rules: there is no block that is valid under the rules proposed in this BIP but not under the existing Bitcoin consensus rules. As a consequence these changes are backward-compatible with non-upgraded node software. That said, the authors strongly encourage node operators to upgrade in order to fully validate all consensus rules. ## Implementation * https://github.com/instagibbs/bitcoin/tree/2025-07-op_templatehash ## Test Vectors For development and testing purposes, we provide a [collection of test vectors](bip-0446/). The test vectors are separated into two JSON files. The [first one](bip-0446/basics.json) is a short list of simple test cases exercising the various fields of a transaction committed to when using `OP_TEMPLATEHASH`. The [second one](bip-0446/script_assets_test.json) is a more exhaustive suite of tests exercising `OP_TEMPLATEHASH` under a large number of different conditions. It reuses the [Bitcoin Core Taproot test framework][feature_taproot.py] introduced with the implementation of BIP341. Format details and usage demonstration are available [here](bip-0446/README.md). ## Acknowledgements Credit to Jeremy Rubin for his leadership and perseverance in defending how a simple primitive which allows committing to the entire spending transaction is useful for reducing interactivity in second layer protocols. This BIP draws on the design of BIP119 and is heavily inspired by his exploration of the potential uses for such a primitive. ## Copyright This document is licensed under the Creative Commons CC0 1.0 Universal license. [^ln-second-stage]: Second-stage HTLC transactions are currently enforced through a 2-of-2 multisig between the channel partners. Committing to the HTLC transaction directly in the commitment transaction's HTLC output is a drop-in replacement for the multisig, which has the advantage of not requiring Lightning nodes to transmit and store signatures for every HTLC at every state it is still active for. [^commit-exact-tx]: All the transaction's fields are committed to except the inputs' prevout. This means the output must be spent by this exact transaction, although the other spent outputs may vary. [^no-commit-other-coins]: It is possible to commit to an underfunded transaction to spend a coin. If the transaction commits to more than one input, it is possible to recover from the mistake by creating a separate coin of an appropriate value and spending it along with the encumbered coin. Committing to other inputs this transaction must spend or their input removes the ability to recover from such a mistake. [^commit-spent-amounts]: Adding commitments to the spent amounts may offer extra protection when reusing a public key previously associate with a rebindable signature. See [BIP118's rationale][apo-bip-spent-amounts] for more about this. [^hashed-msg-max-size]: If no annex is committed, 77 bytes are hashed: 72 bytes of transaction data + 5 bytes of data about this input. Committing to an annex adds 32 additional bytes of data about this input, bringing the total to 109. [schnorr-bip]: bip-0340.mediawiki [taproot-bip]: bip-0341.mediawiki [tapscript-bip]: bip-0342.mediawiki [ctv-bip]: bip-0119.mediawiki [apo-bip-spent-amounts]: https://github.com/bitcoin/bips/blob/master/bip-0118.mediawiki#cite_note-3 [ark-case-ctv]: https://delvingbitcoin.org/t/the-ark-case-for-ctv/1528 [symmetric-greg]: https://delvingbitcoin.org/t/ln-symmetry-project-recap/359 [greg-attack-input-ownership]: https://gnusha.org/pi/bitcoindev/CAB3F3Dv1kuJdu8veNUHa4b58TvWy=BT6zfxdhqEPBQ8rjDfWtA@mail.gmail.com [symmetry-annex-publication]: https://github.com/instagibbs/bolts/blob/eltoo_draft/XX-eltoo-transactions.md#update-transaction [ln-commit-signed]: https://github.com/lightning/bolts/blob/master/02-peer-protocol.md#committing-updates-so-far-commitment_signed [fournier-ctv-dlcs]: https://gnusha.org/pi/bitcoindev/CAH5Bsr2vxL3FWXnJTszMQj83jTVdRvvuVpimEfY7JpFCyP1AZA@mail.gmail.com [optech-dlcs]: https://bitcoinops.org/en/topics/discreet-log-contracts [feature_taproot.py]: https://github.com/bitcoin/bitcoin/blob/v29.0/test/functional/feature_taproot.py ================================================ FILE: bip-0448.md ================================================ ``` BIP: 448 Layer: Consensus (soft fork) Title: Taproot-native (Re)bindable Transactions Authors: Gregory Sanders Antoine Poinsot Steven Roose Status: Draft Type: Specification Assigned: 2026-03-11 License: CC0-1.0 ``` ## Abstract This document proposes deploying three new operations for [Tapscript][tapscript-bip]: [BIP 446 `OP_TEMPLATEHASH`][templatehash-bip], [BIP 348 `OP_CHECKSIGFROMSTACK`][csfs-bip], and [BIP 349 `OP_INTERNALKEY`][internalkey-bip]. These minimal operations introduce modular functionalities which improve existing second layer protocols and make new ones possible through plausible interactivity requirements. ## Motivation The three proposed operations are simple, well-understood, and enable powerful new capabilities while minimizing the risk of surprising behavior or unintended applications. They improve existing, well-studied protocols and make promising new ones possible. `OP_TEMPLATEHASH` allows a Tapscript to commit to the exact transaction that must spend it. This capability is a common building block for second-layer protocols that is emulated today by requiring a signature from all involved parties. Using `OP_TEMPLATEHASH` instead reduces interactivity, making such protocols simpler, safer, and sometimes significantly more efficient. `OP_CHECKSIGFROMSTACK` introduces [BIP 340][schnorr-bip] signature verification for arbitrary messages, which enables delegation and oracle attestations. Together, these features enable rebindable transaction signatures, making possible a new type of payment channel: [LN-Symmetry ("Eltoo")][optech-eltoo]. Its simplicity makes advanced constructs like multiparty channels practical, enables simplifications for 2-party channels such as [Daric][daric-channels], and can substantially improve [statechains][statechains-optech]. Rebindable signatures also enable further interactivity reduction in second layer protocols, as illustrated by the Ark variant "[Erk][ark-erk]" or the [dramatic simplification][greg-rebindable-ptlcs] they bring to upgrading today's Lightning to [Point Time Locked Contracts][optech-ptlcs]. `OP_INTERNALKEY` allows to push the [Taproot][taproot-bip] internal key on the stack. This is a natural and extremely simple optimisation for rebindable signatures. ## Specification In [BIP 342 Tapscript](bip-0342.mediawiki), the following operations are updated. `OP_TEMPLATEHASH` redefines `OP_SUCCESS206` (0xce) as per the specification of [BIP 446][templatehash-bip]. `OP_CHECKSIGFROMSTACK` redefines `OP_SUCCESS204` (0xcc) as per the specification of [BIP 348][csfs-bip]. `OP_INTERNALKEY` redefines `OP_SUCCESS203` (0xcb) as per the specification of [BIP 349][internalkey-bip]. ### Deployment The specific activation is left to be determined at a later date. ## Rationale This proposal seeks to extend Bitcoin's scripting capabilities in areas that are useful to proven approaches to scaling Bitcoin payments. The operations proposed to achieve these capabilities are contained within the more modern and well-studied Tapscript context. They are simple, composable and unlikely to be made obsolete by future extensions to Bitcoin Script. They build upon existing operations and therefore present a minimal cost to validation and implementation complexity. More modular operations (such as [BIP 346][txhash-bip]) also enable these capabilities, and more. However they come with an increased risk surface, notably in terms of implementation complexity. As the additional capabilities have not been demonstrated to enable new important use cases or substantially improve existing ones beyond this proposal, we favour the minimal approach. An alternative to [BIP 446 `OP_TEMPLATEHASH`][templatehash-bip] is [BIP 119 `OP_CHECKTEMPLATEVERIFY`][ctv-bip]. This proposal favours the minimal approach of [BIP 446 `OP_TEMPLATEHASH`][templatehash-bip] that does not modify legacy scripting contexts and reuses the existing Taproot signature hashes. See [the rationale section of BIP 446][templatehash-rationale] for more details. ## Backward compatibility This document proposes to give meaning to three Tapscript `OP_SUCCESS` operations. The presence of an `OP_SUCCESS` in a Tapscript would previously make it unconditionally succeed. This proposal therefore only tightens the block validation rules: there is no block that is valid under the rules proposed in this BIP but not under the existing Bitcoin consensus rules. As a consequence these changes are backward-compatible with non-upgraded node software. That said, the authors strongly encourage node operators to upgrade in order to fully validate all consensus rules. ## Acknowledgements This proposal is similar to the combination of opcodes Brandon Black previously [proposed](https://delvingbitcoin.org/t/lnhance-bips-and-implementation/376) for activation under the name "LNHANCE". ## Copyright This document is licensed under the Creative Commons CC0 1.0 Universal license. [templatehash-bip]: bip-0446.md [templatehash-rationale]: bip-0446.md#rationale [ctv-bip]: bip-0119.mediawiki [csfs-bip]: bip-0348.md [internalkey-bip]: bip-0349.md [schnorr-bip]: bip-0340.mediawiki [taproot-bip]: bip-0341.mediawiki [tapscript-bip]: bip-0342.mediawiki [optech-eltoo]: https://bitcoinops.org/en/topics/eltoo [optech-ptlcs]: https://bitcoinops.org/en/topics/ptlc [txhash-bip]: bip-0346.md [ark-erk]: https://delvingbitcoin.org/t/evolving-the-ark-protocol-using-ctv-and-csfs/1602 [greg-rebindable-ptlcs]: https://gist.github.com/instagibbs/1d02d0251640c250ceea1c66665ec163 [daric-channels]: https://eprint.iacr.org/2022/1295 [statechains-optech]: https://bitcoinops.org/en/topics/statechains/ ================================================ FILE: scripts/buildtable.pl ================================================ #!/usr/bin/perl use strict; use warnings; my $topbip = 9999; my $include_layer = 1; my %RequiredFields = ( BIP => undef, Title => undef, Authors => undef, Status => undef, Type => undef, Assigned => undef, # License => undef, (has exceptions) ); my %MayHaveMulti = ( Authors => undef, Deputies => undef, 'Comments-URI' => undef, License => undef, 'License-Code' => undef, 'Discussion' => undef, ); my %DateField = ( Assigned => undef, ); my %EmailField = ( Authors => undef, Editor => undef, Deputies => undef, ); my %MiscField = ( 'Deputies' => undef, 'Comments-URI' => undef, 'Comments-Summary' => undef, 'Discussion' => undef, 'Replaces' => undef, 'Requires' => undef, 'Proposed-Replacement' => undef, ); my %VersionField = ( 'Version' => undef, ); my @FieldOrder = qw( BIP Layer Title Author Authors Editor Deputies Discussions-To Comments-Summary Comments-URI Status Type Assigned License License-Code Discussion Post-History Version Requires Replaces Proposed-Replacement Superseded-By ); my %ValidLayer = ( 'Consensus (soft fork)' => undef, 'Consensus (hard fork)' => undef, 'Peer Services' => undef, 'API/RPC' => undef, 'Applications' => undef, ); my %ValidStatus = ( Draft => undef, Complete => "background-color: #ffffcf", Deployed => "background-color: #cfffcf", Closed => "background-color: #ffcfcf", ); my %ValidType = ( 'Specification' => undef, 'Informational' => undef, 'Process' => undef, ); my %AcceptableLicenses = ( 'BSD-2-Clause' => undef, 'BSD-3-Clause' => undef, 'CC0-1.0' => undef, 'FSFAP' => undef, 'MIT' => undef, 'CC-BY-4.0' => undef, 'Apache-2.0' => undef, 'BSL-1.0' => undef, ); my %DefinedLicenses = ( %AcceptableLicenses, 'CC-BY-SA-4.0' => undef, 'AGPL-3.0' => undef, 'AGPL-3.0+' => undef, 'FDL-1.3' => undef, 'GPL-2.0' => undef, 'GPL-2.0+' => undef, 'LGPL-2.1' => undef, 'LGPL-2.1+' => undef, 'OPUBL-1.0' => undef, # There's no identifier for "Public Domain" in the SPDX list but "PD" is used in some BIPs. 'PD' => undef, ); my %GrandfatheredPD = map { $_ => undef } qw(9 36 37 38 42 49 50 60 65 67 69 74 80 81 83 90 99 105 107 109 111 112 113 114 122 124 125 126 130 131 132 133 140 141 142 143 144 146 147 150 151 152); my %GrandfatheredCCBySA = map { $_ => undef } qw(98 116 117 134); my %TolerateMissingLicense = map { $_ => undef } qw(1 10 11 12 13 14 15 16 21 31 33 34 35 39 43 44 45 47 61 64 68 70 71 72 73 101 102 106 120 121 134); my %TolerateTitleTooLong = map { $_ => undef } qw(39 44 45 47 49 60 67 68 69 73 74 75 80 81 99 105 106 109 113 122 126 131 143 145 147 173 327); my %emails; my $bipnum = 0; while (++$bipnum <= $topbip) { my $fn = sprintf "bip-%04d.mediawiki", $bipnum; my $is_markdown = 0; if (!-e $fn) { $fn = sprintf "bip-%04d.md", $bipnum; $is_markdown = 1; } -e $fn || next; open my $F, "<$fn"; if ($is_markdown) { while (<$F> !~ m[^(?:\xef\xbb\xbf)?```$]) { die "No ``` in $fn" if eof $F; } } else { while (<$F> !~ m[^(?:\xef\xbb\xbf)?
$]) {
			die "No 
 in $fn" if eof $F;
		}
	}
	my %found;
	my ($title, $authors, $status, $type, $layer);
	my ($field, $val, @field_order, $continuation);
	while (<$F>) {
		last if ($is_markdown && m[^```$]);
		last if (!$is_markdown && m[^
$]); if (m[^ ([\w-]+)\: (.*\S)$]) { $field = $1; $val = $2; $continuation = 0; die "Duplicate $field field in $fn" if exists $found{$field}; die "Too many spaces in $fn" if $val =~ /^\s/; } elsif (m[^ ( +)(.*\S)$]) { die "Continuation of non-field in $fn" unless defined $field; die "Too many spaces in $fn" if length $1 != 2 + length $field; die "Not allowed for multi-value in $fn" unless exists $MayHaveMulti{$field}; $val = $2; $continuation = 1; } else { die "Bad line in $fn preamble"; } die "Extra spaces in $fn" if $val =~ /^\s/; if ($field eq 'BIP') { die "$fn claims to be BIP $val" if $val ne $bipnum; } elsif ($field eq 'Title') { $title = $val; my $title_len = length($title); die "$fn has too-long Title ($title_len > 50 char max)" if $title_len > 50 and not exists $TolerateTitleTooLong{$bipnum}; } elsif ($field eq 'Authors') { $val =~ m/^(\S[^<@>]*\S) \<([^@>]*\@[\w.-]+\.\w+)\>$/ or die "Malformed Authors line in $fn"; my ($authorname, $authoremail) = ($1, $2); $authoremail =~ s/(?<=\D)$bipnum(?=\D)//g; $emails{$authorname}->{$authoremail} = undef; if (defined $authors) { $authors .= ", $authorname"; } else { $authors = $authorname; } } elsif ($field eq 'Status') { if ($bipnum == 38) { # HACK $val =~ s/\s+\(.*\)$//; } die "Invalid status in $fn" unless exists $ValidStatus{$val}; $status = $val; } elsif ($field eq 'Type') { die "Invalid type in $fn" unless exists $ValidType{$val}; if (defined $ValidType{$val}) { $type = $ValidType{$val}; } else { $type = $val; } } elsif ($field eq 'Layer') { # BIP 123 die "Invalid layer $val in $fn" unless exists $ValidLayer{$val}; $layer = $val; } elsif ($field =~ /^License(?:\-Code)?$/) { die "License continued across lines in $fn, use SPDX expression (... OR $val) instead" if $continuation; $val =~ s/ OR .*//; die "Undefined license $val in $fn" unless exists $DefinedLicenses{$val}; if (not $found{$field}) { die "Unacceptable license $val in $fn" unless exists $AcceptableLicenses{$val} or ($val eq 'PD' and exists $GrandfatheredPD{$bipnum}) or ($val eq 'CC-BY-SA-4.0' and exists $GrandfatheredCCBySA{$bipnum}); } } elsif ($field eq 'Comments-URI') { if ($found{'Comments-URI'}) { my $first_comments_uri = sprintf('https://github.com/bitcoin/bips/wiki/Comments:BIP-%04d', $bipnum); die "First Comments-URI must be exactly \"$first_comments_uri\" in $fn" unless $val eq $first_comments_uri; } } elsif (exists $DateField{$field}) { # Enforce date format 20XX-MM-DD, where XX is 00-99, MM is 01-12 and DD is 01-31 die "Invalid date format in $fn" unless $val =~ /^20\d{2}\-(?:0[1-9]|1[0-2])\-(?:0[1-9]|[12]\d|30|31)$/; } elsif (exists $EmailField{$field}) { $val =~ m/^(\S[^<@>]*\S) \<[^@>]*\@[\w.]+\.\w+\>$/ or die "Malformed $field line in $fn"; } elsif (exists $VersionField{$field}) { $val =~ m/^(\d+\.\d+\.\d+)$/ or die "Malformed $field line in $fn"; } elsif (not exists $MiscField{$field}) { die "Unknown field $field in $fn"; } ++$found{$field}; push @field_order, $field unless @field_order and $field_order[-1] eq $field; } if (not $found{License}) { die "Missing License in $fn" unless exists $TolerateMissingLicense{$bipnum}; } for my $field (keys %RequiredFields) { die "Missing $field in $fn" unless $found{$field}; } my @expected_field_order = grep { exists $found{$_} } @FieldOrder; if ("@expected_field_order" ne "@field_order") { die "Field order is incorrect in $fn, should be:\n\t" . join(", ", @expected_field_order) . "\nbut contains:\n\t" . join(", ", @field_order); } print "|-"; if (defined $ValidStatus{$status}) { print " style=\"" . $ValidStatus{$status} . "\""; } print "\n"; print "| [[${fn}|${bipnum}]]\n"; if ($include_layer) { if (defined $layer) { print "| ${layer}\n"; } else { print "|\n"; } } print "| ${title}\n"; print "| ${authors}\n"; print "| ${type}\n"; print "| ${status}\n"; close $F; } for my $authors (sort keys %emails) { my @emails = sort keys %{$emails{$authors}}; my $email_count = @emails; next unless $email_count > 1; warn "NOTE: $authors has $email_count email addresses: @emails\n"; } ================================================ FILE: scripts/diffcheck.expected ================================================ < |- < | 40 < | API/RPC < | Stratum wire protocol < | Marek Palatinus < | Standard < | BIP number allocated < |- < | 41 < | API/RPC < | Stratum mining protocol < | Marek Palatinus < | Standard < | BIP number allocated < |- < | 63 < | Applications < | Stealth Addresses < | Peter Todd < | Standard < | BIP number allocated < | Leon Olsson Curr, Pearlwort Sneed, Andrew Poelstra > | Leon Olsson Curr and Pearlwort Sneed, Andrew Poelstra < |} ================================================ FILE: scripts/diffcheck.sh ================================================ #!/bin/bash scripts/buildtable.pl >/tmp/table.mediawiki 2> /dev/null diff README.mediawiki /tmp/table.mediawiki | grep '^[<>] |' >/tmp/after.diff || true newdiff=$(diff -s scripts/diffcheck.expected /tmp/after.diff -u | grep '^[-+]') if [ -n "$newdiff" ]; then echo "$newdiff" exit 1 fi echo "README table matches expected table from BIP files" ================================================ FILE: scripts/link-format-chk.sh ================================================ #!/usr/bin/env bash # # Copyright (c) 2019 The Bitcoin Core developers # Distributed under the MIT software license, see the accompanying # file COPYING or http://www.opensource.org/licenses/mit-license.php. # # Check wrong mediawiki link format ECODE=0 for fname in *.mediawiki; do GRES=$(grep -n '](http' "$fname") if [ "$GRES" != "" ]; then if [ $ECODE -eq 0 ]; then >&2 echo "Github Mediawiki format writes link as [URL text], not as [text](url):" fi ECODE=1 echo "- $fname:$GRES" fi done exit $ECODE