| Commit message (Collapse) | Author | Age | Files | Lines |
| |
|
|
|
|
|
| |
still accepted); silent-payment leftovers removed
Co-Authored-By: Claude Opus 5.5 <[email protected]>
Claude-Session: https://claude.ai/code/session_01YRC6aKhwAud231ot9FPmhi
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Two things:
- Only confirmed SP coins enter the spend pool. Unconfirmed ones are excluded
(the sender's tx could be replaced, invalidating our spend) — matching the
spendable headline, which already counted confirmed-only.
- SP→SP sending: our own silent-payment coins can now fund a payment TO an sp1
address (previously excluded). _applySilentPayments includes SP inputs with
their key d = spend_priv + t_k, and silentPaymentScripts negates a taproot
input's key when it gives odd Y, per BIP-352 (so the sender's A = a·G matches
what the indexer reconstructs). signing was already SP-aware.
Validated: BIP-352 sending vectors pass for all clean key-path-taproot-input
cases (the remaining vector failures are NUMS script-path / labels / uncompressed
keys — input types the wallet never spends). End-to-end on regtest: an SP coin
funds a payment to another sp address, testmempoolaccept passes, and the recipient
scans and finds it.
Note: silentPaymentScripts derives input_hash from the eligible inputs it's given,
which is correct because the wallet only ever spends all-eligible coins (P2WPKH +
key-path SP); it isn't a general-purpose sender for txs with ineligible inputs.
Co-Authored-By: Claude Opus 4.8 (1M context) <[email protected]>
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
silentpay.js: silentPaymentCandidate() (our P_0 for a tweak) + buildBloom/bloomHas
(double-hashed sha256, ~0.8% FP). Validated: candidate == P_0 on all no-label
vectors.
Indexer /scan now returns, per block, the tweaks + a Bloom over that block's
taproot output keys (no outputs), with an optional dustLimit. The wallet derives
a candidate per tweak, tests the filter, and only fetches /block on a hit — so a
big historical scan costs candidate math + a handful of fetches instead of
downloading and scanning every block. Live WS pushes still carry full items.
SP_DUST_LIMIT defaults to 0 (receive everything; the indexer honors any value).
Verified end-to-end on regtest: the filter flow finds the output.
Co-Authored-By: Claude Opus 4.8 (1M context) <[email protected]>
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
| |
tools/sp-indexer.js: a minimal BIP-352 oracle (Bun) that walks Core and serves,
per block, one entry per eligible tx — the tweak (input_hash*A) plus that tx's
taproot outputs — for the wallet to scan on-device. Shares src/silentpay.js so
the tweak math is the vector-validated code. Added to the regtest compose as the
'sp' service (oven/bun, pointed at bc:18443).
inputPubKey now accepts a witness as either serialized hex (vectors) or an array
of stack items (Core getblock RPC). Verified end-to-end on regtest: a real SP
payment is indexed and the scan recovers the output, value, and spend tweak.
Co-Authored-By: Claude Opus 4.8 (1M context) <[email protected]>
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
silentpay.js gains the receiving half of silent payments, validated against all
official BIP-352 vectors (29/29 receiving sub-cases):
- inputPubKey(): recover the eligible input pubkey from P2PKH/P2WPKH/P2SH-P2WPKH/
P2TR inputs (skips uncompressed keys, excludes NUMS script-path, hash160-matches
malleated P2PKH scriptSigs)
- silentPaymentTweak(): the oracle tweak input_hash*A (sum over eligible inputs,
input hash over all outpoints, point-at-infinity guarded) — used by the indexer
- silentPaymentScan(): ecdh = scan_priv*tweak, derive P_k = B_spend + t_k*G, match
the tx's taproot outputs, return per-output spend tweaks
- silentPaymentOutputPrivKey(), deriveSilentPaymentKeys() (m/352' paths),
encodeSilentPaymentAddress()
Labels not yet implemented (wallet uses a single no-label address).
Co-Authored-By: Claude Opus 4.8 (1M context) <[email protected]>
|
|
|
Pay sp1… addresses: the wallet derives the one-time taproot output from the
recipient's address + the transaction's own input keys (ECDH), so payments are
unlinkable on-chain with no interaction. New src/silentpay.js implements the
sender derivation + bech32m address decode, validated against the official
BIP-352 test vectors (all P2WPKH-input / single-recipient cases pass; the rest
exercise input types Hal never spends).
buildTx detects sp1… recipients, selects coins against a same-size placeholder
taproot output, then swaps in the script derived from the final input set
(updateOutput). Works for normal sends, multi-recipient, and send-max. The
review screen shows the sp1… address with a 'Silent payment' label (the on-chain
output is a derived one-time taproot address). End-to-end signing verified.
Co-Authored-By: Claude Opus 4.8 (1M context) <[email protected]>
|