From: Matt Corallo Date: Fri, 18 Nov 2022 22:51:17 +0000 (+0000) Subject: Explicitly track the set of spendable transactions which confirm X-Git-Tag: v0.0.113~28^2~2 X-Git-Url: http://git.bitcoin.ninja/index.cgi?a=commitdiff_plain;h=537e91cb1ec4ef65728e3fdda5eb5e2e19fd91c8;p=rust-lightning Explicitly track the set of spendable transactions which confirm In `ChannelMonitor`s, when a transaction containing a spend of a revoked remote output reaches 6 confs, we may have no other tracking of that txid remaining. Thus, if we see that transaction again (because a user duplicatively confirms it), we'll generate a redundant spendable output event for it. Here we simply explicitly track all txids of transactions which confirm with a spendable output, allowing us to check this condition in the next commit. --- diff --git a/lightning/src/chain/channelmonitor.rs b/lightning/src/chain/channelmonitor.rs index c0d0affcc..1cbc85350 100644 --- a/lightning/src/chain/channelmonitor.rs +++ b/lightning/src/chain/channelmonitor.rs @@ -826,6 +826,13 @@ pub(crate) struct ChannelMonitorImpl { /// spending CSV for revocable outputs). htlcs_resolved_on_chain: Vec, + /// The set of `SpendableOutput` events which we have already passed upstream to be claimed. + /// These are tracked explicitly to ensure that we don't generate the same events redundantly + /// if users duplicatively confirm old transactions. Specifically for transactions claiming a + /// revoked remote outpoint we otherwise have no tracking at all once they've reached + /// [`ANTI_REORG_DELAY`], so we have to track them here. + spendable_txids_confirmed: Vec, + // We simply modify best_block in Channel's block_connected so that serialization is // consistent but hopefully the users' copy handles block_connected in a consistent way. // (we do *not*, however, update them in update_monitor to ensure any local user copies keep @@ -1071,6 +1078,7 @@ impl Writeable for ChannelMonitorImpl { (7, self.funding_spend_seen, required), (9, self.counterparty_node_id, option), (11, self.confirmed_commitment_tx_counterparty_output, option), + (13, self.spendable_txids_confirmed, vec_type), }); Ok(()) @@ -1179,6 +1187,7 @@ impl ChannelMonitor { funding_spend_confirmed: None, confirmed_commitment_tx_counterparty_output: None, htlcs_resolved_on_chain: Vec::new(), + spendable_txids_confirmed: Vec::new(), best_block, counterparty_node_id: Some(counterparty_node_id), @@ -3042,6 +3051,7 @@ impl ChannelMonitorImpl { self.pending_events.push(Event::SpendableOutputs { outputs: vec![descriptor] }); + self.spendable_txids_confirmed.push(entry.txid); }, OnchainEvent::HTLCSpendConfirmation { commitment_tx_output_idx, preimage, .. } => { self.htlcs_resolved_on_chain.push(IrrevocablyResolvedHTLC { @@ -3763,6 +3773,7 @@ impl<'a, K: KeysInterface> ReadableArgs<&'a K> let mut funding_spend_seen = Some(false); let mut counterparty_node_id = None; let mut confirmed_commitment_tx_counterparty_output = None; + let mut spendable_txids_confirmed = Some(Vec::new()); read_tlv_fields!(reader, { (1, funding_spend_confirmed, option), (3, htlcs_resolved_on_chain, vec_type), @@ -3770,6 +3781,7 @@ impl<'a, K: KeysInterface> ReadableArgs<&'a K> (7, funding_spend_seen, option), (9, counterparty_node_id, option), (11, confirmed_commitment_tx_counterparty_output, option), + (13, spendable_txids_confirmed, vec_type), }); let mut secp_ctx = Secp256k1::new(); @@ -3822,6 +3834,7 @@ impl<'a, K: KeysInterface> ReadableArgs<&'a K> funding_spend_confirmed, confirmed_commitment_tx_counterparty_output, htlcs_resolved_on_chain: htlcs_resolved_on_chain.unwrap(), + spendable_txids_confirmed: spendable_txids_confirmed.unwrap(), best_block, counterparty_node_id,