Browse Source

df: finalize redeemscript at the same time as witness stack

libwally has a quirk where the finalize method will fail to 'completely'
finalize an input's parts if either the final_scriptsig or
final_redeemscript fields are set

since we manually set the final_witness stack here, we also need to
fully finalize the redeemscript -> final_scriptsig here as well.
travis-experimental
niftynei 4 years ago
committed by Rusty Russell
parent
commit
fe56f572ed
  1. 2
      channeld/channeld.c
  2. 37
      common/psbt_internal.c
  3. 10
      common/psbt_internal.h

2
channeld/channeld.c

@ -2134,7 +2134,7 @@ static void handle_tx_sigs(struct peer *peer, const u8 *msg)
elem = cast_const2(const struct witness_element **, elem = cast_const2(const struct witness_element **,
ws[j++]->witness_element); ws[j++]->witness_element);
psbt_input_set_final_witness_stack(peer->psbt, in, elem); psbt_finalize_input(peer->psbt, in, elem);
} }
/* Send to the peer controller, who will broadcast the funding_tx /* Send to the peer controller, who will broadcast the funding_tx

37
common/psbt_internal.c

@ -1,12 +1,15 @@
#include "common/psbt_internal.h" #include "common/psbt_internal.h"
#include <bitcoin/script.h>
#include <ccan/ccan/tal/tal.h>
#include <common/psbt_open.h> #include <common/psbt_open.h>
#include <wally_psbt.h> #include <wally_psbt.h>
#include <wire/peer_wire.h> #include <wire/peer_wire.h>
#if EXPERIMENTAL_FEATURES #if EXPERIMENTAL_FEATURES
void psbt_input_set_final_witness_stack(const tal_t *ctx, static void
struct wally_psbt_input *in, psbt_input_set_final_witness_stack(const tal_t *ctx,
const struct witness_element **elements) struct wally_psbt_input *in,
const struct witness_element **elements)
{ {
tal_wally_start(); tal_wally_start();
wally_tx_witness_stack_init_alloc(tal_count(elements), wally_tx_witness_stack_init_alloc(tal_count(elements),
@ -19,6 +22,34 @@ void psbt_input_set_final_witness_stack(const tal_t *ctx,
tal_wally_end(ctx); tal_wally_end(ctx);
} }
void psbt_finalize_input(const tal_t *ctx,
struct wally_psbt_input *in,
const struct witness_element **elements)
{
psbt_input_set_final_witness_stack(ctx, in, elements);
/* There's this horrible edgecase where we set the final_witnesses
* directly onto the PSBT, but the input is a P2SH-wrapped input
* (which has redeemscripts that belong in the scriptsig). Because
* of how the internal libwally stuff works calling 'finalize'
* on these just .. ignores it!? Murder. Anyway, here we do a final
* scriptsig check -- if there's a redeemscript field still around we
* just go ahead and mush it into the final_scriptsig field. */
if (in->redeem_script) {
u8 *redeemscript = tal_dup_arr(NULL, u8,
in->redeem_script,
in->redeem_script_len, 0);
in->final_scriptsig =
bitcoin_scriptsig_redeem(NULL,
take(redeemscript));
in->final_scriptsig_len =
tal_bytelen(in->final_scriptsig);
in->redeem_script = tal_free(in->redeem_script);
in->redeem_script_len = 0;
}
}
const struct witness_stack ** const struct witness_stack **
psbt_to_witness_stacks(const tal_t *ctx, psbt_to_witness_stacks(const tal_t *ctx,
const struct wally_psbt *psbt, const struct wally_psbt *psbt,

10
common/psbt_internal.h

@ -12,15 +12,17 @@ struct witness_element;
#endif /* EXPERIMENTAL_FEATURES */ #endif /* EXPERIMENTAL_FEATURES */
#if EXPERIMENTAL_FEATURES #if EXPERIMENTAL_FEATURES
/* psbt_input_set_final_witness_stack - Set the witness stack for PSBT input /* psbt_finalize_input - Finalize an input with a given witness stack
* *
* Sets the given witness elements onto the PSBT. Also finalizes
* the redeem_script, if any.
* @ctx - the context to allocate onto * @ctx - the context to allocate onto
* @in - input to set final_witness for * @in - input to set final_witness for
* @witness_element - elements to add to witness stack * @witness_element - elements to add to witness stack
*/ */
void psbt_input_set_final_witness_stack(const tal_t *ctx, void psbt_finalize_input(const tal_t *ctx,
struct wally_psbt_input *in, struct wally_psbt_input *in,
const struct witness_element **elements); const struct witness_element **elements);
/* psbt_to_witness_stacks - Take all sigs on a PSBT and copy to a /* psbt_to_witness_stacks - Take all sigs on a PSBT and copy to a
* witness_stack * witness_stack
* *

Loading…
Cancel
Save