Skip to content

Commit d5ac2f3

Browse files
committed
Provide non-dust HTLC sources separately for holder commitment updates
Currently, non-dust HTLCs are duplicated across the commitment transaction itself, and the full set of HTLCs (dust & non-dust) along with their `HTLCSource` considered in the commitment transaction. As of v0.0.15, we've had support for providing non-dust HTLC sources separately such that we no longer track duplicate non-dust HTLC data, but only enabled it under testing environments. This commit enables it such that it always happens. Note that we still need to support reading `ChannelMonitorUpdateStep::LatestHolderCommitmentTXInfo` updates that did not separate the non-dust HTLC sources in case they were written in an older version and they've yet to be processed.
1 parent 1fc2726 commit d5ac2f3

File tree

2 files changed

+13
-26
lines changed

2 files changed

+13
-26
lines changed

lightning/src/chain/channelmonitor.rs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -531,6 +531,9 @@ pub(crate) enum ChannelMonitorUpdateStep {
531531
/// Note that LDK after 0.0.115 supports this only containing dust HTLCs (implying the
532532
/// `Signature` field is never filled in). At that point, non-dust HTLCs are implied by the
533533
/// HTLC fields in `commitment_tx` and the sources passed via `nondust_htlc_sources`.
534+
/// Starting with 0.2, the non-dust HTLC sources will always be provided separately, and
535+
/// `htlc_outputs` will only include dust HTLCs. We still have to track the
536+
/// `Option<Signature>` for backwards compatibility.
534537
htlc_outputs: Vec<(HTLCOutputInCommitment, Option<Signature>, Option<HTLCSource>)>,
535538
claimed_htlcs: Vec<(SentHTLCId, PaymentPreimage)>,
536539
nondust_htlc_sources: Vec<HTLCSource>,

lightning/src/ln/channel.rs

Lines changed: 10 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -3534,23 +3534,8 @@ impl<SP: Deref> ChannelContext<SP> where SP::Target: SignerProvider {
35343534
return Err(ChannelError::close(format!("Got wrong number of HTLC signatures ({}) from remote. It must be {}", msg.htlc_signatures.len(), commitment_stats.num_nondust_htlcs)));
35353535
}
35363536

3537-
// Up to LDK 0.0.115, HTLC information was required to be duplicated in the
3538-
// `htlcs_and_sigs` vec and in the `holder_commitment_tx` itself, both of which were passed
3539-
// in the `ChannelMonitorUpdate`. In 0.0.115, support for having a separate set of
3540-
// outbound-non-dust-HTLCSources in the `ChannelMonitorUpdate` was added, however for
3541-
// backwards compatibility, we never use it in production. To provide test coverage, here,
3542-
// we randomly decide (in test/fuzzing builds) to use the new vec sometimes.
3543-
#[allow(unused_assignments, unused_mut)]
3544-
let mut separate_nondust_htlc_sources = false;
3545-
#[cfg(all(feature = "std", any(test, fuzzing)))] {
3546-
use core::hash::{BuildHasher, Hasher};
3547-
// Get a random value using the only std API to do so - the DefaultHasher
3548-
let rand_val = std::collections::hash_map::RandomState::new().build_hasher().finish();
3549-
separate_nondust_htlc_sources = rand_val % 2 == 0;
3550-
}
3551-
3552-
let mut nondust_htlc_sources = Vec::with_capacity(htlcs_cloned.len());
3553-
let mut htlcs_and_sigs = Vec::with_capacity(htlcs_cloned.len());
3537+
let mut nondust_htlc_sources = Vec::with_capacity(commitment_stats.num_nondust_htlcs);
3538+
let mut dust_htlcs = Vec::with_capacity(htlcs_cloned.len() - commitment_stats.num_nondust_htlcs);
35543539
for (idx, (htlc, mut source_opt)) in htlcs_cloned.drain(..).enumerate() {
35553540
if let Some(_) = htlc.transaction_output_index {
35563541
let htlc_tx = chan_utils::build_htlc_transaction(&commitment_txid, commitment_stats.feerate_per_kw,
@@ -3566,16 +3551,15 @@ impl<SP: Deref> ChannelContext<SP> where SP::Target: SignerProvider {
35663551
if let Err(_) = self.secp_ctx.verify_ecdsa(&htlc_sighash, &msg.htlc_signatures[idx], &keys.countersignatory_htlc_key.to_public_key()) {
35673552
return Err(ChannelError::close("Invalid HTLC tx signature from peer".to_owned()));
35683553
}
3569-
if !separate_nondust_htlc_sources {
3570-
htlcs_and_sigs.push((htlc, Some(msg.htlc_signatures[idx]), source_opt.take()));
3554+
if htlc.offered {
3555+
if let Some(source) = source_opt.take() {
3556+
nondust_htlc_sources.push(source);
3557+
} else {
3558+
panic!("Missing outbound HTLC source");
3559+
}
35713560
}
35723561
} else {
3573-
htlcs_and_sigs.push((htlc, None, source_opt.take()));
3574-
}
3575-
if separate_nondust_htlc_sources {
3576-
if let Some(source) = source_opt.take() {
3577-
nondust_htlc_sources.push(source);
3578-
}
3562+
dust_htlcs.push((htlc, None, source_opt.take()));
35793563
}
35803564
debug_assert!(source_opt.is_none(), "HTLCSource should have been put somewhere");
35813565
}
@@ -3593,7 +3577,7 @@ impl<SP: Deref> ChannelContext<SP> where SP::Target: SignerProvider {
35933577

35943578
Ok(LatestHolderCommitmentTXInfo {
35953579
commitment_tx: holder_commitment_tx,
3596-
htlc_outputs: htlcs_and_sigs,
3580+
htlc_outputs: dust_htlcs,
35973581
nondust_htlc_sources,
35983582
})
35993583
}

0 commit comments

Comments
 (0)