From 14d722d48da1552b4caa2289a33b1beb2efd621f Mon Sep 17 00:00:00 2001 From: Rusty Russell Date: Sun, 24 Apr 2016 19:38:13 +0930 Subject: [PATCH] bitcoind: pretend normalized txids are in the block. This lets us live in a segwit world, before segwit. It's a shim which we can remove once we've changed all our outputs. We need a few more sleeps in our test script, since we've slowed things down by doing these calls for every tx in every block. Signed-off-by: Rusty Russell --- daemon/bitcoind.c | 70 ++++++++++++++++++++++++++++++++++++++++----- daemon/bitcoind.h | 4 ++- daemon/test/test.sh | 4 +-- 3 files changed, 68 insertions(+), 10 deletions(-) diff --git a/daemon/bitcoind.c b/daemon/bitcoind.c index 24472c10c..fdde3f375 100644 --- a/daemon/bitcoind.c +++ b/daemon/bitcoind.c @@ -555,6 +555,39 @@ void bitcoind_get_chaintips_(struct lightningd_state *dstate, "getchaintips", NULL); } +struct normalizing { + u32 mediantime; + struct sha256_double prevblk, blkid; + struct sha256_double *txids; + size_t i; + void (*cb)(struct lightningd_state *dstate, + struct sha256_double *blkid, + struct sha256_double *prevblock, + struct sha256_double *txids, + u32 mediantime, + void *arg); + void *cb_arg; +}; + +/* We append normalized ones, so block contains both. Yuk! */ +static void normalize_txids(struct lightningd_state *dstate, + const struct bitcoin_tx *tx, + struct normalizing *norm) +{ + size_t num = tal_count(norm->txids) / 2; + normalized_txid(tx, &norm->txids[num + norm->i]); + + norm->i++; + if (norm->i == num) { + norm->cb(dstate, &norm->blkid, &norm->prevblk, norm->txids, + norm->mediantime, norm->cb_arg); + tal_free(norm); + return; + } + bitcoind_txid_lookup(dstate, &norm->txids[norm->i], + normalize_txids, norm); +} + static void process_getblock(struct bitcoin_cli *bcli) { const jsmntok_t *tokens, *prevblk_tok, *txs_tok, @@ -564,12 +597,7 @@ static void process_getblock(struct bitcoin_cli *bcli) struct sha256_double *txids; struct sha256_double *prevblk, blkid; size_t i; - void (*cb)(struct lightningd_state *dstate, - struct sha256_double *blkid, - struct sha256_double *prevblock, - struct sha256_double *txids, - u32 mediantime, - void *arg) = bcli->cb; + struct normalizing *norm = tal(bcli->dstate, struct normalizing); log_debug(bcli->dstate->base_log, "Got getblock result"); if (!bcli->output) @@ -665,7 +693,18 @@ static void process_getblock(struct bitcoin_cli *bcli) prevblk_tok ? bcli->output + prevblk_tok->start : NULL, i); - cb(bcli->dstate, &blkid, prevblk, txids, mediantime, bcli->cb_arg); + /* FIXME: After segwitness, all txids will be "normalized" */ + norm->i = 0; + norm->blkid = blkid; + norm->prevblk = *prevblk; + norm->txids = tal_dup_arr(norm, struct sha256_double, txids, + tal_count(txids), tal_count(txids)); + norm->mediantime = mediantime; + norm->cb = bcli->cb; + norm->cb_arg = bcli->cb_arg; + + bitcoind_txid_lookup(bcli->dstate, &norm->txids[0], + normalize_txids, norm); } void bitcoind_getblock_(struct lightningd_state *dstate, @@ -749,6 +788,23 @@ void bitcoind_getblockhash_(struct lightningd_state *dstate, "getblockhash", str, NULL); } +/* FIXME: Seg witness removes need for this! */ +void normalized_txid(const struct bitcoin_tx *tx, struct sha256_double *txid) +{ + size_t i; + struct bitcoin_tx tx_copy = *tx; + struct bitcoin_tx_input input_copy[tx->input_count]; + + /* Copy inputs, but scripts are 0 length. */ + for (i = 0; i < tx_copy.input_count; i++) { + input_copy[i] = tx->input[i]; + input_copy[i].script_length = 0; + } + tx_copy.input = input_copy; + + bitcoin_txid(&tx_copy, txid); +} + /* Make testnet/regtest status matches us. */ void check_bitcoind_config(struct lightningd_state *dstate) { diff --git a/daemon/bitcoind.h b/daemon/bitcoind.h index 467dd50ac..ee8360e72 100644 --- a/daemon/bitcoind.h +++ b/daemon/bitcoind.h @@ -31,7 +31,7 @@ void bitcoind_txid_lookup_(struct lightningd_state *dstate, #define bitcoind_txid_lookup(dstate, txid, cb, arg) \ bitcoind_txid_lookup_((dstate), (txid), \ - typesafe_cb_preargs(struct io_plan *, void *, \ + typesafe_cb_preargs(void, void *, \ (cb), (arg), \ struct lightningd_state *, \ const struct bitcoin_tx *), \ @@ -121,5 +121,7 @@ void bitcoind_getblockhash_(struct lightningd_state *dstate, const struct sha256_double *), \ (arg)) +void normalized_txid(const struct bitcoin_tx *tx, struct sha256_double *txid); + void check_bitcoind_config(struct lightningd_state *dstate); #endif /* LIGHTNING_DAEMON_BITCOIND_H */ diff --git a/daemon/test/test.sh b/daemon/test/test.sh index fd86f4643..9aa38dc12 100755 --- a/daemon/test/test.sh +++ b/daemon/test/test.sh @@ -276,7 +276,7 @@ if [ -n "$TIMEOUT_ANCHOR" ]; then $CLI generate 99 TIME=$(($TIME + 1)) lcli1 dev-mocktime $TIME - sleep 2 + sleep 5 # Considers it all done now. check_no_peers lcli1 @@ -399,7 +399,7 @@ $CLI generate 99 # Make sure they saw it! lcli1 dev-mocktime $(($EXPIRY + 32)) lcli2 dev-mocktime $(($EXPIRY + 32)) -sleep 1 +sleep 5 check_peerstate lcli1 STATE_CLOSE_WAIT_CLOSE check_peerstate lcli2 STATE_CLOSE_WAIT_CLOSE