diff --git a/bitcoin/psbt.c b/bitcoin/psbt.c index 383f51f4f..e17237ae5 100644 --- a/bitcoin/psbt.c +++ b/bitcoin/psbt.c @@ -340,6 +340,38 @@ struct amount_sat psbt_input_get_amount(struct wally_psbt *psbt, return val; } +struct wally_tx *psbt_finalize(struct wally_psbt *psbt, bool finalize_in_place) +{ + struct wally_psbt *tmppsbt; + struct wally_tx *wtx; + + /* We want the 'finalized' tx since that includes any signature + * data, not the global tx. But 'finalizing' a tx destroys some fields + * so we 'clone' it first and then finalize it */ + if (!finalize_in_place) { + if (wally_psbt_clone(psbt, &tmppsbt) != WALLY_OK) + return NULL; + } else + tmppsbt = cast_const(struct wally_psbt *, psbt); + + if (wally_finalize_psbt(tmppsbt) != WALLY_OK) { + if (!finalize_in_place) + wally_psbt_free(tmppsbt); + return NULL; + } + + if (psbt_is_finalized(tmppsbt) + && wally_extract_psbt(tmppsbt, &wtx) == WALLY_OK) { + if (!finalize_in_place) + wally_psbt_free(tmppsbt); + return wtx; + } + + if (!finalize_in_place) + wally_psbt_free(tmppsbt); + return NULL; +} + bool psbt_from_b64(const char *b64str, struct wally_psbt **psbt) { int wally_err; diff --git a/bitcoin/psbt.h b/bitcoin/psbt.h index 8a483d682..68d718f96 100644 --- a/bitcoin/psbt.h +++ b/bitcoin/psbt.h @@ -32,6 +32,8 @@ struct wally_psbt *new_psbt(const tal_t *ctx, */ bool psbt_is_finalized(struct wally_psbt *psbt); +struct wally_tx *psbt_finalize(struct wally_psbt *psbt, bool finalize_in_place); + struct wally_psbt_input *psbt_add_input(struct wally_psbt *psbt, struct wally_tx_input *input, size_t insert_at); diff --git a/bitcoin/tx.c b/bitcoin/tx.c index d7e839417..50f224a41 100644 --- a/bitcoin/tx.c +++ b/bitcoin/tx.c @@ -501,38 +501,18 @@ char *bitcoin_tx_to_psbt_base64(const tal_t *ctx, struct bitcoin_tx *tx) struct bitcoin_tx *bitcoin_tx_with_psbt(const tal_t *ctx, struct wally_psbt *psbt STEALS) { - struct wally_psbt *tmppsbt; struct bitcoin_tx *tx = bitcoin_tx(ctx, chainparams, psbt->tx->num_inputs, psbt->tx->num_outputs, psbt->tx->locktime); wally_tx_free(tx->wtx); - - /* We want the 'finalized' tx since that includes any signature - * data, not the global tx. But 'finalizing' a tx destroys some fields - * so we 'clone' it first and then finalize it */ - if (wally_psbt_clone(psbt, &tmppsbt) != WALLY_OK) + tx->wtx = psbt_finalize(psbt, false); + if (!tx->wtx && wally_tx_clone(psbt->tx, &tx->wtx) != WALLY_OK) return NULL; - if (wally_finalize_psbt(tmppsbt) != WALLY_OK) { - wally_psbt_free(tmppsbt); - return NULL; - } - - if (psbt_is_finalized(tmppsbt)) { - if (wally_extract_psbt(tmppsbt, &tx->wtx) != WALLY_OK) { - wally_psbt_free(tmppsbt); - return NULL; - } - } else if (wally_tx_clone(psbt->tx, &tx->wtx) != WALLY_OK) { - wally_psbt_free(tmppsbt); - return NULL; - } - - wally_psbt_free(tmppsbt); - tal_free(tx->psbt); tx->psbt = tal_steal(tx, psbt); + return tx; }