@@ -66,6 +66,8 @@ use crate::util::errors::APIError;
6666use crate::util::config::{UserConfig, ChannelConfig, LegacyChannelConfig, ChannelHandshakeConfig, ChannelHandshakeLimits, MaxDustHTLCExposure};
6767use crate::util::scid_utils::scid_from_parts;
6868
69+ use alloc::collections::BTreeMap;
70+
6971use crate::io;
7072use crate::prelude::*;
7173use core::time::Duration;
@@ -5777,6 +5779,11 @@ impl<SP: Deref> FundedChannel<SP> where
57775779 ClosureReason::HolderForceClosed { broadcasted_latest_txn: Some(false) },
57785780 )));
57795781 }
5782+
5783+ if msg.batch.is_some() {
5784+ return Err(ChannelError::close("Peer sent initial commitment_signed with a batch".to_owned()));
5785+ }
5786+
57805787 let holder_commitment_point = &mut self.holder_commitment_point.clone();
57815788 self.context.assert_no_commitment_advancement(holder_commitment_point.transaction_number(), "initial commitment_signed");
57825789
@@ -5804,6 +5811,49 @@ impl<SP: Deref> FundedChannel<SP> where
58045811 pub fn commitment_signed<L: Deref>(&mut self, msg: &msgs::CommitmentSigned, logger: &L) -> Result<Option<ChannelMonitorUpdate>, ChannelError>
58055812 where L::Target: Logger
58065813 {
5814+ self.commitment_signed_check_state()?;
5815+
5816+ let updates = self
5817+ .context
5818+ .validate_commitment_signed(&self.funding, &self.holder_commitment_point, msg, logger)
5819+ .map(|LatestHolderCommitmentTXInfo { commitment_tx, htlc_outputs, nondust_htlc_sources }|
5820+ vec![ChannelMonitorUpdateStep::LatestHolderCommitmentTXInfo {
5821+ commitment_tx, htlc_outputs, claimed_htlcs: vec![], nondust_htlc_sources,
5822+ }]
5823+ )?;
5824+
5825+ self.commitment_signed_update_monitor(updates, logger)
5826+ }
5827+
5828+ pub fn commitment_signed_batch<L: Deref>(&mut self, batch: &BTreeMap<Txid, msgs::CommitmentSigned>, logger: &L) -> Result<Option<ChannelMonitorUpdate>, ChannelError>
5829+ where L::Target: Logger
5830+ {
5831+ self.commitment_signed_check_state()?;
5832+
5833+ // Any commitment_signed not associated with a FundingScope is ignored below if a
5834+ // pending splice transaction has confirmed since receiving the batch.
5835+ let updates = core::iter::once(&self.funding)
5836+ .chain(self.pending_funding.iter())
5837+ .map(|funding| {
5838+ let funding_txid = funding.get_funding_txo().unwrap().txid;
5839+ let msg = batch
5840+ .get(&funding_txid)
5841+ .ok_or_else(|| ChannelError::close(format!("Peer did not send a commitment_signed for pending splice transaction: {}", funding_txid)))?;
5842+ self.context
5843+ .validate_commitment_signed(funding, &self.holder_commitment_point, msg, logger)
5844+ .map(|LatestHolderCommitmentTXInfo { commitment_tx, htlc_outputs, nondust_htlc_sources }|
5845+ ChannelMonitorUpdateStep::LatestHolderCommitmentTXInfo {
5846+ commitment_tx, htlc_outputs, claimed_htlcs: vec![], nondust_htlc_sources,
5847+ }
5848+ )
5849+ }
5850+ )
5851+ .collect::<Result<Vec<_>, ChannelError>>()?;
5852+
5853+ self.commitment_signed_update_monitor(updates, logger)
5854+ }
5855+
5856+ fn commitment_signed_check_state(&self) -> Result<(), ChannelError> {
58075857 if self.context.channel_state.is_quiescent() {
58085858 return Err(ChannelError::WarnAndDisconnect("Got commitment_signed message while quiescent".to_owned()));
58095859 }
@@ -5817,8 +5867,12 @@ impl<SP: Deref> FundedChannel<SP> where
58175867 return Err(ChannelError::close("Peer sent commitment_signed after we'd started exchanging closing_signeds".to_owned()));
58185868 }
58195869
5820- let commitment_tx_info = self.context.validate_commitment_signed(&self.funding, &self.holder_commitment_point, msg, logger)?;
5870+ Ok(())
5871+ }
58215872
5873+ fn commitment_signed_update_monitor<L: Deref>(&mut self, mut updates: Vec<ChannelMonitorUpdateStep>, logger: &L) -> Result<Option<ChannelMonitorUpdate>, ChannelError>
5874+ where L::Target: Logger
5875+ {
58225876 if self.holder_commitment_point.advance(&self.context.holder_signer, &self.context.secp_ctx, logger).is_err() {
58235877 // We only fail to advance our commitment point/number if we're currently
58245878 // waiting for our signer to unblock and provide a commitment point.
@@ -5872,18 +5926,21 @@ impl<SP: Deref> FundedChannel<SP> where
58725926 }
58735927 }
58745928
5875- let LatestHolderCommitmentTXInfo {
5876- commitment_tx, htlc_outputs, nondust_htlc_sources,
5877- } = commitment_tx_info;
5929+ for mut update in updates.iter_mut() {
5930+ if let ChannelMonitorUpdateStep::LatestHolderCommitmentTXInfo {
5931+ claimed_htlcs: ref mut update_claimed_htlcs, ..
5932+ } = &mut update {
5933+ debug_assert!(update_claimed_htlcs.is_empty());
5934+ *update_claimed_htlcs = claimed_htlcs.clone();
5935+ } else {
5936+ debug_assert!(false);
5937+ }
5938+ }
5939+
58785940 self.context.latest_monitor_update_id += 1;
58795941 let mut monitor_update = ChannelMonitorUpdate {
58805942 update_id: self.context.latest_monitor_update_id,
5881- updates: vec![ChannelMonitorUpdateStep::LatestHolderCommitmentTXInfo {
5882- commitment_tx,
5883- htlc_outputs,
5884- claimed_htlcs,
5885- nondust_htlc_sources,
5886- }],
5943+ updates,
58875944 channel_id: Some(self.context.channel_id()),
58885945 };
58895946
0 commit comments