X-Git-Url: http://git.bitcoin.ninja/index.cgi?a=blobdiff_plain;f=lightning%2Fsrc%2Futil%2Fevents.rs;h=a9687d28802266dfe0aa89868d1cf9aef61e845d;hb=94a07d9caee6d38d42954ac783c49afe1cf89697;hp=ef0c619b02e9f7a1b03cd6dd14b439e7799264dc;hpb=1fd6c6fb9f7e58e8c0cf6539e7a9451e57a2b6fd;p=rust-lightning diff --git a/lightning/src/util/events.rs b/lightning/src/util/events.rs index ef0c619b..a9687d28 100644 --- a/lightning/src/util/events.rs +++ b/lightning/src/util/events.rs @@ -14,27 +14,31 @@ //! future, as well as generate and broadcast funding transactions handle payment preimages and a //! few other things. -use chain::keysinterface::SpendableOutputDescriptor; -use ln::channelmanager::PaymentId; -use ln::channel::FUNDING_CONF_DEADLINE_BLOCKS; -use ln::features::ChannelTypeFeatures; -use ln::msgs; -use ln::msgs::DecodeError; -use ln::{PaymentPreimage, PaymentHash, PaymentSecret}; -use routing::network_graph::NetworkUpdate; -use util::ser::{BigSize, FixedLengthReader, Writeable, Writer, MaybeReadable, Readable, VecReadWrapper, VecWriteWrapper}; -use routing::router::{RouteHop, RouteParameters}; +use crate::chain::keysinterface::SpendableOutputDescriptor; +#[cfg(anchors)] +use crate::ln::chan_utils::HTLCOutputInCommitment; +use crate::ln::channelmanager::PaymentId; +use crate::ln::channel::FUNDING_CONF_DEADLINE_BLOCKS; +use crate::ln::features::ChannelTypeFeatures; +use crate::ln::msgs; +use crate::ln::msgs::DecodeError; +use crate::ln::{PaymentPreimage, PaymentHash, PaymentSecret}; +use crate::routing::gossip::NetworkUpdate; +use crate::util::ser::{BigSize, FixedLengthReader, Writeable, Writer, MaybeReadable, Readable, WithoutLength, OptionDeserWrapper}; +use crate::routing::router::{RouteHop, RouteParameters}; -use bitcoin::Transaction; +use bitcoin::{PackedLockTime, Transaction}; +#[cfg(anchors)] +use bitcoin::OutPoint; use bitcoin::blockdata::script::Script; use bitcoin::hashes::Hash; use bitcoin::hashes::sha256::Hash as Sha256; use bitcoin::secp256k1::PublicKey; -use io; -use prelude::*; +use crate::io; +use crate::prelude::*; use core::time::Duration; use core::ops::Deref; -use sync::Arc; +use crate::sync::Arc; /// Some information provided on receipt of payment depends on whether the payment received is a /// spontaneous payment or a "conventional" lightning payment that's paying an invoice. @@ -66,7 +70,15 @@ pub enum PaymentPurpose { SpontaneousPayment(PaymentPreimage), } -#[derive(Clone, Debug, PartialEq)] +impl_writeable_tlv_based_enum!(PaymentPurpose, + (0, InvoicePayment) => { + (0, payment_preimage, option), + (2, payment_secret, required), + }; + (2, SpontaneousPayment) +); + +#[derive(Clone, Debug, PartialEq, Eq)] /// The reason the channel was closed. See individual variants more details. pub enum ClosureReason { /// Closure generated from receiving a peer error message. @@ -103,11 +115,19 @@ pub enum ClosureReason { /// The peer disconnected prior to funding completing. In this case the spec mandates that we /// forget the channel entirely - we can attempt again if the peer reconnects. /// + /// This includes cases where we restarted prior to funding completion, including prior to the + /// initial [`ChannelMonitor`] persistence completing. + /// /// In LDK versions prior to 0.0.107 this could also occur if we were unable to connect to the /// peer because of mutual incompatibility between us and our channel counterparty. + /// + /// [`ChannelMonitor`]: crate::chain::channelmonitor::ChannelMonitor DisconnectedPeer, - /// Closure generated from `ChannelManager::read` if the ChannelMonitor is newer than - /// the ChannelManager deserialized. + /// Closure generated from `ChannelManager::read` if the [`ChannelMonitor`] is newer than + /// the [`ChannelManager`] deserialized. + /// + /// [`ChannelMonitor`]: crate::chain::channelmonitor::ChannelMonitor + /// [`ChannelManager`]: crate::ln::channelmanager::ChannelManager OutdatedChannelManager } @@ -144,6 +164,130 @@ impl_writeable_tlv_based_enum_upgradable!(ClosureReason, (12, OutdatedChannelManager) => {}, ); +/// Intended destination of a failed HTLC as indicated in [`Event::HTLCHandlingFailed`]. +#[derive(Clone, Debug, PartialEq, Eq)] +pub enum HTLCDestination { + /// We tried forwarding to a channel but failed to do so. An example of such an instance is when + /// there is insufficient capacity in our outbound channel. + NextHopChannel { + /// The `node_id` of the next node. For backwards compatibility, this field is + /// marked as optional, versions prior to 0.0.110 may not always be able to provide + /// counterparty node information. + node_id: Option, + /// The outgoing `channel_id` between us and the next node. + channel_id: [u8; 32], + }, + /// Scenario where we are unsure of the next node to forward the HTLC to. + UnknownNextHop { + /// Short channel id we are requesting to forward an HTLC to. + requested_forward_scid: u64, + }, + /// Failure scenario where an HTLC may have been forwarded to be intended for us, + /// but is invalid for some reason, so we reject it. + /// + /// Some of the reasons may include: + /// * HTLC Timeouts + /// * Expected MPP amount to claim does not equal HTLC total + /// * Claimable amount does not match expected amount + FailedPayment { + /// The payment hash of the payment we attempted to process. + payment_hash: PaymentHash + }, +} + +impl_writeable_tlv_based_enum_upgradable!(HTLCDestination, + (0, NextHopChannel) => { + (0, node_id, required), + (2, channel_id, required), + }, + (2, UnknownNextHop) => { + (0, requested_forward_scid, required), + }, + (4, FailedPayment) => { + (0, payment_hash, required), + } +); + +#[cfg(anchors)] +/// A descriptor used to sign for a commitment transaction's anchor output. +#[derive(Clone, Debug)] +pub struct AnchorDescriptor { + /// A unique identifier used along with `channel_value_satoshis` to re-derive the + /// [`InMemorySigner`] required to sign `input`. + /// + /// [`InMemorySigner`]: crate::chain::keysinterface::InMemorySigner + pub channel_keys_id: [u8; 32], + /// The value in satoshis of the channel we're attempting to spend the anchor output of. This is + /// used along with `channel_keys_id` to re-derive the [`InMemorySigner`] required to sign + /// `input`. + /// + /// [`InMemorySigner`]: crate::chain::keysinterface::InMemorySigner + pub channel_value_satoshis: u64, + /// The transaction input's outpoint corresponding to the commitment transaction's anchor + /// output. + pub outpoint: OutPoint, +} + +#[cfg(anchors)] +/// Represents the different types of transactions, originating from LDK, to be bumped. +#[derive(Clone, Debug)] +pub enum BumpTransactionEvent { + /// Indicates that a channel featuring anchor outputs is to be closed by broadcasting the local + /// commitment transaction. Since commitment transactions have a static feerate pre-agreed upon, + /// they may need additional fees to be attached through a child transaction using the popular + /// [Child-Pays-For-Parent](https://bitcoinops.org/en/topics/cpfp) fee bumping technique. This + /// child transaction must include the anchor input described within `anchor_descriptor` along + /// with additional inputs to meet the target feerate. Failure to meet the target feerate + /// decreases the confirmation odds of the transaction package (which includes the commitment + /// and child anchor transactions), possibly resulting in a loss of funds. Once the transaction + /// is constructed, it must be fully signed for and broadcasted by the consumer of the event + /// along with the `commitment_tx` enclosed. Note that the `commitment_tx` must always be + /// broadcast first, as the child anchor transaction depends on it. + /// + /// The consumer should be able to sign for any of the additional inputs included within the + /// child anchor transaction. To sign its anchor input, an [`InMemorySigner`] should be + /// re-derived through [`KeysManager::derive_channel_keys`] with the help of + /// [`AnchorDescriptor::channel_keys_id`] and [`AnchorDescriptor::channel_value_satoshis`]. + /// + /// It is possible to receive more than one instance of this event if a valid child anchor + /// transaction is never broadcast or is but not with a sufficient fee to be mined. Care should + /// be taken by the consumer of the event to ensure any future iterations of the child anchor + /// transaction adhere to the [Replace-By-Fee + /// rules](https://github.com/bitcoin/bitcoin/blob/master/doc/policy/mempool-replacements.md) + /// for fee bumps to be accepted into the mempool, and eventually the chain. As the frequency of + /// these events is not user-controlled, users may ignore/drop the event if they are no longer + /// able to commit external confirmed funds to the child anchor transaction. + /// + /// The set of `pending_htlcs` on the commitment transaction to be broadcast can be inspected to + /// determine whether a significant portion of the channel's funds are allocated to HTLCs, + /// enabling users to make their own decisions regarding the importance of the commitment + /// transaction's confirmation. Note that this is not required, but simply exists as an option + /// for users to override LDK's behavior. On commitments with no HTLCs (indicated by those with + /// an empty `pending_htlcs`), confirmation of the commitment transaction can be considered to + /// be not urgent. + /// + /// [`InMemorySigner`]: crate::chain::keysinterface::InMemorySigner + /// [`KeysManager::derive_channel_keys`]: crate::chain::keysinterface::KeysManager::derive_channel_keys + ChannelClose { + /// The target feerate that the transaction package, which consists of the commitment + /// transaction and the to-be-crafted child anchor transaction, must meet. + package_target_feerate_sat_per_1000_weight: u32, + /// The channel's commitment transaction to bump the fee of. This transaction should be + /// broadcast along with the anchor transaction constructed as a result of consuming this + /// event. + commitment_tx: Transaction, + /// The absolute fee in satoshis of the commitment transaction. This can be used along the + /// with weight of the commitment transaction to determine its feerate. + commitment_tx_fee_satoshis: u64, + /// The descriptor to sign the anchor input of the anchor transaction constructed as a + /// result of consuming this event. + anchor_descriptor: AnchorDescriptor, + /// The set of pending HTLCs on the commitment transaction that need to be resolved once the + /// commitment transaction confirms. + pending_htlcs: Vec, + }, +} + /// An Event which you should probably take some action in response to. /// /// Note that while Writeable and Readable are implemented for Event, you probably shouldn't use @@ -180,8 +324,9 @@ pub enum Event { /// [`ChannelManager::create_channel`]: crate::ln::channelmanager::ChannelManager::create_channel user_channel_id: u64, }, - /// Indicates we've received money! Just gotta dig out that payment preimage and feed it to - /// [`ChannelManager::claim_funds`] to get it.... + /// Indicates we've received (an offer of) money! Just gotta dig out that payment preimage and + /// feed it to [`ChannelManager::claim_funds`] to get it.... + /// /// Note that if the preimage is not known, you should call /// [`ChannelManager::fail_htlc_backwards`] to free up resources for this HTLC and avoid /// network congestion. @@ -200,11 +345,35 @@ pub enum Event { /// not stop you from registering duplicate payment hashes for inbound payments. payment_hash: PaymentHash, /// The value, in thousandths of a satoshi, that this payment is for. - amt: u64, + amount_msat: u64, /// Information for claiming this received payment, based on whether the purpose of the /// payment is to pay an invoice or to send a spontaneous payment. purpose: PaymentPurpose, }, + /// Indicates a payment has been claimed and we've received money! + /// + /// This most likely occurs when [`ChannelManager::claim_funds`] has been called in response + /// to an [`Event::PaymentReceived`]. However, if we previously crashed during a + /// [`ChannelManager::claim_funds`] call you may see this event without a corresponding + /// [`Event::PaymentReceived`] event. + /// + /// # Note + /// LDK will not stop an inbound payment from being paid multiple times, so multiple + /// `PaymentReceived` events may be generated for the same payment. If you then call + /// [`ChannelManager::claim_funds`] twice for the same [`Event::PaymentReceived`] you may get + /// multiple `PaymentClaimed` events. + /// + /// [`ChannelManager::claim_funds`]: crate::ln::channelmanager::ChannelManager::claim_funds + PaymentClaimed { + /// The payment hash of the claimed payment. Note that LDK will not stop you from + /// registering duplicate payment hashes for inbound payments. + payment_hash: PaymentHash, + /// The value, in thousandths of a satoshi, that this payment is for. + amount_msat: u64, + /// The purpose of this claimed payment, i.e. whether the payment was for an invoice or a + /// spontaneous payment. + purpose: PaymentPurpose, + }, /// Indicates an outbound payment we made succeeded (i.e. it made it all the way to its target /// and we got back the payment preimage for it). /// @@ -240,8 +409,8 @@ pub enum Event { /// provide failure information for each MPP part in the payment. /// /// This event is provided once there are no further pending HTLCs for the payment and the - /// payment is no longer retryable, either due to a several-block timeout or because - /// [`ChannelManager::abandon_payment`] was previously called for the corresponding payment. + /// payment is no longer retryable due to [`ChannelManager::abandon_payment`] having been + /// called for the corresponding payment. /// /// [`ChannelManager::abandon_payment`]: crate::ln::channelmanager::ChannelManager::abandon_payment PaymentFailed { @@ -280,9 +449,14 @@ pub enum Event { /// Indicates an outbound HTLC we sent failed. Probably some intermediary node dropped /// something. You may wish to retry with a different route. /// + /// If you have given up retrying this payment and wish to fail it, you MUST call + /// [`ChannelManager::abandon_payment`] at least once for a given [`PaymentId`] or memory + /// related to payment tracking will leak. + /// /// Note that this does *not* indicate that all paths for an MPP payment have failed, see /// [`Event::PaymentFailed`] and [`all_paths_failed`]. /// + /// [`ChannelManager::abandon_payment`]: crate::ln::channelmanager::ChannelManager::abandon_payment /// [`all_paths_failed`]: Self::PaymentPathFailed::all_paths_failed PaymentPathFailed { /// The id returned by [`ChannelManager::send_payment`] and used with @@ -299,15 +473,14 @@ pub enum Event { /// Indicates the payment was rejected for some reason by the recipient. This implies that /// the payment has failed, not just the route in question. If this is not set, you may /// retry the payment via a different route. - rejected_by_dest: bool, + payment_failed_permanently: bool, /// Any failure information conveyed via the Onion return packet by a node along the failed /// payment route. /// /// Should be applied to the [`NetworkGraph`] so that routing decisions can take into - /// account the update. [`NetGraphMsgHandler`] is capable of doing this. + /// account the update. /// - /// [`NetworkGraph`]: crate::routing::network_graph::NetworkGraph - /// [`NetGraphMsgHandler`]: crate::routing::network_graph::NetGraphMsgHandler + /// [`NetworkGraph`]: crate::routing::gossip::NetworkGraph network_update: Option, /// For both single-path and multi-path payments, this is set if all paths of the payment have /// failed. This will be set to false if (1) this is an MPP payment and (2) other parts of the @@ -331,6 +504,10 @@ pub enum Event { path: Vec, /// The channel responsible for the failed payment path. /// + /// Note that for route hints or for the first hop in a path this may be an SCID alias and + /// may not refer to a channel in the public network graph. These aliases may also collide + /// with channels in the public network graph. + /// /// If this is `Some`, then the corresponding channel should be avoided when the payment is /// retried. May be `None` for older [`Event`] serializations. short_channel_id: Option, @@ -346,6 +523,38 @@ pub enum Event { #[cfg(test)] error_data: Option>, }, + /// Indicates that a probe payment we sent returned successful, i.e., only failed at the destination. + ProbeSuccessful { + /// The id returned by [`ChannelManager::send_probe`]. + /// + /// [`ChannelManager::send_probe`]: crate::ln::channelmanager::ChannelManager::send_probe + payment_id: PaymentId, + /// The hash generated by [`ChannelManager::send_probe`]. + /// + /// [`ChannelManager::send_probe`]: crate::ln::channelmanager::ChannelManager::send_probe + payment_hash: PaymentHash, + /// The payment path that was successful. + path: Vec, + }, + /// Indicates that a probe payment we sent failed at an intermediary node on the path. + ProbeFailed { + /// The id returned by [`ChannelManager::send_probe`]. + /// + /// [`ChannelManager::send_probe`]: crate::ln::channelmanager::ChannelManager::send_probe + payment_id: PaymentId, + /// The hash generated by [`ChannelManager::send_probe`]. + /// + /// [`ChannelManager::send_probe`]: crate::ln::channelmanager::ChannelManager::send_probe + payment_hash: PaymentHash, + /// The payment path that failed. + path: Vec, + /// The channel responsible for the failed probe. + /// + /// Note that for route hints or for the first hop in a path this may be an SCID alias and + /// may not refer to a channel in the public network graph. These aliases may also collide + /// with channels in the public network graph. + short_channel_id: Option, + }, /// Used to indicate that [`ChannelManager::process_pending_htlc_forwards`] should be called at /// a time in the future. /// @@ -393,7 +602,29 @@ pub enum Event { /// transaction. claim_from_onchain_tx: bool, }, - /// Used to indicate that a channel with the given `channel_id` is in the process of closure. + /// Used to indicate that a channel with the given `channel_id` is ready to + /// be used. This event is emitted either when the funding transaction has been confirmed + /// on-chain, or, in case of a 0conf channel, when both parties have confirmed the channel + /// establishment. + ChannelReady { + /// The channel_id of the channel that is ready. + channel_id: [u8; 32], + /// The `user_channel_id` value passed in to [`ChannelManager::create_channel`] for outbound + /// channels, or to [`ChannelManager::accept_inbound_channel`] for inbound channels if + /// [`UserConfig::manually_accept_inbound_channels`] config flag is set to true. Otherwise + /// `user_channel_id` will be 0 for an inbound channel. + /// + /// [`ChannelManager::create_channel`]: crate::ln::channelmanager::ChannelManager::create_channel + /// [`ChannelManager::accept_inbound_channel`]: crate::ln::channelmanager::ChannelManager::accept_inbound_channel + /// [`UserConfig::manually_accept_inbound_channels`]: crate::util::config::UserConfig::manually_accept_inbound_channels + user_channel_id: u64, + /// The node_id of the channel counterparty. + counterparty_node_id: PublicKey, + /// The features that this channel will operate with. + channel_type: ChannelTypeFeatures, + }, + /// Used to indicate that a previously opened channel with the given `channel_id` is in the + /// process of closure. ChannelClosed { /// The channel_id of the channel which has been closed. Note that on-chain transactions /// resolving the channel are likely still awaiting confirmation. @@ -422,33 +653,33 @@ pub enum Event { /// Indicates a request to open a new channel by a peer. /// /// To accept the request, call [`ChannelManager::accept_inbound_channel`]. To reject the - /// request, call [`ChannelManager::force_close_channel`]. + /// request, call [`ChannelManager::force_close_without_broadcasting_txn`]. /// /// The event is only triggered when a new open channel request is received and the /// [`UserConfig::manually_accept_inbound_channels`] config flag is set to true. /// /// [`ChannelManager::accept_inbound_channel`]: crate::ln::channelmanager::ChannelManager::accept_inbound_channel - /// [`ChannelManager::force_close_channel`]: crate::ln::channelmanager::ChannelManager::force_close_channel + /// [`ChannelManager::force_close_without_broadcasting_txn`]: crate::ln::channelmanager::ChannelManager::force_close_without_broadcasting_txn /// [`UserConfig::manually_accept_inbound_channels`]: crate::util::config::UserConfig::manually_accept_inbound_channels OpenChannelRequest { /// The temporary channel ID of the channel requested to be opened. /// /// When responding to the request, the `temporary_channel_id` should be passed /// back to the ChannelManager through [`ChannelManager::accept_inbound_channel`] to accept, - /// or through [`ChannelManager::force_close_channel`] to reject. + /// or through [`ChannelManager::force_close_without_broadcasting_txn`] to reject. /// /// [`ChannelManager::accept_inbound_channel`]: crate::ln::channelmanager::ChannelManager::accept_inbound_channel - /// [`ChannelManager::force_close_channel`]: crate::ln::channelmanager::ChannelManager::force_close_channel + /// [`ChannelManager::force_close_without_broadcasting_txn`]: crate::ln::channelmanager::ChannelManager::force_close_without_broadcasting_txn temporary_channel_id: [u8; 32], /// The node_id of the counterparty requesting to open the channel. /// /// When responding to the request, the `counterparty_node_id` should be passed /// back to the `ChannelManager` through [`ChannelManager::accept_inbound_channel`] to - /// accept the request, or through [`ChannelManager::force_close_channel`] to reject the + /// accept the request, or through [`ChannelManager::force_close_without_broadcasting_txn`] to reject the /// request. /// /// [`ChannelManager::accept_inbound_channel`]: crate::ln::channelmanager::ChannelManager::accept_inbound_channel - /// [`ChannelManager::force_close_channel`]: crate::ln::channelmanager::ChannelManager::force_close_channel + /// [`ChannelManager::force_close_without_broadcasting_txn`]: crate::ln::channelmanager::ChannelManager::force_close_without_broadcasting_txn counterparty_node_id: PublicKey, /// The channel value of the requested channel. funding_satoshis: u64, @@ -462,9 +693,40 @@ pub enum Event { /// the resulting [`ChannelManager`] will not be readable by versions of LDK prior to /// 0.0.106. /// + /// Furthermore, note that if [`ChannelTypeFeatures::supports_zero_conf`] returns true on this type, + /// the resulting [`ChannelManager`] will not be readable by versions of LDK prior to + /// 0.0.107. Channels setting this type also need to get manually accepted via + /// [`crate::ln::channelmanager::ChannelManager::accept_inbound_channel_from_trusted_peer_0conf`], + /// or will be rejected otherwise. + /// /// [`ChannelManager`]: crate::ln::channelmanager::ChannelManager channel_type: ChannelTypeFeatures, }, + /// Indicates that the HTLC was accepted, but could not be processed when or after attempting to + /// forward it. + /// + /// Some scenarios where this event may be sent include: + /// * Insufficient capacity in the outbound channel + /// * While waiting to forward the HTLC, the channel it is meant to be forwarded through closes + /// * When an unknown SCID is requested for forwarding a payment. + /// * Claiming an amount for an MPP payment that exceeds the HTLC total + /// * The HTLC has timed out + /// + /// This event, however, does not get generated if an HTLC fails to meet the forwarding + /// requirements (i.e. insufficient fees paid, or a CLTV that is too soon). + HTLCHandlingFailed { + /// The channel over which the HTLC was received. + prev_channel_id: [u8; 32], + /// Destination of the HTLC that failed to be processed. + failed_next_destination: HTLCDestination, + }, + #[cfg(anchors)] + /// Indicates that a transaction originating from LDK needs to have its fee bumped. This event + /// requires confirmed external funds to be readily available to spend. + /// + /// LDK does not currently generate this event. It is limited to the scope of channels with + /// anchor outputs, which will be introduced in a future release. + BumpTransaction(BumpTransactionEvent), } impl Writeable for Event { @@ -475,7 +737,7 @@ impl Writeable for Event { // We never write out FundingGenerationReady events as, upon disconnection, peers // drop any channels which have not yet exchanged funding_signed. }, - &Event::PaymentReceived { ref payment_hash, ref amt, ref purpose } => { + &Event::PaymentReceived { ref payment_hash, ref amount_msat, ref purpose } => { 1u8.write(writer)?; let mut payment_secret = None; let payment_preimage; @@ -491,7 +753,7 @@ impl Writeable for Event { write_tlv_fields!(writer, { (0, payment_hash, required), (2, payment_secret, option), - (4, amt, required), + (4, amount_msat, required), (6, 0u64, required), // user_payment_id required for compatibility with 0.0.103 and earlier (8, payment_preimage, option), }); @@ -506,7 +768,7 @@ impl Writeable for Event { }); }, &Event::PaymentPathFailed { - ref payment_id, ref payment_hash, ref rejected_by_dest, ref network_update, + ref payment_id, ref payment_hash, ref payment_failed_permanently, ref network_update, ref all_paths_failed, ref path, ref short_channel_id, ref retry, #[cfg(test)] ref error_code, @@ -521,9 +783,9 @@ impl Writeable for Event { write_tlv_fields!(writer, { (0, payment_hash, required), (1, network_update, option), - (2, rejected_by_dest, required), + (2, payment_failed_permanently, required), (3, all_paths_failed, required), - (5, path, vec_type), + (5, *path, vec_type), (7, short_channel_id, option), (9, retry, option), (11, payment_id, option), @@ -537,7 +799,7 @@ impl Writeable for Event { &Event::SpendableOutputs { ref outputs } => { 5u8.write(writer)?; write_tlv_fields!(writer, { - (0, VecWriteWrapper(outputs), required), + (0, WithoutLength(outputs), required), }); }, &Event::PaymentForwarded { fee_earned_msat, prev_channel_id, claim_from_onchain_tx, next_channel_id } => { @@ -569,7 +831,7 @@ impl Writeable for Event { write_tlv_fields!(writer, { (0, payment_id, required), (2, payment_hash, option), - (4, path, vec_type) + (4, *path, vec_type) }) }, &Event::PaymentFailed { ref payment_id, ref payment_hash } => { @@ -584,6 +846,56 @@ impl Writeable for Event { // We never write the OpenChannelRequest events as, upon disconnection, peers // drop any channels which have not yet exchanged funding_signed. }, + &Event::PaymentClaimed { ref payment_hash, ref amount_msat, ref purpose } => { + 19u8.write(writer)?; + write_tlv_fields!(writer, { + (0, payment_hash, required), + (2, purpose, required), + (4, amount_msat, required), + }); + }, + &Event::ProbeSuccessful { ref payment_id, ref payment_hash, ref path } => { + 21u8.write(writer)?; + write_tlv_fields!(writer, { + (0, payment_id, required), + (2, payment_hash, required), + (4, *path, vec_type) + }) + }, + &Event::ProbeFailed { ref payment_id, ref payment_hash, ref path, ref short_channel_id } => { + 23u8.write(writer)?; + write_tlv_fields!(writer, { + (0, payment_id, required), + (2, payment_hash, required), + (4, *path, vec_type), + (6, short_channel_id, option), + }) + }, + &Event::HTLCHandlingFailed { ref prev_channel_id, ref failed_next_destination } => { + 25u8.write(writer)?; + write_tlv_fields!(writer, { + (0, prev_channel_id, required), + (2, failed_next_destination, required), + }) + }, + #[cfg(anchors)] + &Event::BumpTransaction(ref event)=> { + 27u8.write(writer)?; + match event { + // We never write the ChannelClose events as they'll be replayed upon restarting + // anyway if the commitment transaction remains unconfirmed. + BumpTransactionEvent::ChannelClose { .. } => {} + } + } + &Event::ChannelReady { ref channel_id, ref user_channel_id, ref counterparty_node_id, ref channel_type } => { + 29u8.write(writer)?; + write_tlv_fields!(writer, { + (0, channel_id, required), + (2, user_channel_id, required), + (4, counterparty_node_id, required), + (6, channel_type, required), + }); + }, // Note that, going forward, all new events must only write data inside of // `write_tlv_fields`. Versions 0.0.101+ will ignore odd-numbered events that write // data via `write_tlv_fields`. @@ -602,12 +914,12 @@ impl MaybeReadable for Event { let mut payment_hash = PaymentHash([0; 32]); let mut payment_preimage = None; let mut payment_secret = None; - let mut amt = 0; + let mut amount_msat = 0; let mut _user_payment_id = None::; // For compatibility with 0.0.103 and earlier read_tlv_fields!(reader, { (0, payment_hash, required), (2, payment_secret, option), - (4, amt, required), + (4, amount_msat, required), (6, _user_payment_id, option), (8, payment_preimage, option), }); @@ -621,7 +933,7 @@ impl MaybeReadable for Event { }; Ok(Some(Event::PaymentReceived { payment_hash, - amt, + amount_msat, purpose, })) }; @@ -658,7 +970,7 @@ impl MaybeReadable for Event { #[cfg(test)] let error_data = Readable::read(reader)?; let mut payment_hash = PaymentHash([0; 32]); - let mut rejected_by_dest = false; + let mut payment_failed_permanently = false; let mut network_update = None; let mut all_paths_failed = Some(true); let mut path: Option> = Some(vec![]); @@ -668,7 +980,7 @@ impl MaybeReadable for Event { read_tlv_fields!(reader, { (0, payment_hash, required), (1, network_update, ignorable), - (2, rejected_by_dest, required), + (2, payment_failed_permanently, required), (3, all_paths_failed, option), (5, path, vec_type), (7, short_channel_id, option), @@ -678,7 +990,7 @@ impl MaybeReadable for Event { Ok(Some(Event::PaymentPathFailed { payment_id, payment_hash, - rejected_by_dest, + payment_failed_permanently, network_update, all_paths_failed: all_paths_failed.unwrap(), path: path.unwrap(), @@ -695,7 +1007,7 @@ impl MaybeReadable for Event { 4u8 => Ok(None), 5u8 => { let f = || { - let mut outputs = VecReadWrapper(Vec::new()); + let mut outputs = WithoutLength(Vec::new()); read_tlv_fields!(reader, { (0, outputs, required), }); @@ -738,7 +1050,7 @@ impl MaybeReadable for Event { 11u8 => { let f = || { let mut channel_id = [0; 32]; - let mut transaction = Transaction{ version: 2, lock_time: 0, input: Vec::new(), output: Vec::new() }; + let mut transaction = Transaction{ version: 2, lock_time: PackedLockTime::ZERO, input: Vec::new(), output: Vec::new() }; read_tlv_fields!(reader, { (0, channel_id, required), (2, transaction, required), @@ -784,6 +1096,109 @@ impl MaybeReadable for Event { // Value 17 is used for `Event::OpenChannelRequest`. Ok(None) }, + 19u8 => { + let f = || { + let mut payment_hash = PaymentHash([0; 32]); + let mut purpose = None; + let mut amount_msat = 0; + read_tlv_fields!(reader, { + (0, payment_hash, required), + (2, purpose, ignorable), + (4, amount_msat, required), + }); + if purpose.is_none() { return Ok(None); } + Ok(Some(Event::PaymentClaimed { + payment_hash, + purpose: purpose.unwrap(), + amount_msat, + })) + }; + f() + }, + 21u8 => { + let f = || { + let mut payment_id = PaymentId([0; 32]); + let mut payment_hash = PaymentHash([0; 32]); + let mut path: Option> = Some(vec![]); + read_tlv_fields!(reader, { + (0, payment_id, required), + (2, payment_hash, required), + (4, path, vec_type), + }); + Ok(Some(Event::ProbeSuccessful { + payment_id, + payment_hash, + path: path.unwrap(), + })) + }; + f() + }, + 23u8 => { + let f = || { + let mut payment_id = PaymentId([0; 32]); + let mut payment_hash = PaymentHash([0; 32]); + let mut path: Option> = Some(vec![]); + let mut short_channel_id = None; + read_tlv_fields!(reader, { + (0, payment_id, required), + (2, payment_hash, required), + (4, path, vec_type), + (6, short_channel_id, option), + }); + Ok(Some(Event::ProbeFailed { + payment_id, + payment_hash, + path: path.unwrap(), + short_channel_id, + })) + }; + f() + }, + 25u8 => { + let f = || { + let mut prev_channel_id = [0; 32]; + let mut failed_next_destination_opt = None; + read_tlv_fields!(reader, { + (0, prev_channel_id, required), + (2, failed_next_destination_opt, ignorable), + }); + if let Some(failed_next_destination) = failed_next_destination_opt { + Ok(Some(Event::HTLCHandlingFailed { + prev_channel_id, + failed_next_destination, + })) + } else { + // If we fail to read a `failed_next_destination` assume it's because + // `MaybeReadable::read` returned `Ok(None)`, though it's also possible we + // were simply missing the field. + Ok(None) + } + }; + f() + }, + 27u8 => Ok(None), + 29u8 => { + let f = || { + let mut channel_id = [0; 32]; + let mut user_channel_id: u64 = 0; + let mut counterparty_node_id = OptionDeserWrapper(None); + let mut channel_type = OptionDeserWrapper(None); + read_tlv_fields!(reader, { + (0, channel_id, required), + (2, user_channel_id, required), + (4, counterparty_node_id, required), + (6, channel_type, required), + }); + + Ok(Some(Event::ChannelReady { + channel_id, + user_channel_id, + counterparty_node_id: counterparty_node_id.0.unwrap(), + channel_type: channel_type.0.unwrap() + })) + }; + f() + }, // Versions prior to 0.0.100 did not ignore odd types, instead returning InvalidValue. // Version 0.0.100 failed to properly ignore odd types, possibly resulting in corrupt // reads. @@ -838,12 +1253,12 @@ pub enum MessageSendEvent { /// The message which should be sent. msg: msgs::FundingSigned, }, - /// Used to indicate that a funding_locked message should be sent to the peer with the given node_id. - SendFundingLocked { + /// Used to indicate that a channel_ready message should be sent to the peer with the given node_id. + SendChannelReady { /// The node_id of the node which should receive these message(s) node_id: PublicKey, - /// The funding_locked message which should be sent. - msg: msgs::FundingLocked, + /// The channel_ready message which should be sent. + msg: msgs::ChannelReady, }, /// Used to indicate that an announcement_signatures message should be sent to the peer with the given node_id. SendAnnouncementSignatures { @@ -888,25 +1303,32 @@ pub enum MessageSendEvent { /// The message which should be sent. msg: msgs::ChannelReestablish, }, + /// Used to send a channel_announcement and channel_update to a specific peer, likely on + /// initial connection to ensure our peers know about our channels. + SendChannelAnnouncement { + /// The node_id of the node which should receive this message + node_id: PublicKey, + /// The channel_announcement which should be sent. + msg: msgs::ChannelAnnouncement, + /// The followup channel_update which should be sent. + update_msg: msgs::ChannelUpdate, + }, /// Used to indicate that a channel_announcement and channel_update should be broadcast to all /// peers (except the peer with node_id either msg.contents.node_id_1 or msg.contents.node_id_2). /// - /// Note that after doing so, you very likely (unless you did so very recently) want to call - /// ChannelManager::broadcast_node_announcement to trigger a BroadcastNodeAnnouncement event. - /// This ensures that any nodes which see our channel_announcement also have a relevant + /// Note that after doing so, you very likely (unless you did so very recently) want to + /// broadcast a node_announcement (e.g. via [`PeerManager::broadcast_node_announcement`]). This + /// ensures that any nodes which see our channel_announcement also have a relevant /// node_announcement, including relevant feature flags which may be important for routing /// through or to us. + /// + /// [`PeerManager::broadcast_node_announcement`]: crate::ln::peer_handler::PeerManager::broadcast_node_announcement BroadcastChannelAnnouncement { /// The channel_announcement which should be sent. msg: msgs::ChannelAnnouncement, /// The followup channel_update which should be sent. update_msg: msgs::ChannelUpdate, }, - /// Used to indicate that a node_announcement should be broadcast to all peers. - BroadcastNodeAnnouncement { - /// The node_announcement which should be sent. - msg: msgs::NodeAnnouncement, - }, /// Used to indicate that a channel_update should be broadcast to all peers. BroadcastChannelUpdate { /// The channel_update which should be sent. @@ -968,17 +1390,29 @@ pub trait MessageSendEventsProvider { fn get_and_clear_pending_msg_events(&self) -> Vec; } +/// A trait indicating an object may generate onion messages to send +pub trait OnionMessageProvider { + /// Gets the next pending onion message for the peer with the given node id. + fn next_onion_message_for_peer(&self, peer_node_id: PublicKey) -> Option; +} + /// A trait indicating an object may generate events. /// /// Events are processed by passing an [`EventHandler`] to [`process_pending_events`]. /// /// # Requirements /// -/// See [`process_pending_events`] for requirements around event processing. -/// /// When using this trait, [`process_pending_events`] will call [`handle_event`] for each pending -/// event since the last invocation. The handler must either act upon the event immediately -/// or preserve it for later handling. +/// event since the last invocation. +/// +/// In order to ensure no [`Event`]s are lost, implementors of this trait will persist [`Event`]s +/// and replay any unhandled events on startup. An [`Event`] is considered handled when +/// [`process_pending_events`] returns, thus handlers MUST fully handle [`Event`]s and persist any +/// relevant changes to disk *before* returning. +/// +/// Further, because an application may crash between an [`Event`] being handled and the +/// implementor of this trait being re-serialized, [`Event`] handling must be idempotent - in +/// effect, [`Event`]s may be replayed. /// /// Note, handlers may call back into the provider and thus deadlocking must be avoided. Be sure to /// consult the provider's documentation on the implication of processing events and how a handler @@ -995,9 +1429,7 @@ pub trait MessageSendEventsProvider { pub trait EventsProvider { /// Processes any events generated since the last call using the given event handler. /// - /// Subsequent calls must only process new events. However, handlers must be capable of handling - /// duplicate events across process restarts. This may occur if the provider was recovered from - /// an old state (i.e., it hadn't been successfully persisted after processing pending events). + /// See the trait-level documentation for requirements. fn process_pending_events(&self, handler: H) where H::Target: EventHandler; }