From 1a3886c1168588a0d97be5e78f291fdd91743f80 Mon Sep 17 00:00:00 2001 From: Rusty Russell Date: Wed, 5 Jun 2019 16:30:02 +0930 Subject: [PATCH] wallet: keep a list of unreleased transactions. We're going to use this in the next patch. Signed-off-by: Rusty Russell --- gossipd/test/run-bench-find_route.c | 3 -- gossipd/test/run-find_route-specific.c | 3 -- gossipd/test/run-find_route.c | 3 -- gossipd/test/run-overlong.c | 3 -- lightningd/lightningd.c | 1 + lightningd/test/run-find_my_abspath.c | 3 ++ wallet/wallet.c | 40 ++++++++++++++++++++++++++ wallet/wallet.h | 27 +++++++++++++++++ 8 files changed, 71 insertions(+), 12 deletions(-) diff --git a/gossipd/test/run-bench-find_route.c b/gossipd/test/run-bench-find_route.c index 343d341de..747e1956e 100644 --- a/gossipd/test/run-bench-find_route.c +++ b/gossipd/test/run-bench-find_route.c @@ -72,9 +72,6 @@ u8 *towire_errorfmt(const tal_t *ctx UNNEEDED, const struct channel_id *channel UNNEEDED, const char *fmt UNNEEDED, ...) { fprintf(stderr, "towire_errorfmt called!\n"); abort(); } -/* Generated stub for towire_gossipd_local_add_channel */ -u8 *towire_gossipd_local_add_channel(const tal_t *ctx UNNEEDED, const struct short_channel_id *short_channel_id UNNEEDED, const struct node_id *remote_node_id UNNEEDED, struct amount_sat satoshis UNNEEDED) -{ fprintf(stderr, "towire_gossipd_local_add_channel called!\n"); abort(); } /* Generated stub for towire_gossip_store_channel_amount */ u8 *towire_gossip_store_channel_amount(const tal_t *ctx UNNEEDED, struct amount_sat satoshis UNNEEDED) { fprintf(stderr, "towire_gossip_store_channel_amount called!\n"); abort(); } diff --git a/gossipd/test/run-find_route-specific.c b/gossipd/test/run-find_route-specific.c index d7ebd84d0..eecdba46b 100644 --- a/gossipd/test/run-find_route-specific.c +++ b/gossipd/test/run-find_route-specific.c @@ -61,9 +61,6 @@ u8 *towire_errorfmt(const tal_t *ctx UNNEEDED, const struct channel_id *channel UNNEEDED, const char *fmt UNNEEDED, ...) { fprintf(stderr, "towire_errorfmt called!\n"); abort(); } -/* Generated stub for towire_gossipd_local_add_channel */ -u8 *towire_gossipd_local_add_channel(const tal_t *ctx UNNEEDED, const struct short_channel_id *short_channel_id UNNEEDED, const struct node_id *remote_node_id UNNEEDED, struct amount_sat satoshis UNNEEDED) -{ fprintf(stderr, "towire_gossipd_local_add_channel called!\n"); abort(); } /* Generated stub for towire_gossip_store_channel_amount */ u8 *towire_gossip_store_channel_amount(const tal_t *ctx UNNEEDED, struct amount_sat satoshis UNNEEDED) { fprintf(stderr, "towire_gossip_store_channel_amount called!\n"); abort(); } diff --git a/gossipd/test/run-find_route.c b/gossipd/test/run-find_route.c index 826a4f6ba..dba033410 100644 --- a/gossipd/test/run-find_route.c +++ b/gossipd/test/run-find_route.c @@ -59,9 +59,6 @@ u8 *towire_errorfmt(const tal_t *ctx UNNEEDED, const struct channel_id *channel UNNEEDED, const char *fmt UNNEEDED, ...) { fprintf(stderr, "towire_errorfmt called!\n"); abort(); } -/* Generated stub for towire_gossipd_local_add_channel */ -u8 *towire_gossipd_local_add_channel(const tal_t *ctx UNNEEDED, const struct short_channel_id *short_channel_id UNNEEDED, const struct node_id *remote_node_id UNNEEDED, struct amount_sat satoshis UNNEEDED) -{ fprintf(stderr, "towire_gossipd_local_add_channel called!\n"); abort(); } /* Generated stub for towire_gossip_store_channel_amount */ u8 *towire_gossip_store_channel_amount(const tal_t *ctx UNNEEDED, struct amount_sat satoshis UNNEEDED) { fprintf(stderr, "towire_gossip_store_channel_amount called!\n"); abort(); } diff --git a/gossipd/test/run-overlong.c b/gossipd/test/run-overlong.c index e8a190f64..eb14b238b 100644 --- a/gossipd/test/run-overlong.c +++ b/gossipd/test/run-overlong.c @@ -59,9 +59,6 @@ u8 *towire_errorfmt(const tal_t *ctx UNNEEDED, const struct channel_id *channel UNNEEDED, const char *fmt UNNEEDED, ...) { fprintf(stderr, "towire_errorfmt called!\n"); abort(); } -/* Generated stub for towire_gossipd_local_add_channel */ -u8 *towire_gossipd_local_add_channel(const tal_t *ctx UNNEEDED, const struct short_channel_id *short_channel_id UNNEEDED, const struct node_id *remote_node_id UNNEEDED, struct amount_sat satoshis UNNEEDED) -{ fprintf(stderr, "towire_gossipd_local_add_channel called!\n"); abort(); } /* Generated stub for towire_gossip_store_channel_amount */ u8 *towire_gossip_store_channel_amount(const tal_t *ctx UNNEEDED, struct amount_sat satoshis UNNEEDED) { fprintf(stderr, "towire_gossip_store_channel_amount called!\n"); abort(); } diff --git a/lightningd/lightningd.c b/lightningd/lightningd.c index 7f3a81731..9f19a4334 100644 --- a/lightningd/lightningd.c +++ b/lightningd/lightningd.c @@ -831,6 +831,7 @@ int main(int argc, char *argv[]) * unreserving UTXOs (see #1737) */ db_begin_transaction(ld->wallet->db); tal_free(ld->jsonrpc); + free_unreleased_txs(ld->wallet); db_commit_transaction(ld->wallet->db); remove(ld->pidfile); diff --git a/lightningd/test/run-find_my_abspath.c b/lightningd/test/run-find_my_abspath.c index 9590aebb8..593d6bc3f 100644 --- a/lightningd/test/run-find_my_abspath.c +++ b/lightningd/test/run-find_my_abspath.c @@ -63,6 +63,9 @@ void fatal(const char *fmt UNNEEDED, ...) /* Generated stub for free_htlcs */ void free_htlcs(struct lightningd *ld UNNEEDED, const struct channel *channel UNNEEDED) { fprintf(stderr, "free_htlcs called!\n"); abort(); } +/* Generated stub for free_unreleased_txs */ +void free_unreleased_txs(struct wallet *w UNNEEDED) +{ fprintf(stderr, "free_unreleased_txs called!\n"); abort(); } /* Generated stub for fromwire_status_fail */ bool fromwire_status_fail(const tal_t *ctx UNNEEDED, const void *p UNNEEDED, enum status_failreason *failreason UNNEEDED, wirestring **desc UNNEEDED) { fprintf(stderr, "fromwire_status_fail called!\n"); abort(); } diff --git a/wallet/wallet.c b/wallet/wallet.c index 738b721d3..d86b8cad7 100644 --- a/wallet/wallet.c +++ b/wallet/wallet.c @@ -52,6 +52,7 @@ struct wallet *wallet_new(struct lightningd *ld, wallet->log = log; wallet->bip32_base = NULL; list_head_init(&wallet->unstored_payments); + list_head_init(&wallet->unreleased_txs); db_begin_transaction(wallet->db); wallet->invoices = invoices_new(wallet, wallet->db, log, timers); @@ -2699,3 +2700,42 @@ const struct forwarding *wallet_forwarded_payments_get(struct wallet *w, return results; } + +struct unreleased_tx *find_unreleased_tx(struct wallet *w, + const struct bitcoin_txid *txid) +{ + struct unreleased_tx *utx; + + list_for_each(&w->unreleased_txs, utx, list) { + if (bitcoin_txid_eq(txid, &utx->txid)) + return utx; + } + return NULL; +} + +static void destroy_unreleased_tx(struct unreleased_tx *utx) +{ + list_del(&utx->list); +} + +void remove_unreleased_tx(struct unreleased_tx *utx) +{ + tal_del_destructor(utx, destroy_unreleased_tx); + list_del(&utx->list); +} + +void add_unreleased_tx(struct wallet *w, struct unreleased_tx *utx) +{ + list_add_tail(&w->unreleased_txs, &utx->list); + tal_add_destructor(utx, destroy_unreleased_tx); +} + +/* These will touch the db, so need to be explicitly freed. */ +void free_unreleased_txs(struct wallet *w) +{ + struct unreleased_tx *utx; + + while ((utx = list_top(&w->unreleased_txs, struct unreleased_tx, list))) + tal_free(utx); +} + diff --git a/wallet/wallet.h b/wallet/wallet.h index af2301df4..06eedf46f 100644 --- a/wallet/wallet.h +++ b/wallet/wallet.h @@ -45,6 +45,24 @@ struct wallet { /* Filter matching all outpoints that might be a funding transaction on * the blockchain. This is currently all P2WSH outputs */ struct outpointfilter *utxoset_outpoints; + + /* Unreleased txs, waiting for txdiscard/txsend */ + struct list_head unreleased_txs; +}; + +/* A transaction we've txprepared, but haven't signed and released yet */ +struct unreleased_tx { + /* In wallet->unreleased_txs */ + struct list_node list; + /* All the utxos. */ + struct wallet_tx *wtx; + /* Scriptpubkey this pays to. */ + const u8 *destination; + /* The tx itself (unsigned initially) */ + struct bitcoin_tx *tx; + struct bitcoin_txid txid; + /* Index of change output, or -1 if none. */ + int change_outnum; }; /* Possible states for tracked outputs in the database. Not sure yet @@ -1080,4 +1098,13 @@ const struct forwarding *wallet_forwarded_payments_get(struct wallet *w, bool wallet_remote_ann_sigs_load(const tal_t *ctx, struct wallet *w, u64 id, secp256k1_ecdsa_signature **remote_ann_node_sig, secp256k1_ecdsa_signature **remote_ann_bitcoin_sig); + +/* Operations for unreleased transactions */ +struct unreleased_tx *find_unreleased_tx(struct wallet *w, + const struct bitcoin_txid *txid); +void remove_unreleased_tx(struct unreleased_tx *utx); +void add_unreleased_tx(struct wallet *w, struct unreleased_tx *utx); + +/* These will touch the db, so need to be explicitly freed. */ +void free_unreleased_txs(struct wallet *w); #endif /* LIGHTNING_WALLET_WALLET_H */