From 4b22760cf91b90cd9a14c7999d2d339e68b1bd1b Mon Sep 17 00:00:00 2001 From: Christian Decker Date: Tue, 17 Apr 2018 15:31:30 +0200 Subject: [PATCH] onchaind: Replay stored channeltxs to restore onchaind state Signed-off-by: Christian Decker --- lightningd/lightningd.c | 4 +++ lightningd/onchain_control.c | 45 +++++++++++++++++++++++++++++- lightningd/onchain_control.h | 4 +++ lightningd/test/run-find_my_path.c | 3 ++ 4 files changed, 55 insertions(+), 1 deletion(-) diff --git a/lightningd/lightningd.c b/lightningd/lightningd.c index c05a66c1b..104a63a36 100644 --- a/lightningd/lightningd.c +++ b/lightningd/lightningd.c @@ -30,6 +30,7 @@ #include #include #include +#include #include #include #include @@ -369,6 +370,9 @@ int main(int argc, char *argv[]) ld->config.poll_time, first_blocknum); + /* Replay transactions for all running onchainds */ + onchaind_replay_channels(ld); + /* Create RPC socket (if any) */ setup_jsonrpc(ld, ld->rpc_filename); diff --git a/lightningd/onchain_control.c b/lightningd/onchain_control.c index 40b383cec..52ad3f4eb 100644 --- a/lightningd/onchain_control.c +++ b/lightningd/onchain_control.c @@ -3,7 +3,6 @@ #include #include #include -#include #include #include #include @@ -469,3 +468,47 @@ enum watch_result onchaind_funding_spent(struct channel *channel, /* We keep watching until peer finally deleted, for reorgs. */ return KEEP_WATCHING; } + +void onchaind_replay_channels(struct lightningd *ld) +{ + u32 *onchaind_ids; + struct channeltx *txs; + struct channel *chan; + + db_begin_transaction(ld->wallet->db); + onchaind_ids = wallet_onchaind_channels(ld->wallet, ld); + + for (size_t i = 0; i < tal_count(onchaind_ids); i++) { + log_info(ld->log, "Restarting onchaind for channel %d", + onchaind_ids[i]); + + txs = wallet_channeltxs_get(ld->wallet, onchaind_ids, + onchaind_ids[i]); + chan = channel_by_dbid(ld, onchaind_ids[i]); + + for (size_t j = 0; j < tal_count(txs); j++) { + if (txs[j].type == WIRE_ONCHAIN_INIT) { + onchaind_funding_spent(chan, txs[j].tx, + txs[j].blockheight); + + } else if (txs[j].type == WIRE_ONCHAIN_SPENT) { + onchain_txo_spent(chan, txs[j].tx, + txs[j].input_num, + txs[j].blockheight); + + } else if (txs[j].type == WIRE_ONCHAIN_DEPTH) { + onchain_tx_depth(chan, &txs[j].txid, + txs[j].depth); + + } else { + fatal("unknown message of type %d during " + "onchaind replay", + txs[j].type); + } + } + tal_free(txs); + } + tal_free(onchaind_ids); + + db_commit_transaction(ld->wallet->db); +} diff --git a/lightningd/onchain_control.h b/lightningd/onchain_control.h index b7366ec5a..7ecfdf8a2 100644 --- a/lightningd/onchain_control.h +++ b/lightningd/onchain_control.h @@ -2,6 +2,8 @@ #define LIGHTNING_LIGHTNINGD_ONCHAIN_CONTROL_H #include "config.h" #include +#include +#include struct channel; struct bitcoin_tx; @@ -11,4 +13,6 @@ enum watch_result onchaind_funding_spent(struct channel *channel, const struct bitcoin_tx *tx, u32 blockheight); +void onchaind_replay_channels(struct lightningd *ld); + #endif /* LIGHTNING_LIGHTNINGD_ONCHAIN_CONTROL_H */ diff --git a/lightningd/test/run-find_my_path.c b/lightningd/test/run-find_my_path.c index 498a7aa54..0be2ab349 100644 --- a/lightningd/test/run-find_my_path.c +++ b/lightningd/test/run-find_my_path.c @@ -74,6 +74,9 @@ struct log_book *new_log_book(size_t max_mem UNNEEDED, /* Generated stub for new_topology */ struct chain_topology *new_topology(struct lightningd *ld UNNEEDED, struct log *log UNNEEDED) { fprintf(stderr, "new_topology called!\n"); abort(); } +/* Generated stub for onchaind_replay_channels */ +void onchaind_replay_channels(struct lightningd *ld UNNEEDED) +{ fprintf(stderr, "onchaind_replay_channels called!\n"); abort(); } /* Generated stub for register_opts */ void register_opts(struct lightningd *ld UNNEEDED) { fprintf(stderr, "register_opts called!\n"); abort(); }