diff --git a/common/daemon.c b/common/daemon.c index c3adac2a0..651582838 100644 --- a/common/daemon.c +++ b/common/daemon.c @@ -1,5 +1,8 @@ #include "config.h" #include +/*~ This is Ian Lance Taylor's libbacktrace. It turns out that it's + * horrifically difficult to obtain a decent backtrace in C; the standard + * backtrace function is useless in most programs. */ #include #include #include diff --git a/lightningd/lightningd.c b/lightningd/lightningd.c index f5128229c..fda955dfa 100644 --- a/lightningd/lightningd.c +++ b/lightningd/lightningd.c @@ -21,9 +21,8 @@ * before anything else. */ #include "config.h" -/*~ This is Ian Lance Taylor's libbacktrace. It turns out that it's - * horrifically difficult to obtain a decent backtrace in C; the standard - * backtrace function is useless in most programs. */ +/*~ Various bitcoin-related helpers live in the bitcoin/ directory */ +#include /*~ These headers are from CCAN: http://ccodearchive.net. * @@ -56,8 +55,8 @@ #include #include #include -#include +#include #include #include #include @@ -676,7 +675,7 @@ static void init_txfilter(struct wallet *w, struct ext_key ext; /*~ Note the use of ccan/short_types u64 rather than uint64_t. * Thank me later. */ - u64 bip32_max_index; + u64 bip32_max_index, bip86_max_index; bip32_max_index = db_get_intvar(w->db, "bip32_max_index", 0); /*~ One of the C99 things I unequivocally approve: for-loop scope. */ @@ -686,6 +685,17 @@ static void init_txfilter(struct wallet *w, } txfilter_add_derkey(filter, ext.pub_key); } + + /* If BIP86 is enabled, also add BIP86-derived keys to the filter */ + if (w->ld->bip86_base) { + bip86_max_index = db_get_intvar(w->db, "bip86_max_index", 0); + for (u64 i = 0; i <= bip86_max_index + w->keyscan_gap; i++) { + struct pubkey pubkey; + bip86_pubkey(w->ld, &pubkey, i); + u8 *script = scriptpubkey_p2tr(tmpctx, &pubkey); + txfilter_add_scriptpubkey(filter, take(script)); + } + } } /*~ The normal advice for daemons is to move into the root directory, so you diff --git a/lightningd/test/run-find_my_abspath.c b/lightningd/test/run-find_my_abspath.c index 7f15dc1b8..995322590 100644 --- a/lightningd/test/run-find_my_abspath.c +++ b/lightningd/test/run-find_my_abspath.c @@ -227,6 +227,12 @@ struct wallet *wallet_new(struct lightningd *ld UNNEEDED, struct timers *timers /* Generated stub for wallet_sanity_check */ bool wallet_sanity_check(struct wallet *w UNNEEDED) { fprintf(stderr, "wallet_sanity_check called!\n"); abort(); } +/* Generated stub for bip86_pubkey */ +void bip86_pubkey(struct lightningd *ld UNNEEDED, struct pubkey *pubkey UNNEEDED, u32 index UNNEEDED) +{ fprintf(stderr, "bip86_pubkey called!\n"); abort(); } +/* Generated stub for txfilter_add_scriptpubkey */ +void txfilter_add_scriptpubkey(struct txfilter *filter UNNEEDED, const u8 *script TAKES UNNEEDED) +{ fprintf(stderr, "txfilter_add_scriptpubkey called!\n"); abort(); } /* AUTOGENERATED MOCKS END */ struct logger *crashlog; diff --git a/wallet/wallet.c b/wallet/wallet.c index e76192983..0e0d5a032 100644 --- a/wallet/wallet.c +++ b/wallet/wallet.c @@ -148,6 +148,12 @@ static void our_addresses_add_for_index(struct wallet *w, u32 i) /* FIXME: We could deprecate P2SH once we don't see * any, since we stopped publishing them in 24.02 */ if (!wallet_get_addrtype(w, i, &addrtype)) { + if (w->ld->bip86_base) { + /* Derive and add BIP86 script for this index */ + our_addresses_add_bip86_for_index(w, i); + return; + } + const u8 *addr; scriptpubkey = scriptpubkey_p2wpkh_derkey(NULL, ext.pub_key); addr = scriptpubkey_p2sh(NULL, scriptpubkey); @@ -205,7 +211,17 @@ static void our_addresses_init(struct wallet *w) w->our_addresses_maxindex = 0; w->our_addresses = new_htable(w, wallet_address_htable); - our_addresses_add_for_index(w, w->our_addresses_maxindex); + /* If BIP86 is enabled, prefill the address table up to keyscan_gap so + * rescans immediately include BIP86 scripts without needing prior + * address allocations. */ + if (w->ld->bip86_base) { + for (u32 i = 0; i <= w->keyscan_gap; i++) { + our_addresses_add_for_index(w, i); + } + w->our_addresses_maxindex = w->keyscan_gap; + } else { + our_addresses_add_for_index(w, w->our_addresses_maxindex); + } } static void outpointfilters_init(struct wallet *w)