@@ -662,16 +662,38 @@ pub fn make_funding_redeemscript(broadcaster: &PublicKey, countersignatory: &Pub
662
662
/// commitment transaction).
663
663
pub fn build_htlc_transaction ( commitment_txid : & Txid , feerate_per_kw : u32 , contest_delay : u16 , htlc : & HTLCOutputInCommitment , opt_anchors : bool , use_non_zero_fee_anchors : bool , broadcaster_delayed_payment_key : & PublicKey , revocation_key : & PublicKey ) -> Transaction {
664
664
let mut txins: Vec < TxIn > = Vec :: new ( ) ;
665
- txins. push ( TxIn {
665
+ txins. push ( build_htlc_input ( commitment_txid, htlc, opt_anchors) ) ;
666
+
667
+ let mut txouts: Vec < TxOut > = Vec :: new ( ) ;
668
+ txouts. push ( build_htlc_output (
669
+ feerate_per_kw, contest_delay, htlc, opt_anchors, use_non_zero_fee_anchors,
670
+ broadcaster_delayed_payment_key, revocation_key
671
+ ) ) ;
672
+
673
+ Transaction {
674
+ version : 2 ,
675
+ lock_time : PackedLockTime ( if htlc. offered { htlc. cltv_expiry } else { 0 } ) ,
676
+ input : txins,
677
+ output : txouts,
678
+ }
679
+ }
680
+
681
+ pub ( crate ) fn build_htlc_input ( commitment_txid : & Txid , htlc : & HTLCOutputInCommitment , opt_anchors : bool ) -> TxIn {
682
+ TxIn {
666
683
previous_output : OutPoint {
667
684
txid : commitment_txid. clone ( ) ,
668
685
vout : htlc. transaction_output_index . expect ( "Can't build an HTLC transaction for a dust output" ) ,
669
686
} ,
670
687
script_sig : Script :: new ( ) ,
671
688
sequence : Sequence ( if opt_anchors { 1 } else { 0 } ) ,
672
689
witness : Witness :: new ( ) ,
673
- } ) ;
690
+ }
691
+ }
674
692
693
+ pub ( crate ) fn build_htlc_output (
694
+ feerate_per_kw : u32 , contest_delay : u16 , htlc : & HTLCOutputInCommitment , opt_anchors : bool ,
695
+ use_non_zero_fee_anchors : bool , broadcaster_delayed_payment_key : & PublicKey , revocation_key : & PublicKey
696
+ ) -> TxOut {
675
697
let weight = if htlc. offered {
676
698
htlc_timeout_tx_weight ( opt_anchors)
677
699
} else {
@@ -684,18 +706,41 @@ pub fn build_htlc_transaction(commitment_txid: &Txid, feerate_per_kw: u32, conte
684
706
htlc. amount_msat / 1000 - total_fee
685
707
} ;
686
708
687
- let mut txouts: Vec < TxOut > = Vec :: new ( ) ;
688
- txouts. push ( TxOut {
709
+ TxOut {
689
710
script_pubkey : get_revokeable_redeemscript ( revocation_key, contest_delay, broadcaster_delayed_payment_key) . to_v0_p2wsh ( ) ,
690
711
value : output_value,
691
- } ) ;
712
+ }
713
+ }
692
714
693
- Transaction {
694
- version : 2 ,
695
- lock_time : PackedLockTime ( if htlc. offered { htlc. cltv_expiry } else { 0 } ) ,
696
- input : txins,
697
- output : txouts,
715
+ /// Returns the witness required to satisfy and spend a HTLC input.
716
+ pub fn build_htlc_input_witness (
717
+ local_sig : & Signature , remote_sig : & Signature , preimage : & Option < PaymentPreimage > ,
718
+ redeem_script : & Script , opt_anchors : bool ,
719
+ ) -> Witness {
720
+ let remote_sighash_type = if opt_anchors {
721
+ EcdsaSighashType :: SinglePlusAnyoneCanPay
722
+ } else {
723
+ EcdsaSighashType :: All
724
+ } ;
725
+ let mut remote_sig = remote_sig. serialize_der ( ) . to_vec ( ) ;
726
+ remote_sig. push ( remote_sighash_type as u8 ) ;
727
+
728
+ let mut local_sig = local_sig. serialize_der ( ) . to_vec ( ) ;
729
+ local_sig. push ( EcdsaSighashType :: All as u8 ) ;
730
+
731
+ let mut witness = Witness :: new ( ) ;
732
+ // First push the multisig dummy, note that due to BIP147 (NULLDUMMY) it must be a zero-length element.
733
+ witness. push ( vec ! [ ] ) ;
734
+ witness. push ( remote_sig) ;
735
+ witness. push ( local_sig) ;
736
+ if let Some ( preimage) = preimage {
737
+ witness. push ( preimage. 0 . to_vec ( ) ) ;
738
+ } else {
739
+ // Due to BIP146 (MINIMALIF) this must be a zero-length element to relay.
740
+ witness. push ( vec ! [ ] ) ;
698
741
}
742
+ witness. push ( redeem_script. to_bytes ( ) ) ;
743
+ witness
699
744
}
700
745
701
746
/// Gets the witnessScript for the to_remote output when anchors are enabled.
@@ -1536,26 +1581,9 @@ impl<'a> TrustedCommitmentTransaction<'a> {
1536
1581
1537
1582
let htlc_redeemscript = get_htlc_redeemscript_with_explicit_keys ( & this_htlc, self . opt_anchors ( ) , & keys. broadcaster_htlc_key , & keys. countersignatory_htlc_key , & keys. revocation_key ) ;
1538
1583
1539
- let sighashtype = if self . opt_anchors ( ) { EcdsaSighashType :: SinglePlusAnyoneCanPay } else { EcdsaSighashType :: All } ;
1540
-
1541
- // First push the multisig dummy, note that due to BIP147 (NULLDUMMY) it must be a zero-length element.
1542
- htlc_tx. input [ 0 ] . witness . push ( Vec :: new ( ) ) ;
1543
-
1544
- let mut cp_sig_ser = counterparty_signature. serialize_der ( ) . to_vec ( ) ;
1545
- cp_sig_ser. push ( sighashtype as u8 ) ;
1546
- htlc_tx. input [ 0 ] . witness . push ( cp_sig_ser) ;
1547
- let mut holder_sig_ser = signature. serialize_der ( ) . to_vec ( ) ;
1548
- holder_sig_ser. push ( EcdsaSighashType :: All as u8 ) ;
1549
- htlc_tx. input [ 0 ] . witness . push ( holder_sig_ser) ;
1550
-
1551
- if this_htlc. offered {
1552
- // Due to BIP146 (MINIMALIF) this must be a zero-length element to relay.
1553
- htlc_tx. input [ 0 ] . witness . push ( Vec :: new ( ) ) ;
1554
- } else {
1555
- htlc_tx. input [ 0 ] . witness . push ( preimage. unwrap ( ) . 0 . to_vec ( ) ) ;
1556
- }
1557
-
1558
- htlc_tx. input [ 0 ] . witness . push ( htlc_redeemscript. as_bytes ( ) . to_vec ( ) ) ;
1584
+ htlc_tx. input [ 0 ] . witness = chan_utils:: build_htlc_input_witness (
1585
+ signature, counterparty_signature, preimage, & htlc_redeemscript, self . opt_anchors ( ) ,
1586
+ ) ;
1559
1587
htlc_tx
1560
1588
}
1561
1589
}
0 commit comments