]> git.bitcoin.ninja Git - rust-lightning/commitdiff
Merge pull request #674 from TheBlueMatt/2020-08-keyif-rand-names
authorMatt Corallo <649246+TheBlueMatt@users.noreply.github.com>
Wed, 26 Aug 2020 15:07:58 +0000 (08:07 -0700)
committerGitHub <noreply@github.com>
Wed, 26 Aug 2020 15:07:58 +0000 (08:07 -0700)
Simplify + clarify random-bytes-fetching from KeysInterface

fuzz/src/chanmon_consistency.rs
lightning/src/ln/channel.rs
lightning/src/ln/channelmanager.rs
lightning/src/ln/channelmonitor.rs
lightning/src/ln/functional_tests.rs
lightning/src/ln/msgs.rs
lightning/src/ln/reorg_tests.rs
lightning/src/routing/router.rs
lightning/src/util/test_utils.rs

index 16e8cdf65cf791f34ec47dcc63d25d4f2f180b72..65f721e484032c1965aea8c2a54141ec63e5e063 100644 (file)
@@ -34,7 +34,7 @@ use lightning::chain::transaction::OutPoint;
 use lightning::chain::chaininterface::{BroadcasterInterface,ConfirmationTarget,ChainListener,FeeEstimator,ChainWatchInterfaceUtil,ChainWatchInterface};
 use lightning::chain::keysinterface::{KeysInterface, InMemoryChannelKeys};
 use lightning::ln::channelmonitor;
-use lightning::ln::channelmonitor::{ChannelMonitor, ChannelMonitorUpdateErr, HTLCUpdate};
+use lightning::ln::channelmonitor::{ChannelMonitor, ChannelMonitorUpdateErr, MonitorEvent};
 use lightning::ln::channelmanager::{ChannelManager, PaymentHash, PaymentPreimage, PaymentSecret, ChannelManagerReadArgs};
 use lightning::ln::features::{ChannelFeatures, InitFeatures, NodeFeatures};
 use lightning::ln::msgs::{CommitmentUpdate, ChannelMessageHandler, ErrorAction, UpdateAddHTLC, Init};
@@ -135,8 +135,8 @@ impl channelmonitor::ManyChannelMonitor for TestChannelMonitor {
                self.update_ret.lock().unwrap().clone()
        }
 
-       fn get_and_clear_pending_htlcs_updated(&self) -> Vec<HTLCUpdate> {
-               return self.simple_monitor.get_and_clear_pending_htlcs_updated();
+       fn get_and_clear_pending_monitor_events(&self) -> Vec<MonitorEvent> {
+               return self.simple_monitor.get_and_clear_pending_monitor_events();
        }
 }
 
index 6079c47ee870e8d0d2e74e9d72cd27a31e074b6f..f7f138274331e1b167bb2158cd952c77e7d257c5 100644 (file)
@@ -386,9 +386,6 @@ pub(super) struct Channel<ChanSigner: ChannelKeys> {
 
        their_shutdown_scriptpubkey: Option<Script>,
 
-       /// Used exclusively to broadcast the latest local state, mostly a historical quirk that this
-       /// is here:
-       channel_monitor: Option<ChannelMonitor<ChanSigner>>,
        commitment_secrets: CounterpartyCommitmentSecrets,
 
        network_sync: UpdateStatus,
@@ -557,7 +554,6 @@ impl<ChanSigner: ChannelKeys> Channel<ChanSigner> {
 
                        their_shutdown_scriptpubkey: None,
 
-                       channel_monitor: None,
                        commitment_secrets: CounterpartyCommitmentSecrets::new(),
 
                        network_sync: UpdateStatus::Fresh,
@@ -786,7 +782,6 @@ impl<ChanSigner: ChannelKeys> Channel<ChanSigner> {
 
                        their_shutdown_scriptpubkey,
 
-                       channel_monitor: None,
                        commitment_secrets: CounterpartyCommitmentSecrets::new(),
 
                        network_sync: UpdateStatus::Fresh,
@@ -1222,7 +1217,6 @@ impl<ChanSigner: ChannelKeys> Channel<ChanSigner> {
                                payment_preimage: payment_preimage_arg.clone(),
                        }],
                };
-               self.channel_monitor.as_mut().unwrap().update_monitor_ooo(monitor_update.clone(), logger).unwrap();
 
                if (self.channel_state & (ChannelState::AwaitingRemoteRevoke as u32 | ChannelState::PeerDisconnected as u32 | ChannelState::MonitorUpdateFailed as u32)) != 0 {
                        for pending_update in self.holding_cell_htlc_updates.iter() {
@@ -1552,7 +1546,6 @@ impl<ChanSigner: ChannelKeys> Channel<ChanSigner> {
                        } }
                }
 
-               self.channel_monitor = Some(create_monitor!());
                let channel_monitor = create_monitor!();
 
                self.channel_state = ChannelState::FundingSent as u32;
@@ -1618,7 +1611,6 @@ impl<ChanSigner: ChannelKeys> Channel<ChanSigner> {
                        } }
                }
 
-               self.channel_monitor = Some(create_monitor!());
                let channel_monitor = create_monitor!();
 
                assert_eq!(self.channel_state & (ChannelState::MonitorUpdateFailed as u32), 0); // We have no had any monitor(s) yet to fail update!
@@ -2060,7 +2052,6 @@ impl<ChanSigner: ChannelKeys> Channel<ChanSigner> {
                                htlc_outputs: htlcs_and_sigs
                        }]
                };
-               self.channel_monitor.as_mut().unwrap().update_monitor_ooo(monitor_update.clone(), logger).unwrap();
 
                for htlc in self.pending_inbound_htlcs.iter_mut() {
                        let new_forward = if let &InboundHTLCState::RemoteAnnounced(ref forward_info) = &htlc.state {
@@ -2280,7 +2271,6 @@ impl<ChanSigner: ChannelKeys> Channel<ChanSigner> {
                                secret: msg.per_commitment_secret,
                        }],
                };
-               self.channel_monitor.as_mut().unwrap().update_monitor_ooo(monitor_update.clone(), logger).unwrap();
 
                // Update state now that we've passed all the can-fail calls...
                // (note that we may still fail to generate the new commitment_signed message, but that's
@@ -3115,14 +3105,6 @@ impl<ChanSigner: ChannelKeys> Channel<ChanSigner> {
                self.user_id
        }
 
-       /// May only be called after funding has been initiated (ie is_funding_initiated() is true)
-       pub fn channel_monitor(&mut self) -> &mut ChannelMonitor<ChanSigner> {
-               if self.channel_state < ChannelState::FundingSent as u32 {
-                       panic!("Can't get a channel monitor until funding has been created");
-               }
-               self.channel_monitor.as_mut().unwrap()
-       }
-
        /// Guaranteed to be Some after both FundingLocked messages have been exchanged (and, thus,
        /// is_usable() returns true).
        /// Allowed in any state (including after shutdown)
@@ -3397,9 +3379,6 @@ impl<ChanSigner: ChannelKeys> Channel<ChanSigner> {
                if header.bitcoin_hash() != self.last_block_connected {
                        self.last_block_connected = header.bitcoin_hash();
                        self.update_time_counter = cmp::max(self.update_time_counter, header.time);
-                       if let Some(channel_monitor) = self.channel_monitor.as_mut() {
-                               channel_monitor.last_block_hash = self.last_block_connected;
-                       }
                        if self.funding_tx_confirmations > 0 {
                                if self.funding_tx_confirmations == self.minimum_depth as u64 {
                                        let need_commitment_update = if non_shutdown_state == ChannelState::FundingSent as u32 {
@@ -3458,9 +3437,6 @@ impl<ChanSigner: ChannelKeys> Channel<ChanSigner> {
                        self.funding_tx_confirmations = self.minimum_depth as u64 - 1;
                }
                self.last_block_connected = header.bitcoin_hash();
-               if let Some(channel_monitor) = self.channel_monitor.as_mut() {
-                       channel_monitor.last_block_hash = self.last_block_connected;
-               }
                false
        }
 
@@ -3871,7 +3847,6 @@ impl<ChanSigner: ChannelKeys> Channel<ChanSigner> {
                                their_revocation_point: self.their_cur_commitment_point.unwrap()
                        }]
                };
-               self.channel_monitor.as_mut().unwrap().update_monitor_ooo(monitor_update.clone(), logger).unwrap();
                self.channel_state |= ChannelState::AwaitingRemoteRevoke as u32;
                Ok((res, monitor_update))
        }
@@ -4242,8 +4217,6 @@ impl<ChanSigner: ChannelKeys + Writeable> Writeable for Channel<ChanSigner> {
                self.their_shutdown_scriptpubkey.write(writer)?;
 
                self.commitment_secrets.write(writer)?;
-
-               self.channel_monitor.as_ref().unwrap().write_for_disk(writer)?;
                Ok(())
        }
 }
@@ -4398,13 +4371,6 @@ impl<ChanSigner: ChannelKeys + Readable> Readable for Channel<ChanSigner> {
                let their_shutdown_scriptpubkey = Readable::read(reader)?;
                let commitment_secrets = Readable::read(reader)?;
 
-               let (monitor_last_block, channel_monitor) = Readable::read(reader)?;
-               // We drop the ChannelMonitor's last block connected hash cause we don't actually bother
-               // doing full block connection operations on the internal ChannelMonitor copies
-               if monitor_last_block != last_block_connected {
-                       return Err(DecodeError::InvalidValue);
-               }
-
                Ok(Channel {
                        user_id,
 
@@ -4476,7 +4442,6 @@ impl<ChanSigner: ChannelKeys + Readable> Readable for Channel<ChanSigner> {
 
                        their_shutdown_scriptpubkey,
 
-                       channel_monitor: Some(channel_monitor),
                        commitment_secrets,
 
                        network_sync: UpdateStatus::Fresh,
index ccd0b00444ae3c4f5d6d48cb74933013ea6faa3f..fdbbb43da3dd104ee5bd6699937af92df6dc4f7d 100644 (file)
@@ -38,7 +38,7 @@ use bitcoin::secp256k1;
 use chain::chaininterface::{BroadcasterInterface,ChainListener,FeeEstimator};
 use chain::transaction::OutPoint;
 use ln::channel::{Channel, ChannelError};
-use ln::channelmonitor::{ChannelMonitor, ChannelMonitorUpdate, ChannelMonitorUpdateErr, ManyChannelMonitor, HTLC_FAIL_BACK_BUFFER, CLTV_CLAIM_BUFFER, LATENCY_GRACE_PERIOD_BLOCKS, ANTI_REORG_DELAY};
+use ln::channelmonitor::{ChannelMonitor, ChannelMonitorUpdate, ChannelMonitorUpdateErr, ManyChannelMonitor, HTLC_FAIL_BACK_BUFFER, CLTV_CLAIM_BUFFER, LATENCY_GRACE_PERIOD_BLOCKS, ANTI_REORG_DELAY, MonitorEvent};
 use ln::features::{InitFeatures, NodeFeatures};
 use routing::router::{Route, RouteHop};
 use ln::msgs;
@@ -2967,6 +2967,48 @@ impl<ChanSigner: ChannelKeys, M: Deref, T: Deref, K: Deref, F: Deref, L: Deref>
                        Err(e) => { Err(APIError::APIMisuseError { err: e.err })}
                }
        }
+
+       /// Process pending events from the ManyChannelMonitor.
+       fn process_pending_monitor_events(&self) {
+               let mut failed_channels = Vec::new();
+               {
+                       for monitor_event in self.monitor.get_and_clear_pending_monitor_events() {
+                               match monitor_event {
+                                       MonitorEvent::HTLCEvent(htlc_update) => {
+                                               if let Some(preimage) = htlc_update.payment_preimage {
+                                                       log_trace!(self.logger, "Claiming HTLC with preimage {} from our monitor", log_bytes!(preimage.0));
+                                                       self.claim_funds_internal(self.channel_state.lock().unwrap(), htlc_update.source, preimage);
+                                               } else {
+                                                       log_trace!(self.logger, "Failing HTLC with hash {} from our monitor", log_bytes!(htlc_update.payment_hash.0));
+                                                       self.fail_htlc_backwards_internal(self.channel_state.lock().unwrap(), htlc_update.source, &htlc_update.payment_hash, HTLCFailReason::Reason { failure_code: 0x4000 | 8, data: Vec::new() });
+                                               }
+                                       },
+                                       MonitorEvent::CommitmentTxBroadcasted(funding_outpoint) => {
+                                               let mut channel_lock = self.channel_state.lock().unwrap();
+                                               let channel_state = &mut *channel_lock;
+                                               let by_id = &mut channel_state.by_id;
+                                               let short_to_id = &mut channel_state.short_to_id;
+                                               let pending_msg_events = &mut channel_state.pending_msg_events;
+                                               if let Some(mut chan) = by_id.remove(&funding_outpoint.to_channel_id()) {
+                                                       if let Some(short_id) = chan.get_short_channel_id() {
+                                                               short_to_id.remove(&short_id);
+                                                       }
+                                                       failed_channels.push(chan.force_shutdown(false));
+                                                       if let Ok(update) = self.get_channel_update(&chan) {
+                                                               pending_msg_events.push(events::MessageSendEvent::BroadcastChannelUpdate {
+                                                                       msg: update
+                                                               });
+                                                       }
+                                               }
+                                       },
+                               }
+                       }
+               }
+
+               for failure in failed_channels.drain(..) {
+                       self.finish_force_close_channel(failure);
+               }
+       }
 }
 
 impl<ChanSigner: ChannelKeys, M: Deref, T: Deref, K: Deref, F: Deref, L: Deref> events::MessageSendEventsProvider for ChannelManager<ChanSigner, M, T, K, F, L>
@@ -2977,21 +3019,9 @@ impl<ChanSigner: ChannelKeys, M: Deref, T: Deref, K: Deref, F: Deref, L: Deref>
                                L::Target: Logger,
 {
        fn get_and_clear_pending_msg_events(&self) -> Vec<events::MessageSendEvent> {
-               // TODO: Event release to users and serialization is currently race-y: it's very easy for a
-               // user to serialize a ChannelManager with pending events in it and lose those events on
-               // restart. This is doubly true for the fail/fulfill-backs from monitor events!
-               {
-                       //TODO: This behavior should be documented.
-                       for htlc_update in self.monitor.get_and_clear_pending_htlcs_updated() {
-                               if let Some(preimage) = htlc_update.payment_preimage {
-                                       log_trace!(self.logger, "Claiming HTLC with preimage {} from our monitor", log_bytes!(preimage.0));
-                                       self.claim_funds_internal(self.channel_state.lock().unwrap(), htlc_update.source, preimage);
-                               } else {
-                                       log_trace!(self.logger, "Failing HTLC with hash {} from our monitor", log_bytes!(htlc_update.payment_hash.0));
-                                       self.fail_htlc_backwards_internal(self.channel_state.lock().unwrap(), htlc_update.source, &htlc_update.payment_hash, HTLCFailReason::Reason { failure_code: 0x4000 | 8, data: Vec::new() });
-                               }
-                       }
-               }
+               //TODO: This behavior should be documented. It's non-intuitive that we query
+               // ChannelMonitors when clearing other events.
+               self.process_pending_monitor_events();
 
                let mut ret = Vec::new();
                let mut channel_state = self.channel_state.lock().unwrap();
@@ -3008,21 +3038,9 @@ impl<ChanSigner: ChannelKeys, M: Deref, T: Deref, K: Deref, F: Deref, L: Deref>
                                L::Target: Logger,
 {
        fn get_and_clear_pending_events(&self) -> Vec<events::Event> {
-               // TODO: Event release to users and serialization is currently race-y: it's very easy for a
-               // user to serialize a ChannelManager with pending events in it and lose those events on
-               // restart. This is doubly true for the fail/fulfill-backs from monitor events!
-               {
-                       //TODO: This behavior should be documented.
-                       for htlc_update in self.monitor.get_and_clear_pending_htlcs_updated() {
-                               if let Some(preimage) = htlc_update.payment_preimage {
-                                       log_trace!(self.logger, "Claiming HTLC with preimage {} from our monitor", log_bytes!(preimage.0));
-                                       self.claim_funds_internal(self.channel_state.lock().unwrap(), htlc_update.source, preimage);
-                               } else {
-                                       log_trace!(self.logger, "Failing HTLC with hash {} from our monitor", log_bytes!(htlc_update.payment_hash.0));
-                                       self.fail_htlc_backwards_internal(self.channel_state.lock().unwrap(), htlc_update.source, &htlc_update.payment_hash, HTLCFailReason::Reason { failure_code: 0x4000 | 8, data: Vec::new() });
-                               }
-                       }
-               }
+               //TODO: This behavior should be documented. It's non-intuitive that we query
+               // ChannelMonitors when clearing other events.
+               self.process_pending_monitor_events();
 
                let mut ret = Vec::new();
                let mut pending_events = self.pending_events.lock().unwrap();
@@ -3105,21 +3123,6 @@ impl<ChanSigner: ChannelKeys, M: Deref + Sync + Send, T: Deref + Sync + Send, K:
                                                }
                                        }
                                }
-                               if channel.is_funding_initiated() && channel.channel_monitor().would_broadcast_at_height(height, &self.logger) {
-                                       if let Some(short_id) = channel.get_short_channel_id() {
-                                               short_to_id.remove(&short_id);
-                                       }
-                                       // If would_broadcast_at_height() is true, the channel_monitor will broadcast
-                                       // the latest local tx for us, so we should skip that here (it doesn't really
-                                       // hurt anything, but does make tests a bit simpler).
-                                       failed_channels.push(channel.force_shutdown(false));
-                                       if let Ok(update) = self.get_channel_update(&channel) {
-                                               pending_msg_events.push(events::MessageSendEvent::BroadcastChannelUpdate {
-                                                       msg: update
-                                               });
-                                       }
-                                       return false;
-                               }
                                true
                        });
 
index b69636e0797b5ef9327da195f785474127d92d0f..060e88faa209f7cbacec1ef1228d0d1e7d68bc1e 100644 (file)
@@ -148,6 +148,16 @@ pub enum ChannelMonitorUpdateErr {
 #[derive(Debug)]
 pub struct MonitorUpdateError(pub &'static str);
 
+/// An event to be processed by the ChannelManager.
+#[derive(PartialEq)]
+pub enum MonitorEvent {
+       /// A monitor event containing an HTLCUpdate.
+       HTLCEvent(HTLCUpdate),
+
+       /// A monitor event that the Channel's commitment transaction was broadcasted.
+       CommitmentTxBroadcasted(OutPoint),
+}
+
 /// Simple structure send back by ManyChannelMonitor in case of HTLC detected onchain from a
 /// forward channel and from which info are needed to update HTLC in a backward channel.
 #[derive(Clone, PartialEq)]
@@ -292,12 +302,12 @@ impl<ChanSigner: ChannelKeys, T: Deref + Sync + Send, F: Deref + Sync + Send, L:
                }
        }
 
-       fn get_and_clear_pending_htlcs_updated(&self) -> Vec<HTLCUpdate> {
-               let mut pending_htlcs_updated = Vec::new();
+       fn get_and_clear_pending_monitor_events(&self) -> Vec<MonitorEvent> {
+               let mut pending_monitor_events = Vec::new();
                for chan in self.monitors.lock().unwrap().values_mut() {
-                       pending_htlcs_updated.append(&mut chan.get_and_clear_pending_htlcs_updated());
+                       pending_monitor_events.append(&mut chan.get_and_clear_pending_monitor_events());
                }
-               pending_htlcs_updated
+               pending_monitor_events
        }
 }
 
@@ -729,7 +739,7 @@ impl Readable for ChannelMonitorUpdateStep {
 /// information and are actively monitoring the chain.
 ///
 /// Pending Events or updated HTLCs which have not yet been read out by
-/// get_and_clear_pending_htlcs_updated or get_and_clear_pending_events are serialized to disk and
+/// get_and_clear_pending_monitor_events or get_and_clear_pending_events are serialized to disk and
 /// reloaded at deserialize-time. Thus, you must ensure that, when handling events, all events
 /// gotten are fully handled before re-serializing the new state.
 pub struct ChannelMonitor<ChanSigner: ChannelKeys> {
@@ -784,7 +794,7 @@ pub struct ChannelMonitor<ChanSigner: ChannelKeys> {
 
        payment_preimages: HashMap<PaymentHash, PaymentPreimage>,
 
-       pending_htlcs_updated: Vec<HTLCUpdate>,
+       pending_monitor_events: Vec<MonitorEvent>,
        pending_events: Vec<events::Event>,
 
        // Used to track onchain events, i.e transactions parts of channels confirmed on chain, on which
@@ -818,7 +828,7 @@ pub struct ChannelMonitor<ChanSigner: ChannelKeys> {
        // (we do *not*, however, update them in update_monitor to ensure any local user copies keep
        // their last_block_hash from its state and not based on updated copies that didn't run through
        // the full block_connected).
-       pub(crate) last_block_hash: BlockHash,
+       last_block_hash: BlockHash,
        secp_ctx: Secp256k1<secp256k1::All>, //TODO: dedup this a bit...
 }
 
@@ -881,9 +891,9 @@ pub trait ManyChannelMonitor: Send + Sync {
        /// with success or failure.
        ///
        /// You should probably just call through to
-       /// ChannelMonitor::get_and_clear_pending_htlcs_updated() for each ChannelMonitor and return
+       /// ChannelMonitor::get_and_clear_pending_monitor_events() for each ChannelMonitor and return
        /// the full list.
-       fn get_and_clear_pending_htlcs_updated(&self) -> Vec<HTLCUpdate>;
+       fn get_and_clear_pending_monitor_events(&self) -> Vec<MonitorEvent>;
 }
 
 #[cfg(any(test, feature = "fuzztarget"))]
@@ -914,7 +924,7 @@ impl<ChanSigner: ChannelKeys> PartialEq for ChannelMonitor<ChanSigner> {
                        self.current_local_commitment_number != other.current_local_commitment_number ||
                        self.current_local_commitment_tx != other.current_local_commitment_tx ||
                        self.payment_preimages != other.payment_preimages ||
-                       self.pending_htlcs_updated != other.pending_htlcs_updated ||
+                       self.pending_monitor_events != other.pending_monitor_events ||
                        self.pending_events.len() != other.pending_events.len() || // We trust events to round-trip properly
                        self.onchain_events_waiting_threshold_conf != other.onchain_events_waiting_threshold_conf ||
                        self.outputs_to_watch != other.outputs_to_watch ||
@@ -1070,9 +1080,15 @@ impl<ChanSigner: ChannelKeys + Writeable> ChannelMonitor<ChanSigner> {
                        writer.write_all(&payment_preimage.0[..])?;
                }
 
-               writer.write_all(&byte_utils::be64_to_array(self.pending_htlcs_updated.len() as u64))?;
-               for data in self.pending_htlcs_updated.iter() {
-                       data.write(writer)?;
+               writer.write_all(&byte_utils::be64_to_array(self.pending_monitor_events.len() as u64))?;
+               for event in self.pending_monitor_events.iter() {
+                       match event {
+                               MonitorEvent::HTLCEvent(upd) => {
+                                       0u8.write(writer)?;
+                                       upd.write(writer)?;
+                               },
+                               MonitorEvent::CommitmentTxBroadcasted(_) => 1u8.write(writer)?
+                       }
                }
 
                writer.write_all(&byte_utils::be64_to_array(self.pending_events.len() as u64))?;
@@ -1187,7 +1203,7 @@ impl<ChanSigner: ChannelKeys> ChannelMonitor<ChanSigner> {
                        current_local_commitment_number: 0xffff_ffff_ffff - ((((local_tx_sequence & 0xffffff) << 3*8) | (local_tx_locktime as u64 & 0xffffff)) ^ commitment_transaction_number_obscure_factor),
 
                        payment_preimages: HashMap::new(),
-                       pending_htlcs_updated: Vec::new(),
+                       pending_monitor_events: Vec::new(),
                        pending_events: Vec::new(),
 
                        onchain_events_waiting_threshold_conf: HashMap::new(),
@@ -1351,27 +1367,7 @@ impl<ChanSigner: ChannelKeys> ChannelMonitor<ChanSigner> {
                for tx in self.get_latest_local_commitment_txn(logger).iter() {
                        broadcaster.broadcast_transaction(tx);
                }
-       }
-
-       /// Used in Channel to cheat wrt the update_ids since it plays games, will be removed soon!
-       pub(super) fn update_monitor_ooo<L: Deref>(&mut self, mut updates: ChannelMonitorUpdate, logger: &L) -> Result<(), MonitorUpdateError> where L::Target: Logger {
-               for update in updates.updates.drain(..) {
-                       match update {
-                               ChannelMonitorUpdateStep::LatestLocalCommitmentTXInfo { commitment_tx, htlc_outputs } => {
-                                       if self.lockdown_from_offchain { panic!(); }
-                                       self.provide_latest_local_commitment_tx_info(commitment_tx, htlc_outputs)?
-                               },
-                               ChannelMonitorUpdateStep::LatestRemoteCommitmentTXInfo { unsigned_commitment_tx, htlc_outputs, commitment_number, their_revocation_point } =>
-                                       self.provide_latest_remote_commitment_tx_info(&unsigned_commitment_tx, htlc_outputs, commitment_number, their_revocation_point, logger),
-                               ChannelMonitorUpdateStep::PaymentPreimage { payment_preimage } =>
-                                       self.provide_payment_preimage(&PaymentHash(Sha256::hash(&payment_preimage.0[..]).into_inner()), &payment_preimage),
-                               ChannelMonitorUpdateStep::CommitmentSecret { idx, secret } =>
-                                       self.provide_secret(idx, secret)?,
-                               ChannelMonitorUpdateStep::ChannelForceClosed { .. } => {},
-                       }
-               }
-               self.latest_update_id = updates.update_id;
-               Ok(())
+               self.pending_monitor_events.push(MonitorEvent::CommitmentTxBroadcasted(self.funding_info.0));
        }
 
        /// Updates a ChannelMonitor on the basis of some new information provided by the Channel
@@ -1443,10 +1439,10 @@ impl<ChanSigner: ChannelKeys> ChannelMonitor<ChanSigner> {
        }
 
        /// Get the list of HTLCs who's status has been updated on chain. This should be called by
-       /// ChannelManager via ManyChannelMonitor::get_and_clear_pending_htlcs_updated().
-       pub fn get_and_clear_pending_htlcs_updated(&mut self) -> Vec<HTLCUpdate> {
+       /// ChannelManager via ManyChannelMonitor::get_and_clear_pending_monitor_events().
+       pub fn get_and_clear_pending_monitor_events(&mut self) -> Vec<MonitorEvent> {
                let mut ret = Vec::new();
-               mem::swap(&mut ret, &mut self.pending_htlcs_updated);
+               mem::swap(&mut ret, &mut self.pending_monitor_events);
                ret
        }
 
@@ -1938,7 +1934,9 @@ impl<ChanSigner: ChannelKeys> ChannelMonitor<ChanSigner> {
                        claimable_outpoints.push(ClaimRequest { absolute_timelock: height, aggregable: false, outpoint: BitcoinOutPoint { txid: self.funding_info.0.txid.clone(), vout: self.funding_info.0.index as u32 }, witness_data: InputMaterial::Funding { funding_redeemscript: self.funding_redeemscript.clone() }});
                }
                if should_broadcast {
+                       self.pending_monitor_events.push(MonitorEvent::CommitmentTxBroadcasted(self.funding_info.0));
                        if let Some(commitment_tx) = self.onchain_tx_handler.get_fully_signed_local_tx(&self.funding_redeemscript) {
+                               self.local_tx_signed = true;
                                let (mut new_outpoints, new_outputs, _) = self.broadcast_by_local_state(&commitment_tx, &self.current_local_commitment_tx);
                                if !new_outputs.is_empty() {
                                        watch_outputs.push((self.current_local_commitment_tx.txid.clone(), new_outputs));
@@ -1951,11 +1949,11 @@ impl<ChanSigner: ChannelKeys> ChannelMonitor<ChanSigner> {
                                match ev {
                                        OnchainEvent::HTLCUpdate { htlc_update } => {
                                                log_trace!(logger, "HTLC {} failure update has got enough confirmations to be passed upstream", log_bytes!((htlc_update.1).0));
-                                               self.pending_htlcs_updated.push(HTLCUpdate {
+                                               self.pending_monitor_events.push(MonitorEvent::HTLCEvent(HTLCUpdate {
                                                        payment_hash: htlc_update.1,
                                                        payment_preimage: None,
                                                        source: htlc_update.0,
-                                               });
+                                               }));
                                        },
                                        OnchainEvent::MaturingOutput { descriptor } => {
                                                log_trace!(logger, "Descriptor {} has got enough confirmations to be passed upstream", log_spendable!(descriptor));
@@ -1966,6 +1964,7 @@ impl<ChanSigner: ChannelKeys> ChannelMonitor<ChanSigner> {
                                }
                        }
                }
+
                self.onchain_tx_handler.block_connected(txn_matched, claimable_outpoints, height, &*broadcaster, &*fee_estimator, &*logger);
 
                self.last_block_hash = block_hash.clone();
@@ -1993,7 +1992,7 @@ impl<ChanSigner: ChannelKeys> ChannelMonitor<ChanSigner> {
                self.last_block_hash = block_hash.clone();
        }
 
-       pub(super) fn would_broadcast_at_height<L: Deref>(&self, height: u32, logger: &L) -> bool where L::Target: Logger {
+       fn would_broadcast_at_height<L: Deref>(&self, height: u32, logger: &L) -> bool where L::Target: Logger {
                // We need to consider all HTLCs which are:
                //  * in any unrevoked remote commitment transaction, as they could broadcast said
                //    transactions and we'd end up in a race, or
@@ -2151,22 +2150,26 @@ impl<ChanSigner: ChannelKeys> ChannelMonitor<ChanSigner> {
                        if let Some((source, payment_hash)) = payment_data {
                                let mut payment_preimage = PaymentPreimage([0; 32]);
                                if accepted_preimage_claim {
-                                       if !self.pending_htlcs_updated.iter().any(|update| update.source == source) {
+                                       if !self.pending_monitor_events.iter().any(
+                                               |update| if let &MonitorEvent::HTLCEvent(ref upd) = update { upd.source == source } else { false }) {
                                                payment_preimage.0.copy_from_slice(&input.witness[3]);
-                                               self.pending_htlcs_updated.push(HTLCUpdate {
+                                               self.pending_monitor_events.push(MonitorEvent::HTLCEvent(HTLCUpdate {
                                                        source,
                                                        payment_preimage: Some(payment_preimage),
                                                        payment_hash
-                                               });
+                                               }));
                                        }
                                } else if offered_preimage_claim {
-                                       if !self.pending_htlcs_updated.iter().any(|update| update.source == source) {
+                                       if !self.pending_monitor_events.iter().any(
+                                               |update| if let &MonitorEvent::HTLCEvent(ref upd) = update {
+                                                       upd.source == source
+                                               } else { false }) {
                                                payment_preimage.0.copy_from_slice(&input.witness[1]);
-                                               self.pending_htlcs_updated.push(HTLCUpdate {
+                                               self.pending_monitor_events.push(MonitorEvent::HTLCEvent(HTLCUpdate {
                                                        source,
                                                        payment_preimage: Some(payment_preimage),
                                                        payment_hash
-                                               });
+                                               }));
                                        }
                                } else {
                                        log_info!(logger, "Failing HTLC with payment_hash {} timeout by a spend tx, waiting for confirmation (at height{})", log_bytes!(payment_hash.0), height + ANTI_REORG_DELAY - 1);
@@ -2422,10 +2425,15 @@ impl<ChanSigner: ChannelKeys + Readable> Readable for (BlockHash, ChannelMonitor
                        }
                }
 
-               let pending_htlcs_updated_len: u64 = Readable::read(reader)?;
-               let mut pending_htlcs_updated = Vec::with_capacity(cmp::min(pending_htlcs_updated_len as usize, MAX_ALLOC_SIZE / (32 + 8*3)));
-               for _ in 0..pending_htlcs_updated_len {
-                       pending_htlcs_updated.push(Readable::read(reader)?);
+               let pending_monitor_events_len: u64 = Readable::read(reader)?;
+               let mut pending_monitor_events = Vec::with_capacity(cmp::min(pending_monitor_events_len as usize, MAX_ALLOC_SIZE / (32 + 8*3)));
+               for _ in 0..pending_monitor_events_len {
+                       let ev = match <u8 as Readable>::read(reader)? {
+                               0 => MonitorEvent::HTLCEvent(Readable::read(reader)?),
+                               1 => MonitorEvent::CommitmentTxBroadcasted(funding_info.0),
+                               _ => return Err(DecodeError::InvalidValue)
+                       };
+                       pending_monitor_events.push(ev);
                }
 
                let pending_events_len: u64 = Readable::read(reader)?;
@@ -2516,7 +2524,7 @@ impl<ChanSigner: ChannelKeys + Readable> Readable for (BlockHash, ChannelMonitor
                        current_local_commitment_number,
 
                        payment_preimages,
-                       pending_htlcs_updated,
+                       pending_monitor_events,
                        pending_events,
 
                        onchain_events_waiting_threshold_conf,
index d21f558a65f5c365414171005167ea82ad55de84..4b111f2af455b1a3842965cad2941786ec608383 100644 (file)
@@ -2420,13 +2420,21 @@ fn channel_monitor_network_test() {
        // CLTV expires at TEST_FINAL_CLTV + 1 (current height) + 1 (added in send_payment for
        // buffer space).
 
-       {
+       let (close_chan_update_1, close_chan_update_2) = {
                let mut header = BlockHeader { version: 0x20000000, prev_blockhash: Default::default(), merkle_root: Default::default(), time: 42, bits: 42, nonce: 42 };
                nodes[3].block_notifier.block_connected_checked(&header, 2, &Vec::new()[..], &[0; 0]);
                for i in 3..TEST_FINAL_CLTV + 2 + LATENCY_GRACE_PERIOD_BLOCKS + 1 {
                        header = BlockHeader { version: 0x20000000, prev_blockhash: header.bitcoin_hash(), merkle_root: Default::default(), time: 42, bits: 42, nonce: 42 };
                        nodes[3].block_notifier.block_connected_checked(&header, i, &Vec::new()[..], &[0; 0]);
                }
+               let events = nodes[3].node.get_and_clear_pending_msg_events();
+               assert_eq!(events.len(), 1);
+               let close_chan_update_1 = match events[0] {
+                       MessageSendEvent::BroadcastChannelUpdate { ref msg } => {
+                               msg.clone()
+                       },
+                       _ => panic!("Unexpected event"),
+               };
                check_added_monitors!(nodes[3], 1);
 
                // Clear bumped claiming txn spending node 2 commitment tx. Bumped txn are generated after reaching some height timer.
@@ -2451,7 +2459,14 @@ fn channel_monitor_network_test() {
                        header = BlockHeader { version: 0x20000000, prev_blockhash: header.bitcoin_hash(), merkle_root: Default::default(), time: 42, bits: 42, nonce: 42 };
                        nodes[4].block_notifier.block_connected_checked(&header, i, &Vec::new()[..], &[0; 0]);
                }
-
+               let events = nodes[4].node.get_and_clear_pending_msg_events();
+               assert_eq!(events.len(), 1);
+               let close_chan_update_2 = match events[0] {
+                       MessageSendEvent::BroadcastChannelUpdate { ref msg } => {
+                               msg.clone()
+                       },
+                       _ => panic!("Unexpected event"),
+               };
                check_added_monitors!(nodes[4], 1);
                test_txn_broadcast(&nodes[4], &chan_4, None, HTLCType::SUCCESS);
 
@@ -2459,8 +2474,10 @@ fn channel_monitor_network_test() {
                nodes[4].block_notifier.block_connected(&Block { header, txdata: vec![node_txn[0].clone()] }, TEST_FINAL_CLTV - 5);
 
                check_preimage_claim(&nodes[4], &node_txn);
-       }
-       get_announce_close_broadcast_events(&nodes, 3, 4);
+               (close_chan_update_1, close_chan_update_2)
+       };
+       nodes[3].net_graph_msg_handler.handle_channel_update(&close_chan_update_2).unwrap();
+       nodes[4].net_graph_msg_handler.handle_channel_update(&close_chan_update_1).unwrap();
        assert_eq!(nodes[3].node.list_channels().len(), 0);
        assert_eq!(nodes[4].node.list_channels().len(), 0);
 }
index 4fccba37212ce8584af1ce83e8bddc697a68f5ae..d77a39e59772ec9239d271ab55a988bd4b9fbc8a 100644 (file)
@@ -74,185 +74,278 @@ pub struct Init {
 /// An error message to be sent or received from a peer
 #[derive(Clone)]
 pub struct ErrorMessage {
-       pub(crate) channel_id: [u8; 32],
-       pub(crate) data: String,
+       /// The channel ID involved in the error
+       pub channel_id: [u8; 32],
+       /// A possibly human-readable error description.
+       /// The string should be sanitized before it is used (e.g. emitted to logs
+       /// or printed to stdout).  Otherwise, a well crafted error message may trigger a security
+       /// vulnerability in the terminal emulator or the logging subsystem.
+       pub data: String,
 }
 
 /// A ping message to be sent or received from a peer
 pub struct Ping {
-       pub(crate) ponglen: u16,
-       pub(crate) byteslen: u16,
+       /// The desired response length
+       pub ponglen: u16,
+       /// The ping packet size.
+       /// This field is not sent on the wire. byteslen zeros are sent.
+       pub byteslen: u16,
 }
 
 /// A pong message to be sent or received from a peer
 pub struct Pong {
-       pub(crate) byteslen: u16,
+       /// The pong packet size.
+       /// This field is not sent on the wire. byteslen zeros are sent.
+       pub byteslen: u16,
 }
 
 /// An open_channel message to be sent or received from a peer
 #[derive(Clone)]
 pub struct OpenChannel {
-       pub(crate) chain_hash: BlockHash,
-       pub(crate) temporary_channel_id: [u8; 32],
-       pub(crate) funding_satoshis: u64,
-       pub(crate) push_msat: u64,
-       pub(crate) dust_limit_satoshis: u64,
-       pub(crate) max_htlc_value_in_flight_msat: u64,
-       pub(crate) channel_reserve_satoshis: u64,
-       pub(crate) htlc_minimum_msat: u64,
-       pub(crate) feerate_per_kw: u32,
-       pub(crate) to_self_delay: u16,
-       pub(crate) max_accepted_htlcs: u16,
-       pub(crate) funding_pubkey: PublicKey,
-       pub(crate) revocation_basepoint: PublicKey,
-       pub(crate) payment_point: PublicKey,
-       pub(crate) delayed_payment_basepoint: PublicKey,
-       pub(crate) htlc_basepoint: PublicKey,
-       pub(crate) first_per_commitment_point: PublicKey,
-       pub(crate) channel_flags: u8,
-       pub(crate) shutdown_scriptpubkey: OptionalField<Script>,
+       /// The genesis hash of the blockchain where the channel is to be opened
+       pub chain_hash: BlockHash,
+       /// A temporary channel ID, until the funding outpoint is announced
+       pub temporary_channel_id: [u8; 32],
+       /// The channel value
+       pub funding_satoshis: u64,
+       /// The amount to push to the counterparty as part of the open, in milli-satoshi
+       pub push_msat: u64,
+       /// The threshold below which outputs on transactions broadcast by sender will be omitted
+       pub dust_limit_satoshis: u64,
+       /// The maximum inbound HTLC value in flight towards sender, in milli-satoshi
+       pub max_htlc_value_in_flight_msat: u64,
+       /// The minimum value unencumbered by HTLCs for the counterparty to keep in the channel
+       pub channel_reserve_satoshis: u64,
+       /// The minimum HTLC size incoming to sender, in milli-satoshi
+       pub htlc_minimum_msat: u64,
+       /// The feerate per 1000-weight of sender generated transactions, until updated by update_fee
+       pub feerate_per_kw: u32,
+       /// The number of blocks which the counterparty will have to wait to claim on-chain funds if they broadcast a commitment transaction
+       pub to_self_delay: u16,
+       /// The maximum number of inbound HTLCs towards sender
+       pub max_accepted_htlcs: u16,
+       /// The sender's key controlling the funding transaction
+       pub funding_pubkey: PublicKey,
+       /// Used to derive a revocation key for transactions broadcast by counterparty
+       pub revocation_basepoint: PublicKey,
+       /// A payment key to sender for transactions broadcast by counterparty
+       pub payment_point: PublicKey,
+       /// Used to derive a payment key to sender for transactions broadcast by sender
+       pub delayed_payment_basepoint: PublicKey,
+       /// Used to derive an HTLC payment key to sender
+       pub htlc_basepoint: PublicKey,
+       /// The first to-be-broadcast-by-sender transaction's per commitment point
+       pub first_per_commitment_point: PublicKey,
+       /// Channel flags
+       pub channel_flags: u8,
+       /// Optionally, a request to pre-set the to-sender output's scriptPubkey for when we collaboratively close
+       pub shutdown_scriptpubkey: OptionalField<Script>,
 }
 
 /// An accept_channel message to be sent or received from a peer
 #[derive(Clone)]
 pub struct AcceptChannel {
-       pub(crate) temporary_channel_id: [u8; 32],
-       pub(crate) dust_limit_satoshis: u64,
-       pub(crate) max_htlc_value_in_flight_msat: u64,
-       pub(crate) channel_reserve_satoshis: u64,
-       pub(crate) htlc_minimum_msat: u64,
-       pub(crate) minimum_depth: u32,
-       pub(crate) to_self_delay: u16,
-       pub(crate) max_accepted_htlcs: u16,
-       pub(crate) funding_pubkey: PublicKey,
-       pub(crate) revocation_basepoint: PublicKey,
-       pub(crate) payment_point: PublicKey,
-       pub(crate) delayed_payment_basepoint: PublicKey,
-       pub(crate) htlc_basepoint: PublicKey,
-       pub(crate) first_per_commitment_point: PublicKey,
-       pub(crate) shutdown_scriptpubkey: OptionalField<Script>
+       /// A temporary channel ID, until the funding outpoint is announced
+       pub temporary_channel_id: [u8; 32],
+       /// The threshold below which outputs on transactions broadcast by sender will be omitted
+       pub dust_limit_satoshis: u64,
+       /// The maximum inbound HTLC value in flight towards sender, in milli-satoshi
+       pub max_htlc_value_in_flight_msat: u64,
+       /// The minimum value unencumbered by HTLCs for the counterparty to keep in the channel
+       pub channel_reserve_satoshis: u64,
+       /// The minimum HTLC size incoming to sender, in milli-satoshi
+       pub htlc_minimum_msat: u64,
+       /// Minimum depth of the funding transaction before the channel is considered open
+       pub minimum_depth: u32,
+       /// The number of blocks which the counterparty will have to wait to claim on-chain funds if they broadcast a commitment transaction
+       pub to_self_delay: u16,
+       /// The maximum number of inbound HTLCs towards sender
+       pub max_accepted_htlcs: u16,
+       /// The sender's key controlling the funding transaction
+       pub funding_pubkey: PublicKey,
+       /// Used to derive a revocation key for transactions broadcast by counterparty
+       pub revocation_basepoint: PublicKey,
+       /// A payment key to sender for transactions broadcast by counterparty
+       pub payment_point: PublicKey,
+       /// Used to derive a payment key to sender for transactions broadcast by sender
+       pub delayed_payment_basepoint: PublicKey,
+       /// Used to derive an HTLC payment key to sender for transactions broadcast by counterparty
+       pub htlc_basepoint: PublicKey,
+       /// The first to-be-broadcast-by-sender transaction's per commitment point
+       pub first_per_commitment_point: PublicKey,
+       /// Optionally, a request to pre-set the to-sender output's scriptPubkey for when we collaboratively close
+       pub shutdown_scriptpubkey: OptionalField<Script>,
 }
 
 /// A funding_created message to be sent or received from a peer
 #[derive(Clone)]
 pub struct FundingCreated {
-       pub(crate) temporary_channel_id: [u8; 32],
-       pub(crate) funding_txid: Txid,
-       pub(crate) funding_output_index: u16,
-       pub(crate) signature: Signature,
+       /// A temporary channel ID, until the funding is established
+       pub temporary_channel_id: [u8; 32],
+       /// The funding transaction ID
+       pub funding_txid: Txid,
+       /// The specific output index funding this channel
+       pub funding_output_index: u16,
+       /// The signature of the channel initiator (funder) on the funding transaction
+       pub signature: Signature,
 }
 
 /// A funding_signed message to be sent or received from a peer
 #[derive(Clone)]
 pub struct FundingSigned {
-       pub(crate) channel_id: [u8; 32],
-       pub(crate) signature: Signature,
+       /// The channel ID
+       pub channel_id: [u8; 32],
+       /// The signature of the channel acceptor (fundee) on the funding transaction
+       pub signature: Signature,
 }
 
 /// A funding_locked message to be sent or received from a peer
 #[derive(Clone, PartialEq)]
-#[allow(missing_docs)]
 pub struct FundingLocked {
+       /// The channel ID
        pub channel_id: [u8; 32],
+       /// The per-commitment point of the second commitment transaction
        pub next_per_commitment_point: PublicKey,
 }
 
 /// A shutdown message to be sent or received from a peer
 #[derive(Clone, PartialEq)]
 pub struct Shutdown {
-       pub(crate) channel_id: [u8; 32],
-       pub(crate) scriptpubkey: Script,
+       /// The channel ID
+       pub channel_id: [u8; 32],
+       /// The destination of this peer's funds on closing.
+       /// Must be in one of these forms: p2pkh, p2sh, p2wpkh, p2wsh.
+       pub scriptpubkey: Script,
 }
 
 /// A closing_signed message to be sent or received from a peer
 #[derive(Clone, PartialEq)]
 pub struct ClosingSigned {
-       pub(crate) channel_id: [u8; 32],
-       pub(crate) fee_satoshis: u64,
-       pub(crate) signature: Signature,
+       /// The channel ID
+       pub channel_id: [u8; 32],
+       /// The proposed total fee for the closing transaction
+       pub fee_satoshis: u64,
+       /// A signature on the closing transaction
+       pub signature: Signature,
 }
 
 /// An update_add_htlc message to be sent or received from a peer
 #[derive(Clone, PartialEq)]
 pub struct UpdateAddHTLC {
-       pub(crate) channel_id: [u8; 32],
-       pub(crate) htlc_id: u64,
-       pub(crate) amount_msat: u64,
-       pub(crate) payment_hash: PaymentHash,
-       pub(crate) cltv_expiry: u32,
+       /// The channel ID
+       pub channel_id: [u8; 32],
+       /// The HTLC ID
+       pub htlc_id: u64,
+       /// The HTLC value in milli-satoshi
+       pub amount_msat: u64,
+       /// The payment hash, the pre-image of which controls HTLC redemption
+       pub payment_hash: PaymentHash,
+       /// The expiry height of the HTLC
+       pub cltv_expiry: u32,
        pub(crate) onion_routing_packet: OnionPacket,
 }
 
 /// An update_fulfill_htlc message to be sent or received from a peer
 #[derive(Clone, PartialEq)]
 pub struct UpdateFulfillHTLC {
-       pub(crate) channel_id: [u8; 32],
-       pub(crate) htlc_id: u64,
-       pub(crate) payment_preimage: PaymentPreimage,
+       /// The channel ID
+       pub channel_id: [u8; 32],
+       /// The HTLC ID
+       pub htlc_id: u64,
+       /// The pre-image of the payment hash, allowing HTLC redemption
+       pub payment_preimage: PaymentPreimage,
 }
 
 /// An update_fail_htlc message to be sent or received from a peer
 #[derive(Clone, PartialEq)]
 pub struct UpdateFailHTLC {
-       pub(crate) channel_id: [u8; 32],
-       pub(crate) htlc_id: u64,
+       /// The channel ID
+       pub channel_id: [u8; 32],
+       /// The HTLC ID
+       pub htlc_id: u64,
        pub(crate) reason: OnionErrorPacket,
 }
 
 /// An update_fail_malformed_htlc message to be sent or received from a peer
 #[derive(Clone, PartialEq)]
 pub struct UpdateFailMalformedHTLC {
-       pub(crate) channel_id: [u8; 32],
-       pub(crate) htlc_id: u64,
+       /// The channel ID
+       pub channel_id: [u8; 32],
+       /// The HTLC ID
+       pub htlc_id: u64,
        pub(crate) sha256_of_onion: [u8; 32],
-       pub(crate) failure_code: u16,
+       /// The failure code
+       pub failure_code: u16,
 }
 
 /// A commitment_signed message to be sent or received from a peer
 #[derive(Clone, PartialEq)]
 pub struct CommitmentSigned {
-       pub(crate) channel_id: [u8; 32],
-       pub(crate) signature: Signature,
-       pub(crate) htlc_signatures: Vec<Signature>,
+       /// The channel ID
+       pub channel_id: [u8; 32],
+       /// A signature on the commitment transaction
+       pub signature: Signature,
+       /// Signatures on the HTLC transactions
+       pub htlc_signatures: Vec<Signature>,
 }
 
 /// A revoke_and_ack message to be sent or received from a peer
 #[derive(Clone, PartialEq)]
 pub struct RevokeAndACK {
-       pub(crate) channel_id: [u8; 32],
-       pub(crate) per_commitment_secret: [u8; 32],
-       pub(crate) next_per_commitment_point: PublicKey,
+       /// The channel ID
+       pub channel_id: [u8; 32],
+       /// The secret corresponding to the per-commitment point
+       pub per_commitment_secret: [u8; 32],
+       /// The next sender-broadcast commitment transaction's per-commitment point
+       pub next_per_commitment_point: PublicKey,
 }
 
 /// An update_fee message to be sent or received from a peer
 #[derive(PartialEq, Clone)]
 pub struct UpdateFee {
-       pub(crate) channel_id: [u8; 32],
-       pub(crate) feerate_per_kw: u32,
+       /// The channel ID
+       pub channel_id: [u8; 32],
+       /// Fee rate per 1000-weight of the transaction
+       pub feerate_per_kw: u32,
 }
 
 #[derive(PartialEq, Clone)]
-pub(crate) struct DataLossProtect {
-       pub(crate) your_last_per_commitment_secret: [u8; 32],
-       pub(crate) my_current_per_commitment_point: PublicKey,
+/// Proof that the sender knows the per-commitment secret of the previous commitment transaction.
+/// This is used to convince the recipient that the channel is at a certain commitment
+/// number even if they lost that data due to a local failure.  Of course, the peer may lie
+/// and even later commitments may have been revoked.
+pub struct DataLossProtect {
+       /// Proof that the sender knows the per-commitment secret of a specific commitment transaction
+       /// belonging to the recipient
+       pub your_last_per_commitment_secret: [u8; 32],
+       /// The sender's per-commitment point for their current commitment transaction
+       pub my_current_per_commitment_point: PublicKey,
 }
 
 /// A channel_reestablish message to be sent or received from a peer
 #[derive(PartialEq, Clone)]
 pub struct ChannelReestablish {
-       pub(crate) channel_id: [u8; 32],
-       pub(crate) next_local_commitment_number: u64,
-       pub(crate) next_remote_commitment_number: u64,
-       pub(crate) data_loss_protect: OptionalField<DataLossProtect>,
+       /// The channel ID
+       pub channel_id: [u8; 32],
+       /// The next commitment number for the sender
+       pub next_local_commitment_number: u64,
+       /// The next commitment number for the recipient
+       pub next_remote_commitment_number: u64,
+       /// Optionally, a field proving that next_remote_commitment_number-1 has been revoked
+       pub data_loss_protect: OptionalField<DataLossProtect>,
 }
 
 /// An announcement_signatures message to be sent or received from a peer
 #[derive(PartialEq, Clone, Debug)]
 pub struct AnnouncementSignatures {
-       pub(crate) channel_id: [u8; 32],
-       pub(crate) short_channel_id: u64,
-       pub(crate) node_signature: Signature,
-       pub(crate) bitcoin_signature: Signature,
+       /// The channel ID
+       pub channel_id: [u8; 32],
+       /// The short channel ID
+       pub short_channel_id: u64,
+       /// A signature by the node key
+       pub node_signature: Signature,
+       /// A signature by the funding key
+       pub bitcoin_signature: Signature,
 }
 
 /// An address which can be used to connect to a remote peer
@@ -382,73 +475,99 @@ impl Readable for Result<NetAddress, u8> {
        }
 }
 
-// Only exposed as broadcast of node_announcement should be filtered by node_id
 /// The unsigned part of a node_announcement
 #[derive(PartialEq, Clone, Debug)]
 pub struct UnsignedNodeAnnouncement {
-       pub(crate) features: NodeFeatures,
-       pub(crate) timestamp: u32,
+       /// The advertised features
+       pub features: NodeFeatures,
+       /// A strictly monotonic announcement counter, with gaps allowed
+       pub timestamp: u32,
        /// The node_id this announcement originated from (don't rebroadcast the node_announcement back
        /// to this node).
-       pub        node_id: PublicKey,
-       pub(crate) rgb: [u8; 3],
-       pub(crate) alias: [u8; 32],
-       /// List of addresses on which this node is reachable. Note that you may only have up to one
-       /// address of each type, if you have more, they may be silently discarded or we may panic!
-       pub(crate) addresses: Vec<NetAddress>,
+       pub node_id: PublicKey,
+       /// An RGB color for UI purposes
+       pub rgb: [u8; 3],
+       /// An alias, for UI purposes.  This should be sanitized before use.  There is no guarantee
+       /// of uniqueness.
+       pub alias: [u8; 32],
+       /// List of addresses on which this node is reachable
+       pub addresses: Vec<NetAddress>,
        pub(crate) excess_address_data: Vec<u8>,
        pub(crate) excess_data: Vec<u8>,
 }
 #[derive(PartialEq, Clone, Debug)]
 /// A node_announcement message to be sent or received from a peer
 pub struct NodeAnnouncement {
-       pub(crate) signature: Signature,
-       pub(crate) contents: UnsignedNodeAnnouncement,
+       /// The signature by the node key
+       pub signature: Signature,
+       /// The actual content of the announcement
+       pub contents: UnsignedNodeAnnouncement,
 }
 
-// Only exposed as broadcast of channel_announcement should be filtered by node_id
 /// The unsigned part of a channel_announcement
 #[derive(PartialEq, Clone, Debug)]
 pub struct UnsignedChannelAnnouncement {
-       pub(crate) features: ChannelFeatures,
-       pub(crate) chain_hash: BlockHash,
-       pub(crate) short_channel_id: u64,
+       /// The advertised channel features
+       pub features: ChannelFeatures,
+       /// The genesis hash of the blockchain where the channel is to be opened
+       pub chain_hash: BlockHash,
+       /// The short channel ID
+       pub short_channel_id: u64,
        /// One of the two node_ids which are endpoints of this channel
-       pub        node_id_1: PublicKey,
+       pub node_id_1: PublicKey,
        /// The other of the two node_ids which are endpoints of this channel
-       pub        node_id_2: PublicKey,
-       pub(crate) bitcoin_key_1: PublicKey,
-       pub(crate) bitcoin_key_2: PublicKey,
+       pub node_id_2: PublicKey,
+       /// The funding key for the first node
+       pub bitcoin_key_1: PublicKey,
+       /// The funding key for the second node
+       pub bitcoin_key_2: PublicKey,
        pub(crate) excess_data: Vec<u8>,
 }
 /// A channel_announcement message to be sent or received from a peer
 #[derive(PartialEq, Clone, Debug)]
 pub struct ChannelAnnouncement {
-       pub(crate) node_signature_1: Signature,
-       pub(crate) node_signature_2: Signature,
-       pub(crate) bitcoin_signature_1: Signature,
-       pub(crate) bitcoin_signature_2: Signature,
-       pub(crate) contents: UnsignedChannelAnnouncement,
-}
-
+       /// Authentication of the announcement by the first public node
+       pub node_signature_1: Signature,
+       /// Authentication of the announcement by the second public node
+       pub node_signature_2: Signature,
+       /// Proof of funding UTXO ownership by the first public node
+       pub bitcoin_signature_1: Signature,
+       /// Proof of funding UTXO ownership by the second public node
+       pub bitcoin_signature_2: Signature,
+       /// The actual announcement
+       pub contents: UnsignedChannelAnnouncement,
+}
+
+/// The unsigned part of a channel_update
 #[derive(PartialEq, Clone, Debug)]
-pub(crate) struct UnsignedChannelUpdate {
-       pub(crate) chain_hash: BlockHash,
-       pub(crate) short_channel_id: u64,
-       pub(crate) timestamp: u32,
-       pub(crate) flags: u8,
-       pub(crate) cltv_expiry_delta: u16,
-       pub(crate) htlc_minimum_msat: u64,
-       pub(crate) htlc_maximum_msat: OptionalField<u64>,
-       pub(crate) fee_base_msat: u32,
-       pub(crate) fee_proportional_millionths: u32,
+pub struct UnsignedChannelUpdate {
+       /// The genesis hash of the blockchain where the channel is to be opened
+       pub chain_hash: BlockHash,
+       /// The short channel ID
+       pub short_channel_id: u64,
+       /// A strictly monotonic announcement counter, with gaps allowed, specific to this channel
+       pub timestamp: u32,
+       /// Channel flags
+       pub flags: u8,
+       /// The number of blocks to subtract from incoming HTLC cltv_expiry values
+       pub cltv_expiry_delta: u16,
+       /// The minimum HTLC size incoming to sender, in milli-satoshi
+       pub htlc_minimum_msat: u64,
+       /// Optionally, the maximum HTLC value incoming to sender, in milli-satoshi
+       pub htlc_maximum_msat: OptionalField<u64>,
+       /// The base HTLC fee charged by sender, in milli-satoshi
+       pub fee_base_msat: u32,
+       /// The amount to fee multiplier, in micro-satoshi
+       pub fee_proportional_millionths: u32,
        pub(crate) excess_data: Vec<u8>,
 }
 /// A channel_update message to be sent or received from a peer
 #[derive(PartialEq, Clone, Debug)]
 pub struct ChannelUpdate {
-       pub(crate) signature: Signature,
-       pub(crate) contents: UnsignedChannelUpdate,
+       /// A signature of the channel update
+       pub signature: Signature,
+       /// The actual channel update
+       pub contents: UnsignedChannelUpdate,
 }
 
 /// Used to put an error message in a LightningError
index 9ab687f64e7cbbf9237650bdafd914593f810422..95f575fbff4a1c76a439eb829d17b82977ad5b76 100644 (file)
@@ -122,7 +122,7 @@ fn do_test_onchain_htlc_reorg(local_commitment: bool, claim: bool) {
                header = BlockHeader { version: 0x20000000, prev_blockhash: Default::default(), merkle_root: Default::default(), time: 42, bits: 42, nonce: 42 };
                nodes[1].block_notifier.block_connected(&Block { header, txdata: claim_txn }, CHAN_CONFIRM_DEPTH + 1);
 
-               // ChannelManager only polls ManyChannelMonitor::get_and_clear_pending_htlcs_updated when we
+               // ChannelManager only polls ManyChannelMonitor::get_and_clear_pending_monitor_events when we
                // probe it for events, so we probe non-message events here (which should still end up empty):
                assert_eq!(nodes[1].node.get_and_clear_pending_events().len(), 0);
        } else {
index 2fc0d1745206d5986a0a6375e273b72b23ccb035..7730fd8f2ff4bb11ee7c965363826030aae336b7 100644 (file)
@@ -504,21 +504,46 @@ mod tests {
                };
        }
 
-       #[test]
-       fn route_test() {
+       fn get_nodes(secp_ctx: &Secp256k1<All>) -> (SecretKey, PublicKey, Vec<SecretKey>, Vec<PublicKey>) {
+               let privkeys: Vec<SecretKey> = (2..10).map(|i| {
+                       SecretKey::from_slice(&hex::decode(format!("{:02}", i).repeat(32)).unwrap()[..]).unwrap()
+               }).collect();
+
+               let pubkeys = privkeys.iter().map(|secret| PublicKey::from_secret_key(&secp_ctx, secret)).collect();
+
+               let our_privkey = SecretKey::from_slice(&hex::decode("01".repeat(32)).unwrap()[..]).unwrap();
+               let our_id = PublicKey::from_secret_key(&secp_ctx, &our_privkey);
+
+               (our_privkey, our_id, privkeys, pubkeys)
+       }
+
+       fn id_to_feature_flags(id: u8) -> Vec<u8> {
+               // Set the feature flags to the id'th odd (ie non-required) feature bit so that we can
+               // test for it later.
+               let idx = (id - 1) * 2 + 1;
+               if idx > 8*3 {
+                       vec![1 << (idx - 8*3), 0, 0, 0]
+               } else if idx > 8*2 {
+                       vec![1 << (idx - 8*2), 0, 0]
+               } else if idx > 8*1 {
+                       vec![1 << (idx - 8*1), 0]
+               } else {
+                       vec![1 << idx]
+               }
+       }
+
+       fn build_graph() -> (Secp256k1<All>, NetGraphMsgHandler<std::sync::Arc<crate::chain::chaininterface::ChainWatchInterfaceUtil>, std::sync::Arc<crate::util::test_utils::TestLogger>>, std::sync::Arc<test_utils::TestLogger>) {
                let secp_ctx = Secp256k1::new();
-               let our_privkey = &SecretKey::from_slice(&hex::decode("0101010101010101010101010101010101010101010101010101010101010101").unwrap()[..]).unwrap();
-               let our_id = PublicKey::from_secret_key(&secp_ctx, our_privkey);
                let logger = Arc::new(test_utils::TestLogger::new());
                let chain_monitor = Arc::new(chaininterface::ChainWatchInterfaceUtil::new(Network::Testnet));
                let net_graph_msg_handler = NetGraphMsgHandler::new(chain_monitor, Arc::clone(&logger));
-               // Build network from our_id to node8:
+               // Build network from our_id to node7:
                //
-               //        -1(1)2-  node1  -1(3)2-
+               //        -1(1)2-  node0  -1(3)2-
                //       /                       \
-               // our_id -1(12)2- node8 -1(13)2--- node3
+               // our_id -1(12)2- node7 -1(13)2--- node2
                //       \                       /
-               //        -1(2)2-  node2  -1(4)2-
+               //        -1(2)2-  node1  -1(4)2-
                //
                //
                // chan1  1-to-2: disabled
@@ -540,13 +565,13 @@ mod tests {
                // chan13 2-to-1: enabled, 0 fee
                //
                //
-               //       -1(5)2- node4 -1(8)2--
+               //       -1(5)2- node3 -1(8)2--
                //       |         2          |
                //       |       (11)         |
                //      /          1           \
-               // node3--1(6)2- node5 -1(9)2--- node7 (not in global route map)
+               // node2--1(6)2- node4 -1(9)2--- node6 (not in global route map)
                //      \                      /
-               //       -1(7)2- node6 -1(10)2-
+               //       -1(7)2- node5 -1(10)2-
                //
                // chan5  1-to-2: enabled, 100 msat fee
                // chan5  2-to-1: enabled, 0 fee
@@ -569,44 +594,10 @@ mod tests {
                // chan11 1-to-2: enabled, 0 fee
                // chan11 2-to-1: enabled, 0 fee
 
-               let node1_privkey = &SecretKey::from_slice(&hex::decode("0202020202020202020202020202020202020202020202020202020202020202").unwrap()[..]).unwrap();
-               let node2_privkey = &SecretKey::from_slice(&hex::decode("0303030303030303030303030303030303030303030303030303030303030303").unwrap()[..]).unwrap();
-               let node3_privkey = &SecretKey::from_slice(&hex::decode("0404040404040404040404040404040404040404040404040404040404040404").unwrap()[..]).unwrap();
-               let node4_privkey = &SecretKey::from_slice(&hex::decode("0505050505050505050505050505050505050505050505050505050505050505").unwrap()[..]).unwrap();
-               let node5_privkey = &SecretKey::from_slice(&hex::decode("0606060606060606060606060606060606060606060606060606060606060606").unwrap()[..]).unwrap();
-               let node6_privkey = &SecretKey::from_slice(&hex::decode("0707070707070707070707070707070707070707070707070707070707070707").unwrap()[..]).unwrap();
-               let node7_privkey = &SecretKey::from_slice(&hex::decode("0808080808080808080808080808080808080808080808080808080808080808").unwrap()[..]).unwrap();
-               let node8_privkey = &SecretKey::from_slice(&hex::decode("0909090909090909090909090909090909090909090909090909090909090909").unwrap()[..]).unwrap();
-
-
-               let node1 = PublicKey::from_secret_key(&secp_ctx, node1_privkey);
-               let node2 = PublicKey::from_secret_key(&secp_ctx, node2_privkey);
-               let node3 = PublicKey::from_secret_key(&secp_ctx, node3_privkey);
-               let node4 = PublicKey::from_secret_key(&secp_ctx, node4_privkey);
-               let node5 = PublicKey::from_secret_key(&secp_ctx, node5_privkey);
-               let node6 = PublicKey::from_secret_key(&secp_ctx, node6_privkey);
-               let node7 = PublicKey::from_secret_key(&secp_ctx, node7_privkey);
-               let node8 = PublicKey::from_secret_key(&secp_ctx, node8_privkey);
-
-               macro_rules! id_to_feature_flags {
-                       // Set the feature flags to the id'th odd (ie non-required) feature bit so that we can
-                       // test for it later.
-                       ($id: expr) => { {
-                               let idx = ($id - 1) * 2 + 1;
-                               if idx > 8*3 {
-                                       vec![1 << (idx - 8*3), 0, 0, 0]
-                               } else if idx > 8*2 {
-                                       vec![1 << (idx - 8*2), 0, 0]
-                               } else if idx > 8*1 {
-                                       vec![1 << (idx - 8*1), 0]
-                               } else {
-                                       vec![1 << idx]
-                               }
-                       } }
-               }
+               let (our_privkey, _, privkeys, _) = get_nodes(&secp_ctx);
 
-               add_channel(&net_graph_msg_handler, &secp_ctx, our_privkey, node1_privkey, ChannelFeatures::from_le_bytes(id_to_feature_flags!(1)), 1);
-               update_channel(&net_graph_msg_handler, &secp_ctx, node1_privkey, UnsignedChannelUpdate {
+               add_channel(&net_graph_msg_handler, &secp_ctx, &our_privkey, &privkeys[0], ChannelFeatures::from_le_bytes(id_to_feature_flags(1)), 1);
+               update_channel(&net_graph_msg_handler, &secp_ctx, &privkeys[0], UnsignedChannelUpdate {
                        chain_hash: genesis_block(Network::Testnet).header.bitcoin_hash(),
                        short_channel_id: 1,
                        timestamp: 1,
@@ -618,10 +609,11 @@ mod tests {
                        fee_proportional_millionths: 0,
                        excess_data: Vec::new()
                });
-               add_or_update_node(&net_graph_msg_handler, &secp_ctx, node1_privkey, NodeFeatures::from_le_bytes(id_to_feature_flags!(1)), 0);
 
-               add_channel(&net_graph_msg_handler, &secp_ctx, our_privkey, node2_privkey, ChannelFeatures::from_le_bytes(id_to_feature_flags!(2)), 2);
-               update_channel(&net_graph_msg_handler, &secp_ctx, our_privkey, UnsignedChannelUpdate {
+               add_or_update_node(&net_graph_msg_handler, &secp_ctx, &privkeys[0], NodeFeatures::from_le_bytes(id_to_feature_flags(1)), 0);
+
+               add_channel(&net_graph_msg_handler, &secp_ctx, &our_privkey, &privkeys[1], ChannelFeatures::from_le_bytes(id_to_feature_flags(2)), 2);
+               update_channel(&net_graph_msg_handler, &secp_ctx, &our_privkey, UnsignedChannelUpdate {
                        chain_hash: genesis_block(Network::Testnet).header.bitcoin_hash(),
                        short_channel_id: 2,
                        timestamp: 1,
@@ -633,7 +625,7 @@ mod tests {
                        fee_proportional_millionths: u32::max_value(),
                        excess_data: Vec::new()
                });
-               update_channel(&net_graph_msg_handler, &secp_ctx, node2_privkey, UnsignedChannelUpdate {
+               update_channel(&net_graph_msg_handler, &secp_ctx, &privkeys[1], UnsignedChannelUpdate {
                        chain_hash: genesis_block(Network::Testnet).header.bitcoin_hash(),
                        short_channel_id: 2,
                        timestamp: 1,
@@ -646,10 +638,10 @@ mod tests {
                        excess_data: Vec::new()
                });
 
-               add_or_update_node(&net_graph_msg_handler, &secp_ctx, node2_privkey, NodeFeatures::from_le_bytes(id_to_feature_flags!(2)), 0);
+               add_or_update_node(&net_graph_msg_handler, &secp_ctx, &privkeys[1], NodeFeatures::from_le_bytes(id_to_feature_flags(2)), 0);
 
-               add_channel(&net_graph_msg_handler, &secp_ctx, our_privkey, node8_privkey, ChannelFeatures::from_le_bytes(id_to_feature_flags!(12)), 12);
-               update_channel(&net_graph_msg_handler, &secp_ctx, our_privkey, UnsignedChannelUpdate {
+               add_channel(&net_graph_msg_handler, &secp_ctx, &our_privkey, &privkeys[7], ChannelFeatures::from_le_bytes(id_to_feature_flags(12)), 12);
+               update_channel(&net_graph_msg_handler, &secp_ctx, &our_privkey, UnsignedChannelUpdate {
                        chain_hash: genesis_block(Network::Testnet).header.bitcoin_hash(),
                        short_channel_id: 12,
                        timestamp: 1,
@@ -661,7 +653,7 @@ mod tests {
                        fee_proportional_millionths: u32::max_value(),
                        excess_data: Vec::new()
                });
-               update_channel(&net_graph_msg_handler, &secp_ctx, node8_privkey, UnsignedChannelUpdate {
+               update_channel(&net_graph_msg_handler, &secp_ctx, &privkeys[7], UnsignedChannelUpdate {
                        chain_hash: genesis_block(Network::Testnet).header.bitcoin_hash(),
                        short_channel_id: 12,
                        timestamp: 1,
@@ -674,11 +666,10 @@ mod tests {
                        excess_data: Vec::new()
                });
 
+               add_or_update_node(&net_graph_msg_handler, &secp_ctx, &privkeys[7], NodeFeatures::from_le_bytes(id_to_feature_flags(8)), 0);
 
-               add_or_update_node(&net_graph_msg_handler, &secp_ctx, node8_privkey, NodeFeatures::from_le_bytes(id_to_feature_flags!(8)), 0);
-
-               add_channel(&net_graph_msg_handler, &secp_ctx, node1_privkey, node3_privkey, ChannelFeatures::from_le_bytes(id_to_feature_flags!(3)), 3);
-               update_channel(&net_graph_msg_handler, &secp_ctx, node1_privkey, UnsignedChannelUpdate {
+               add_channel(&net_graph_msg_handler, &secp_ctx, &privkeys[0], &privkeys[2], ChannelFeatures::from_le_bytes(id_to_feature_flags(3)), 3);
+               update_channel(&net_graph_msg_handler, &secp_ctx, &privkeys[0], UnsignedChannelUpdate {
                        chain_hash: genesis_block(Network::Testnet).header.bitcoin_hash(),
                        short_channel_id: 3,
                        timestamp: 1,
@@ -690,7 +681,7 @@ mod tests {
                        fee_proportional_millionths: 0,
                        excess_data: Vec::new()
                });
-               update_channel(&net_graph_msg_handler, &secp_ctx, node3_privkey, UnsignedChannelUpdate {
+               update_channel(&net_graph_msg_handler, &secp_ctx, &privkeys[2], UnsignedChannelUpdate {
                        chain_hash: genesis_block(Network::Testnet).header.bitcoin_hash(),
                        short_channel_id: 3,
                        timestamp: 1,
@@ -703,9 +694,8 @@ mod tests {
                        excess_data: Vec::new()
                });
 
-
-               add_channel(&net_graph_msg_handler, &secp_ctx, node2_privkey, node3_privkey, ChannelFeatures::from_le_bytes(id_to_feature_flags!(4)), 4);
-               update_channel(&net_graph_msg_handler, &secp_ctx, node2_privkey, UnsignedChannelUpdate {
+               add_channel(&net_graph_msg_handler, &secp_ctx, &privkeys[1], &privkeys[2], ChannelFeatures::from_le_bytes(id_to_feature_flags(4)), 4);
+               update_channel(&net_graph_msg_handler, &secp_ctx, &privkeys[1], UnsignedChannelUpdate {
                        chain_hash: genesis_block(Network::Testnet).header.bitcoin_hash(),
                        short_channel_id: 4,
                        timestamp: 1,
@@ -717,7 +707,7 @@ mod tests {
                        fee_proportional_millionths: 1000000,
                        excess_data: Vec::new()
                });
-               update_channel(&net_graph_msg_handler, &secp_ctx, node3_privkey, UnsignedChannelUpdate {
+               update_channel(&net_graph_msg_handler, &secp_ctx, &privkeys[2], UnsignedChannelUpdate {
                        chain_hash: genesis_block(Network::Testnet).header.bitcoin_hash(),
                        short_channel_id: 4,
                        timestamp: 1,
@@ -730,8 +720,8 @@ mod tests {
                        excess_data: Vec::new()
                });
 
-               add_channel(&net_graph_msg_handler, &secp_ctx, node8_privkey, node3_privkey, ChannelFeatures::from_le_bytes(id_to_feature_flags!(13)), 13);
-               update_channel(&net_graph_msg_handler, &secp_ctx, node8_privkey, UnsignedChannelUpdate {
+               add_channel(&net_graph_msg_handler, &secp_ctx, &privkeys[7], &privkeys[2], ChannelFeatures::from_le_bytes(id_to_feature_flags(13)), 13);
+               update_channel(&net_graph_msg_handler, &secp_ctx, &privkeys[7], UnsignedChannelUpdate {
                        chain_hash: genesis_block(Network::Testnet).header.bitcoin_hash(),
                        short_channel_id: 13,
                        timestamp: 1,
@@ -743,7 +733,7 @@ mod tests {
                        fee_proportional_millionths: 2000000,
                        excess_data: Vec::new()
                });
-               update_channel(&net_graph_msg_handler, &secp_ctx, node3_privkey, UnsignedChannelUpdate {
+               update_channel(&net_graph_msg_handler, &secp_ctx, &privkeys[2], UnsignedChannelUpdate {
                        chain_hash: genesis_block(Network::Testnet).header.bitcoin_hash(),
                        short_channel_id: 13,
                        timestamp: 1,
@@ -755,10 +745,11 @@ mod tests {
                        fee_proportional_millionths: 0,
                        excess_data: Vec::new()
                });
-               add_or_update_node(&net_graph_msg_handler, &secp_ctx, node3_privkey, NodeFeatures::from_le_bytes(id_to_feature_flags!(3)), 0);
-               add_channel(&net_graph_msg_handler, &secp_ctx, node3_privkey, node5_privkey, ChannelFeatures::from_le_bytes(id_to_feature_flags!(6)), 6);
 
-               update_channel(&net_graph_msg_handler, &secp_ctx, node3_privkey, UnsignedChannelUpdate {
+               add_or_update_node(&net_graph_msg_handler, &secp_ctx, &privkeys[2], NodeFeatures::from_le_bytes(id_to_feature_flags(3)), 0);
+
+               add_channel(&net_graph_msg_handler, &secp_ctx, &privkeys[2], &privkeys[4], ChannelFeatures::from_le_bytes(id_to_feature_flags(6)), 6);
+               update_channel(&net_graph_msg_handler, &secp_ctx, &privkeys[2], UnsignedChannelUpdate {
                        chain_hash: genesis_block(Network::Testnet).header.bitcoin_hash(),
                        short_channel_id: 6,
                        timestamp: 1,
@@ -770,7 +761,7 @@ mod tests {
                        fee_proportional_millionths: 0,
                        excess_data: Vec::new()
                });
-               update_channel(&net_graph_msg_handler, &secp_ctx, node5_privkey, UnsignedChannelUpdate {
+               update_channel(&net_graph_msg_handler, &secp_ctx, &privkeys[4], UnsignedChannelUpdate {
                        chain_hash: genesis_block(Network::Testnet).header.bitcoin_hash(),
                        short_channel_id: 6,
                        timestamp: 1,
@@ -780,11 +771,11 @@ mod tests {
                        htlc_maximum_msat: OptionalField::Absent,
                        fee_base_msat: 0,
                        fee_proportional_millionths: 0,
-                       excess_data: Vec::new()
+                       excess_data: Vec::new(),
                });
 
-               add_channel(&net_graph_msg_handler, &secp_ctx, node5_privkey, node4_privkey, ChannelFeatures::from_le_bytes(id_to_feature_flags!(11)), 11);
-               update_channel(&net_graph_msg_handler, &secp_ctx, node5_privkey, UnsignedChannelUpdate {
+               add_channel(&net_graph_msg_handler, &secp_ctx, &privkeys[4], &privkeys[3], ChannelFeatures::from_le_bytes(id_to_feature_flags(11)), 11);
+               update_channel(&net_graph_msg_handler, &secp_ctx, &privkeys[4], UnsignedChannelUpdate {
                        chain_hash: genesis_block(Network::Testnet).header.bitcoin_hash(),
                        short_channel_id: 11,
                        timestamp: 1,
@@ -796,7 +787,7 @@ mod tests {
                        fee_proportional_millionths: 0,
                        excess_data: Vec::new()
                });
-               update_channel(&net_graph_msg_handler, &secp_ctx, node4_privkey, UnsignedChannelUpdate {
+               update_channel(&net_graph_msg_handler, &secp_ctx, &privkeys[3], UnsignedChannelUpdate {
                        chain_hash: genesis_block(Network::Testnet).header.bitcoin_hash(),
                        short_channel_id: 11,
                        timestamp: 1,
@@ -808,12 +799,13 @@ mod tests {
                        fee_proportional_millionths: 0,
                        excess_data: Vec::new()
                });
-               add_or_update_node(&net_graph_msg_handler, &secp_ctx, node5_privkey, NodeFeatures::from_le_bytes(id_to_feature_flags!(5)), 0);
-               add_or_update_node(&net_graph_msg_handler, &secp_ctx, node4_privkey, NodeFeatures::from_le_bytes(id_to_feature_flags!(4)), 0);
 
-               add_channel(&net_graph_msg_handler, &secp_ctx, node3_privkey, node6_privkey, ChannelFeatures::from_le_bytes(id_to_feature_flags!(7)), 7);
+               add_or_update_node(&net_graph_msg_handler, &secp_ctx, &privkeys[4], NodeFeatures::from_le_bytes(id_to_feature_flags(5)), 0);
 
-               update_channel(&net_graph_msg_handler, &secp_ctx, node3_privkey, UnsignedChannelUpdate {
+               add_or_update_node(&net_graph_msg_handler, &secp_ctx, &privkeys[3], NodeFeatures::from_le_bytes(id_to_feature_flags(4)), 0);
+
+               add_channel(&net_graph_msg_handler, &secp_ctx, &privkeys[2], &privkeys[5], ChannelFeatures::from_le_bytes(id_to_feature_flags(7)), 7);
+               update_channel(&net_graph_msg_handler, &secp_ctx, &privkeys[2], UnsignedChannelUpdate {
                        chain_hash: genesis_block(Network::Testnet).header.bitcoin_hash(),
                        short_channel_id: 7,
                        timestamp: 1,
@@ -825,7 +817,7 @@ mod tests {
                        fee_proportional_millionths: 1000000,
                        excess_data: Vec::new()
                });
-               update_channel(&net_graph_msg_handler, &secp_ctx, node6_privkey, UnsignedChannelUpdate {
+               update_channel(&net_graph_msg_handler, &secp_ctx, &privkeys[5], UnsignedChannelUpdate {
                        chain_hash: genesis_block(Network::Testnet).header.bitcoin_hash(),
                        short_channel_id: 7,
                        timestamp: 1,
@@ -838,29 +830,42 @@ mod tests {
                        excess_data: Vec::new()
                });
 
-               add_or_update_node(&net_graph_msg_handler, &secp_ctx, node6_privkey, NodeFeatures::from_le_bytes(id_to_feature_flags!(6)), 0);
+               add_or_update_node(&net_graph_msg_handler, &secp_ctx, &privkeys[5], NodeFeatures::from_le_bytes(id_to_feature_flags(6)), 0);
+
+               (secp_ctx, net_graph_msg_handler, logger)
+       }
+
+       #[test]
+       fn simple_route_test() {
+               let (secp_ctx, net_graph_msg_handler, logger) = build_graph();
+               let (_, our_id, _, nodes) = get_nodes(&secp_ctx);
 
                // Simple route to 3 via 2
-               let route = get_route(&our_id, &net_graph_msg_handler.network_graph.read().unwrap(), &node3, None, &Vec::new(), 100, 42, Arc::clone(&logger)).unwrap();
+               let route = get_route(&our_id, &net_graph_msg_handler.network_graph.read().unwrap(), &nodes[2], None, &Vec::new(), 100, 42, Arc::clone(&logger)).unwrap();
                assert_eq!(route.paths[0].len(), 2);
 
-               assert_eq!(route.paths[0][0].pubkey, node2);
+               assert_eq!(route.paths[0][0].pubkey, nodes[1]);
                assert_eq!(route.paths[0][0].short_channel_id, 2);
                assert_eq!(route.paths[0][0].fee_msat, 100);
                assert_eq!(route.paths[0][0].cltv_expiry_delta, (4 << 8) | 1);
-               assert_eq!(route.paths[0][0].node_features.le_flags(), &id_to_feature_flags!(2));
-               assert_eq!(route.paths[0][0].channel_features.le_flags(), &id_to_feature_flags!(2));
+               assert_eq!(route.paths[0][0].node_features.le_flags(), &id_to_feature_flags(2));
+               assert_eq!(route.paths[0][0].channel_features.le_flags(), &id_to_feature_flags(2));
 
-               assert_eq!(route.paths[0][1].pubkey, node3);
+               assert_eq!(route.paths[0][1].pubkey, nodes[2]);
                assert_eq!(route.paths[0][1].short_channel_id, 4);
                assert_eq!(route.paths[0][1].fee_msat, 100);
                assert_eq!(route.paths[0][1].cltv_expiry_delta, 42);
-               assert_eq!(route.paths[0][1].node_features.le_flags(), &id_to_feature_flags!(3));
-               assert_eq!(route.paths[0][1].channel_features.le_flags(), &id_to_feature_flags!(4));
+               assert_eq!(route.paths[0][1].node_features.le_flags(), &id_to_feature_flags(3));
+               assert_eq!(route.paths[0][1].channel_features.le_flags(), &id_to_feature_flags(4));
+       }
 
+       #[test]
+       fn disable_channels_test() {
+               let (secp_ctx, net_graph_msg_handler, logger) = build_graph();
+               let (our_privkey, our_id, privkeys, nodes) = get_nodes(&secp_ctx);
 
                // // Disable channels 4 and 12 by flags=2
-               update_channel(&net_graph_msg_handler, &secp_ctx, node2_privkey, UnsignedChannelUpdate {
+               update_channel(&net_graph_msg_handler, &secp_ctx, &privkeys[1], UnsignedChannelUpdate {
                        chain_hash: genesis_block(Network::Testnet).header.bitcoin_hash(),
                        short_channel_id: 4,
                        timestamp: 2,
@@ -872,7 +877,7 @@ mod tests {
                        fee_proportional_millionths: 0,
                        excess_data: Vec::new()
                });
-               update_channel(&net_graph_msg_handler, &secp_ctx, our_privkey, UnsignedChannelUpdate {
+               update_channel(&net_graph_msg_handler, &secp_ctx, &our_privkey, UnsignedChannelUpdate {
                        chain_hash: genesis_block(Network::Testnet).header.bitcoin_hash(),
                        short_channel_id: 12,
                        timestamp: 2,
@@ -886,15 +891,15 @@ mod tests {
                });
 
                // If all the channels require some features we don't understand, route should fail
-               if let Err(LightningError{err, action: ErrorAction::IgnoreError}) = get_route(&our_id, &net_graph_msg_handler.network_graph.read().unwrap(), &node3, None, &Vec::new(), 100, 42, Arc::clone(&logger)) {
+               if let Err(LightningError{err, action: ErrorAction::IgnoreError}) = get_route(&our_id, &net_graph_msg_handler.network_graph.read().unwrap(), &nodes[2], None, &Vec::new(), 100, 42, Arc::clone(&logger)) {
                        assert_eq!(err, "Failed to find a path to the given destination");
                } else { panic!(); }
 
-               // If we specify a channel to node8, that overrides our local channel view and that gets used
+               // If we specify a channel to node7, that overrides our local channel view and that gets used
                let our_chans = vec![channelmanager::ChannelDetails {
                        channel_id: [0; 32],
                        short_channel_id: Some(42),
-                       remote_network_id: node8.clone(),
+                       remote_network_id: nodes[7].clone(),
                        counterparty_features: InitFeatures::from_le_bytes(vec![0b11]),
                        channel_value_satoshis: 0,
                        user_id: 0,
@@ -902,65 +907,46 @@ mod tests {
                        inbound_capacity_msat: 0,
                        is_live: true,
                }];
-               let route = get_route(&our_id, &net_graph_msg_handler.network_graph.read().unwrap(), &node3, Some(&our_chans),  &Vec::new(), 100, 42, Arc::clone(&logger)).unwrap();
+               let route = get_route(&our_id, &net_graph_msg_handler.network_graph.read().unwrap(), &nodes[2], Some(&our_chans),  &Vec::new(), 100, 42, Arc::clone(&logger)).unwrap();
                assert_eq!(route.paths[0].len(), 2);
 
-               assert_eq!(route.paths[0][0].pubkey, node8);
+               assert_eq!(route.paths[0][0].pubkey, nodes[7]);
                assert_eq!(route.paths[0][0].short_channel_id, 42);
                assert_eq!(route.paths[0][0].fee_msat, 200);
                assert_eq!(route.paths[0][0].cltv_expiry_delta, (13 << 8) | 1);
                assert_eq!(route.paths[0][0].node_features.le_flags(), &vec![0b11]); // it should also override our view of their features
                assert_eq!(route.paths[0][0].channel_features.le_flags(), &Vec::<u8>::new()); // No feature flags will meet the relevant-to-channel conversion
 
-               assert_eq!(route.paths[0][1].pubkey, node3);
+               assert_eq!(route.paths[0][1].pubkey, nodes[2]);
                assert_eq!(route.paths[0][1].short_channel_id, 13);
                assert_eq!(route.paths[0][1].fee_msat, 100);
                assert_eq!(route.paths[0][1].cltv_expiry_delta, 42);
-               assert_eq!(route.paths[0][1].node_features.le_flags(), &id_to_feature_flags!(3));
-               assert_eq!(route.paths[0][1].channel_features.le_flags(), &id_to_feature_flags!(13));
+               assert_eq!(route.paths[0][1].node_features.le_flags(), &id_to_feature_flags(3));
+               assert_eq!(route.paths[0][1].channel_features.le_flags(), &id_to_feature_flags(13));
+       }
+
+       #[test]
+       fn disable_node_test() {
+               let (secp_ctx, net_graph_msg_handler, logger) = build_graph();
+               let (_, our_id, privkeys, nodes) = get_nodes(&secp_ctx);
 
-               // Re-enable channels 4 and 12
-               update_channel(&net_graph_msg_handler, &secp_ctx, node2_privkey, UnsignedChannelUpdate {
-                       chain_hash: genesis_block(Network::Testnet).header.bitcoin_hash(),
-                       short_channel_id: 4,
-                       timestamp: 3,
-                       flags: 0, // to enable
-                       cltv_expiry_delta: (4 << 8) | 1,
-                       htlc_minimum_msat: 0,
-                       htlc_maximum_msat: OptionalField::Absent,
-                       fee_base_msat: 0,
-                       fee_proportional_millionths: 1000000,
-                       excess_data: Vec::new()
-               });
-               update_channel(&net_graph_msg_handler, &secp_ctx, our_privkey, UnsignedChannelUpdate {
-                       chain_hash: genesis_block(Network::Testnet).header.bitcoin_hash(),
-                       short_channel_id: 12,
-                       timestamp: 3,
-                       flags: 0, // to enable
-                       cltv_expiry_delta: u16::max_value(),
-                       htlc_minimum_msat: 0,
-                       htlc_maximum_msat: OptionalField::Absent,
-                       fee_base_msat: u32::max_value(),
-                       fee_proportional_millionths: u32::max_value(),
-                       excess_data: Vec::new()
-               });
                // Disable nodes 1, 2, and 8 by requiring unknown feature bits
                let mut unknown_features = NodeFeatures::known();
                unknown_features.set_required_unknown_bits();
-               add_or_update_node(&net_graph_msg_handler, &secp_ctx, node1_privkey, unknown_features.clone(), 1);
-               add_or_update_node(&net_graph_msg_handler, &secp_ctx, node2_privkey, unknown_features.clone(), 1);
-               add_or_update_node(&net_graph_msg_handler, &secp_ctx, node8_privkey, unknown_features.clone(), 1);
+               add_or_update_node(&net_graph_msg_handler, &secp_ctx, &privkeys[0], unknown_features.clone(), 1);
+               add_or_update_node(&net_graph_msg_handler, &secp_ctx, &privkeys[1], unknown_features.clone(), 1);
+               add_or_update_node(&net_graph_msg_handler, &secp_ctx, &privkeys[7], unknown_features.clone(), 1);
 
-               // // If all nodes require some features we don't understand, route should fail
-               // if let Err(LightningError{err, action: ErrorAction::IgnoreError}) = get_route(&our_id, &net_graph_msg_handler, &node3, None, &Vec::new(), 100, 42, Arc::clone(&logger)) {
-               //      assert_eq!(err, "Failed to find a path to the given destination");
-               // } else { panic!(); }
+               // If all nodes require some features we don't understand, route should fail
+               if let Err(LightningError{err, action: ErrorAction::IgnoreError}) = get_route(&our_id, &net_graph_msg_handler.network_graph.read().unwrap(), &nodes[2], None, &Vec::new(), 100, 42, Arc::clone(&logger)) {
+                       assert_eq!(err, "Failed to find a path to the given destination");
+               } else { panic!(); }
 
-               // If we specify a channel to node8, that overrides our local channel view and that gets used
+               // If we specify a channel to node7, that overrides our local channel view and that gets used
                let our_chans = vec![channelmanager::ChannelDetails {
                        channel_id: [0; 32],
                        short_channel_id: Some(42),
-                       remote_network_id: node8.clone(),
+                       remote_network_id: nodes[7].clone(),
                        counterparty_features: InitFeatures::from_le_bytes(vec![0b11]),
                        channel_value_satoshis: 0,
                        user_id: 0,
@@ -968,62 +954,63 @@ mod tests {
                        inbound_capacity_msat: 0,
                        is_live: true,
                }];
-               let route = get_route(&our_id, &net_graph_msg_handler.network_graph.read().unwrap(), &node3, Some(&our_chans), &Vec::new(), 100, 42, Arc::clone(&logger)).unwrap();
+               let route = get_route(&our_id, &net_graph_msg_handler.network_graph.read().unwrap(), &nodes[2], Some(&our_chans), &Vec::new(), 100, 42, Arc::clone(&logger)).unwrap();
                assert_eq!(route.paths[0].len(), 2);
 
-               assert_eq!(route.paths[0][0].pubkey, node8);
+               assert_eq!(route.paths[0][0].pubkey, nodes[7]);
                assert_eq!(route.paths[0][0].short_channel_id, 42);
                assert_eq!(route.paths[0][0].fee_msat, 200);
                assert_eq!(route.paths[0][0].cltv_expiry_delta, (13 << 8) | 1);
                assert_eq!(route.paths[0][0].node_features.le_flags(), &vec![0b11]); // it should also override our view of their features
                assert_eq!(route.paths[0][0].channel_features.le_flags(), &Vec::<u8>::new()); // No feature flags will meet the relevant-to-channel conversion
 
-               assert_eq!(route.paths[0][1].pubkey, node3);
+               assert_eq!(route.paths[0][1].pubkey, nodes[2]);
                assert_eq!(route.paths[0][1].short_channel_id, 13);
                assert_eq!(route.paths[0][1].fee_msat, 100);
                assert_eq!(route.paths[0][1].cltv_expiry_delta, 42);
-               assert_eq!(route.paths[0][1].node_features.le_flags(), &id_to_feature_flags!(3));
-               assert_eq!(route.paths[0][1].channel_features.le_flags(), &id_to_feature_flags!(13));
-
-               // Re-enable nodes 1, 2, and 8
-               add_or_update_node(&net_graph_msg_handler, &secp_ctx, node1_privkey, NodeFeatures::from_le_bytes(id_to_feature_flags!(1)), 2);
-               add_or_update_node(&net_graph_msg_handler, &secp_ctx, node2_privkey, NodeFeatures::from_le_bytes(id_to_feature_flags!(2)), 2);
-               add_or_update_node(&net_graph_msg_handler, &secp_ctx, node8_privkey, NodeFeatures::from_le_bytes(id_to_feature_flags!(8)), 2);
+               assert_eq!(route.paths[0][1].node_features.le_flags(), &id_to_feature_flags(3));
+               assert_eq!(route.paths[0][1].channel_features.le_flags(), &id_to_feature_flags(13));
 
                // Note that we don't test disabling node 3 and failing to route to it, as we (somewhat
                // naively) assume that the user checked the feature bits on the invoice, which override
                // the node_announcement.
+       }
+
+       #[test]
+       fn our_chans_test() {
+               let (secp_ctx, net_graph_msg_handler, logger) = build_graph();
+               let (_, our_id, _, nodes) = get_nodes(&secp_ctx);
 
                // Route to 1 via 2 and 3 because our channel to 1 is disabled
-               let route = get_route(&our_id, &net_graph_msg_handler.network_graph.read().unwrap(), &node1, None, &Vec::new(), 100, 42, Arc::clone(&logger)).unwrap();
+               let route = get_route(&our_id, &net_graph_msg_handler.network_graph.read().unwrap(), &nodes[0], None, &Vec::new(), 100, 42, Arc::clone(&logger)).unwrap();
                assert_eq!(route.paths[0].len(), 3);
 
-               assert_eq!(route.paths[0][0].pubkey, node2);
+               assert_eq!(route.paths[0][0].pubkey, nodes[1]);
                assert_eq!(route.paths[0][0].short_channel_id, 2);
                assert_eq!(route.paths[0][0].fee_msat, 200);
                assert_eq!(route.paths[0][0].cltv_expiry_delta, (4 << 8) | 1);
-               assert_eq!(route.paths[0][0].node_features.le_flags(), &id_to_feature_flags!(2));
-               assert_eq!(route.paths[0][0].channel_features.le_flags(), &id_to_feature_flags!(2));
+               assert_eq!(route.paths[0][0].node_features.le_flags(), &id_to_feature_flags(2));
+               assert_eq!(route.paths[0][0].channel_features.le_flags(), &id_to_feature_flags(2));
 
-               assert_eq!(route.paths[0][1].pubkey, node3);
+               assert_eq!(route.paths[0][1].pubkey, nodes[2]);
                assert_eq!(route.paths[0][1].short_channel_id, 4);
                assert_eq!(route.paths[0][1].fee_msat, 100);
                assert_eq!(route.paths[0][1].cltv_expiry_delta, (3 << 8) | 2);
-               assert_eq!(route.paths[0][1].node_features.le_flags(), &id_to_feature_flags!(3));
-               assert_eq!(route.paths[0][1].channel_features.le_flags(), &id_to_feature_flags!(4));
+               assert_eq!(route.paths[0][1].node_features.le_flags(), &id_to_feature_flags(3));
+               assert_eq!(route.paths[0][1].channel_features.le_flags(), &id_to_feature_flags(4));
 
-               assert_eq!(route.paths[0][2].pubkey, node1);
+               assert_eq!(route.paths[0][2].pubkey, nodes[0]);
                assert_eq!(route.paths[0][2].short_channel_id, 3);
                assert_eq!(route.paths[0][2].fee_msat, 100);
                assert_eq!(route.paths[0][2].cltv_expiry_delta, 42);
-               assert_eq!(route.paths[0][2].node_features.le_flags(), &id_to_feature_flags!(1));
-               assert_eq!(route.paths[0][2].channel_features.le_flags(), &id_to_feature_flags!(3));
+               assert_eq!(route.paths[0][2].node_features.le_flags(), &id_to_feature_flags(1));
+               assert_eq!(route.paths[0][2].channel_features.le_flags(), &id_to_feature_flags(3));
 
-               // If we specify a channel to node8, that overrides our local channel view and that gets used
+               // If we specify a channel to node7, that overrides our local channel view and that gets used
                let our_chans = vec![channelmanager::ChannelDetails {
                        channel_id: [0; 32],
                        short_channel_id: Some(42),
-                       remote_network_id: node8.clone(),
+                       remote_network_id: nodes[7].clone(),
                        counterparty_features: InitFeatures::from_le_bytes(vec![0b11]),
                        channel_value_satoshis: 0,
                        user_id: 0,
@@ -1031,96 +1018,110 @@ mod tests {
                        inbound_capacity_msat: 0,
                        is_live: true,
                }];
-               let route = get_route(&our_id, &net_graph_msg_handler.network_graph.read().unwrap(), &node3, Some(&our_chans), &Vec::new(), 100, 42, Arc::clone(&logger)).unwrap();
+               let route = get_route(&our_id, &net_graph_msg_handler.network_graph.read().unwrap(), &nodes[2], Some(&our_chans), &Vec::new(), 100, 42, Arc::clone(&logger)).unwrap();
                assert_eq!(route.paths[0].len(), 2);
 
-               assert_eq!(route.paths[0][0].pubkey, node8);
+               assert_eq!(route.paths[0][0].pubkey, nodes[7]);
                assert_eq!(route.paths[0][0].short_channel_id, 42);
                assert_eq!(route.paths[0][0].fee_msat, 200);
                assert_eq!(route.paths[0][0].cltv_expiry_delta, (13 << 8) | 1);
                assert_eq!(route.paths[0][0].node_features.le_flags(), &vec![0b11]);
                assert_eq!(route.paths[0][0].channel_features.le_flags(), &Vec::<u8>::new()); // No feature flags will meet the relevant-to-channel conversion
 
-               assert_eq!(route.paths[0][1].pubkey, node3);
+               assert_eq!(route.paths[0][1].pubkey, nodes[2]);
                assert_eq!(route.paths[0][1].short_channel_id, 13);
                assert_eq!(route.paths[0][1].fee_msat, 100);
                assert_eq!(route.paths[0][1].cltv_expiry_delta, 42);
-               assert_eq!(route.paths[0][1].node_features.le_flags(), &id_to_feature_flags!(3));
-               assert_eq!(route.paths[0][1].channel_features.le_flags(), &id_to_feature_flags!(13));
+               assert_eq!(route.paths[0][1].node_features.le_flags(), &id_to_feature_flags(3));
+               assert_eq!(route.paths[0][1].channel_features.le_flags(), &id_to_feature_flags(13));
+       }
 
+       fn last_hops(nodes: &Vec<PublicKey>) -> Vec<RouteHint> {
                let zero_fees = RoutingFees {
                        base_msat: 0,
                        proportional_millionths: 0,
                };
-               let mut last_hops = vec!(RouteHint {
-                               src_node_id: node4.clone(),
-                               short_channel_id: 8,
-                               fees: zero_fees,
-                               cltv_expiry_delta: (8 << 8) | 1,
-                               htlc_minimum_msat: 0,
-                       }, RouteHint {
-                               src_node_id: node5.clone(),
-                               short_channel_id: 9,
-                               fees: RoutingFees {
-                                       base_msat: 1001,
-                                       proportional_millionths: 0,
-                               },
-                               cltv_expiry_delta: (9 << 8) | 1,
-                               htlc_minimum_msat: 0,
-                       }, RouteHint {
-                               src_node_id: node6.clone(),
-                               short_channel_id: 10,
-                               fees: zero_fees,
-                               cltv_expiry_delta: (10 << 8) | 1,
-                               htlc_minimum_msat: 0,
-                       });
+               vec!(RouteHint {
+                       src_node_id: nodes[3].clone(),
+                       short_channel_id: 8,
+                       fees: zero_fees,
+                       cltv_expiry_delta: (8 << 8) | 1,
+                       htlc_minimum_msat: 0,
+               }, RouteHint {
+                       src_node_id: nodes[4].clone(),
+                       short_channel_id: 9,
+                       fees: RoutingFees {
+                               base_msat: 1001,
+                               proportional_millionths: 0,
+                       },
+                       cltv_expiry_delta: (9 << 8) | 1,
+                       htlc_minimum_msat: 0,
+               }, RouteHint {
+                       src_node_id: nodes[5].clone(),
+                       short_channel_id: 10,
+                       fees: zero_fees,
+                       cltv_expiry_delta: (10 << 8) | 1,
+                       htlc_minimum_msat: 0,
+               })
+       }
+
+       #[test]
+       fn last_hops_test() {
+               let (secp_ctx, net_graph_msg_handler, logger) = build_graph();
+               let (_, our_id, _, nodes) = get_nodes(&secp_ctx);
 
                // Simple test across 2, 3, 5, and 4 via a last_hop channel
-               let route = get_route(&our_id, &net_graph_msg_handler.network_graph.read().unwrap(), &node7, None, &last_hops, 100, 42, Arc::clone(&logger)).unwrap();
+               let route = get_route(&our_id, &net_graph_msg_handler.network_graph.read().unwrap(), &nodes[6], None, &last_hops(&nodes), 100, 42, Arc::clone(&logger)).unwrap();
                assert_eq!(route.paths[0].len(), 5);
 
-               assert_eq!(route.paths[0][0].pubkey, node2);
+               assert_eq!(route.paths[0][0].pubkey, nodes[1]);
                assert_eq!(route.paths[0][0].short_channel_id, 2);
                assert_eq!(route.paths[0][0].fee_msat, 100);
                assert_eq!(route.paths[0][0].cltv_expiry_delta, (4 << 8) | 1);
-               assert_eq!(route.paths[0][0].node_features.le_flags(), &id_to_feature_flags!(2));
-               assert_eq!(route.paths[0][0].channel_features.le_flags(), &id_to_feature_flags!(2));
+               assert_eq!(route.paths[0][0].node_features.le_flags(), &id_to_feature_flags(2));
+               assert_eq!(route.paths[0][0].channel_features.le_flags(), &id_to_feature_flags(2));
 
-               assert_eq!(route.paths[0][1].pubkey, node3);
+               assert_eq!(route.paths[0][1].pubkey, nodes[2]);
                assert_eq!(route.paths[0][1].short_channel_id, 4);
                assert_eq!(route.paths[0][1].fee_msat, 0);
                assert_eq!(route.paths[0][1].cltv_expiry_delta, (6 << 8) | 1);
-               assert_eq!(route.paths[0][1].node_features.le_flags(), &id_to_feature_flags!(3));
-               assert_eq!(route.paths[0][1].channel_features.le_flags(), &id_to_feature_flags!(4));
+               assert_eq!(route.paths[0][1].node_features.le_flags(), &id_to_feature_flags(3));
+               assert_eq!(route.paths[0][1].channel_features.le_flags(), &id_to_feature_flags(4));
 
-               assert_eq!(route.paths[0][2].pubkey, node5);
+               assert_eq!(route.paths[0][2].pubkey, nodes[4]);
                assert_eq!(route.paths[0][2].short_channel_id, 6);
                assert_eq!(route.paths[0][2].fee_msat, 0);
                assert_eq!(route.paths[0][2].cltv_expiry_delta, (11 << 8) | 1);
-               assert_eq!(route.paths[0][2].node_features.le_flags(), &id_to_feature_flags!(5));
-               assert_eq!(route.paths[0][2].channel_features.le_flags(), &id_to_feature_flags!(6));
+               assert_eq!(route.paths[0][2].node_features.le_flags(), &id_to_feature_flags(5));
+               assert_eq!(route.paths[0][2].channel_features.le_flags(), &id_to_feature_flags(6));
 
-               assert_eq!(route.paths[0][3].pubkey, node4);
+               assert_eq!(route.paths[0][3].pubkey, nodes[3]);
                assert_eq!(route.paths[0][3].short_channel_id, 11);
                assert_eq!(route.paths[0][3].fee_msat, 0);
                assert_eq!(route.paths[0][3].cltv_expiry_delta, (8 << 8) | 1);
                // If we have a peer in the node map, we'll use their features here since we don't have
                // a way of figuring out their features from the invoice:
-               assert_eq!(route.paths[0][3].node_features.le_flags(), &id_to_feature_flags!(4));
-               assert_eq!(route.paths[0][3].channel_features.le_flags(), &id_to_feature_flags!(11));
+               assert_eq!(route.paths[0][3].node_features.le_flags(), &id_to_feature_flags(4));
+               assert_eq!(route.paths[0][3].channel_features.le_flags(), &id_to_feature_flags(11));
 
-               assert_eq!(route.paths[0][4].pubkey, node7);
+               assert_eq!(route.paths[0][4].pubkey, nodes[6]);
                assert_eq!(route.paths[0][4].short_channel_id, 8);
                assert_eq!(route.paths[0][4].fee_msat, 100);
                assert_eq!(route.paths[0][4].cltv_expiry_delta, 42);
                assert_eq!(route.paths[0][4].node_features.le_flags(), &Vec::<u8>::new()); // We dont pass flags in from invoices yet
                assert_eq!(route.paths[0][4].channel_features.le_flags(), &Vec::<u8>::new()); // We can't learn any flags from invoices, sadly
+       }
+
+       #[test]
+       fn our_chans_last_hop_connect_test() {
+               let (secp_ctx, net_graph_msg_handler, logger) = build_graph();
+               let (_, our_id, _, nodes) = get_nodes(&secp_ctx);
 
                // Simple test with outbound channel to 4 to test that last_hops and first_hops connect
                let our_chans = vec![channelmanager::ChannelDetails {
                        channel_id: [0; 32],
                        short_channel_id: Some(42),
-                       remote_network_id: node4.clone(),
+                       remote_network_id: nodes[3].clone(),
                        counterparty_features: InitFeatures::from_le_bytes(vec![0b11]),
                        channel_value_satoshis: 0,
                        user_id: 0,
@@ -1128,17 +1129,18 @@ mod tests {
                        inbound_capacity_msat: 0,
                        is_live: true,
                }];
-               let route = get_route(&our_id, &net_graph_msg_handler.network_graph.read().unwrap(), &node7, Some(&our_chans), &last_hops, 100, 42, Arc::clone(&logger)).unwrap();
+               let mut last_hops = last_hops(&nodes);
+               let route = get_route(&our_id, &net_graph_msg_handler.network_graph.read().unwrap(), &nodes[6], Some(&our_chans), &last_hops, 100, 42, Arc::clone(&logger)).unwrap();
                assert_eq!(route.paths[0].len(), 2);
 
-               assert_eq!(route.paths[0][0].pubkey, node4);
+               assert_eq!(route.paths[0][0].pubkey, nodes[3]);
                assert_eq!(route.paths[0][0].short_channel_id, 42);
                assert_eq!(route.paths[0][0].fee_msat, 0);
                assert_eq!(route.paths[0][0].cltv_expiry_delta, (8 << 8) | 1);
                assert_eq!(route.paths[0][0].node_features.le_flags(), &vec![0b11]);
                assert_eq!(route.paths[0][0].channel_features.le_flags(), &Vec::<u8>::new()); // No feature flags will meet the relevant-to-channel conversion
 
-               assert_eq!(route.paths[0][1].pubkey, node7);
+               assert_eq!(route.paths[0][1].pubkey, nodes[6]);
                assert_eq!(route.paths[0][1].short_channel_id, 8);
                assert_eq!(route.paths[0][1].fee_msat, 100);
                assert_eq!(route.paths[0][1].cltv_expiry_delta, 42);
@@ -1148,33 +1150,33 @@ mod tests {
                last_hops[0].fees.base_msat = 1000;
 
                // Revert to via 6 as the fee on 8 goes up
-               let route = get_route(&our_id, &net_graph_msg_handler.network_graph.read().unwrap(), &node7, None, &last_hops, 100, 42, Arc::clone(&logger)).unwrap();
+               let route = get_route(&our_id, &net_graph_msg_handler.network_graph.read().unwrap(), &nodes[6], None, &last_hops, 100, 42, Arc::clone(&logger)).unwrap();
                assert_eq!(route.paths[0].len(), 4);
 
-               assert_eq!(route.paths[0][0].pubkey, node2);
+               assert_eq!(route.paths[0][0].pubkey, nodes[1]);
                assert_eq!(route.paths[0][0].short_channel_id, 2);
                assert_eq!(route.paths[0][0].fee_msat, 200); // fee increased as its % of value transferred across node
                assert_eq!(route.paths[0][0].cltv_expiry_delta, (4 << 8) | 1);
-               assert_eq!(route.paths[0][0].node_features.le_flags(), &id_to_feature_flags!(2));
-               assert_eq!(route.paths[0][0].channel_features.le_flags(), &id_to_feature_flags!(2));
+               assert_eq!(route.paths[0][0].node_features.le_flags(), &id_to_feature_flags(2));
+               assert_eq!(route.paths[0][0].channel_features.le_flags(), &id_to_feature_flags(2));
 
-               assert_eq!(route.paths[0][1].pubkey, node3);
+               assert_eq!(route.paths[0][1].pubkey, nodes[2]);
                assert_eq!(route.paths[0][1].short_channel_id, 4);
                assert_eq!(route.paths[0][1].fee_msat, 100);
                assert_eq!(route.paths[0][1].cltv_expiry_delta, (7 << 8) | 1);
-               assert_eq!(route.paths[0][1].node_features.le_flags(), &id_to_feature_flags!(3));
-               assert_eq!(route.paths[0][1].channel_features.le_flags(), &id_to_feature_flags!(4));
+               assert_eq!(route.paths[0][1].node_features.le_flags(), &id_to_feature_flags(3));
+               assert_eq!(route.paths[0][1].channel_features.le_flags(), &id_to_feature_flags(4));
 
-               assert_eq!(route.paths[0][2].pubkey, node6);
+               assert_eq!(route.paths[0][2].pubkey, nodes[5]);
                assert_eq!(route.paths[0][2].short_channel_id, 7);
                assert_eq!(route.paths[0][2].fee_msat, 0);
                assert_eq!(route.paths[0][2].cltv_expiry_delta, (10 << 8) | 1);
                // If we have a peer in the node map, we'll use their features here since we don't have
                // a way of figuring out their features from the invoice:
-               assert_eq!(route.paths[0][2].node_features.le_flags(), &id_to_feature_flags!(6));
-               assert_eq!(route.paths[0][2].channel_features.le_flags(), &id_to_feature_flags!(7));
+               assert_eq!(route.paths[0][2].node_features.le_flags(), &id_to_feature_flags(6));
+               assert_eq!(route.paths[0][2].channel_features.le_flags(), &id_to_feature_flags(7));
 
-               assert_eq!(route.paths[0][3].pubkey, node7);
+               assert_eq!(route.paths[0][3].pubkey, nodes[6]);
                assert_eq!(route.paths[0][3].short_channel_id, 10);
                assert_eq!(route.paths[0][3].fee_msat, 100);
                assert_eq!(route.paths[0][3].cltv_expiry_delta, 42);
@@ -1182,40 +1184,40 @@ mod tests {
                assert_eq!(route.paths[0][3].channel_features.le_flags(), &Vec::<u8>::new()); // We can't learn any flags from invoices, sadly
 
                // ...but still use 8 for larger payments as 6 has a variable feerate
-               let route = get_route(&our_id, &net_graph_msg_handler.network_graph.read().unwrap(), &node7, None, &last_hops, 2000, 42, Arc::clone(&logger)).unwrap();
+               let route = get_route(&our_id, &net_graph_msg_handler.network_graph.read().unwrap(), &nodes[6], None, &last_hops, 2000, 42, Arc::clone(&logger)).unwrap();
                assert_eq!(route.paths[0].len(), 5);
 
-               assert_eq!(route.paths[0][0].pubkey, node2);
+               assert_eq!(route.paths[0][0].pubkey, nodes[1]);
                assert_eq!(route.paths[0][0].short_channel_id, 2);
                assert_eq!(route.paths[0][0].fee_msat, 3000);
                assert_eq!(route.paths[0][0].cltv_expiry_delta, (4 << 8) | 1);
-               assert_eq!(route.paths[0][0].node_features.le_flags(), &id_to_feature_flags!(2));
-               assert_eq!(route.paths[0][0].channel_features.le_flags(), &id_to_feature_flags!(2));
+               assert_eq!(route.paths[0][0].node_features.le_flags(), &id_to_feature_flags(2));
+               assert_eq!(route.paths[0][0].channel_features.le_flags(), &id_to_feature_flags(2));
 
-               assert_eq!(route.paths[0][1].pubkey, node3);
+               assert_eq!(route.paths[0][1].pubkey, nodes[2]);
                assert_eq!(route.paths[0][1].short_channel_id, 4);
                assert_eq!(route.paths[0][1].fee_msat, 0);
                assert_eq!(route.paths[0][1].cltv_expiry_delta, (6 << 8) | 1);
-               assert_eq!(route.paths[0][1].node_features.le_flags(), &id_to_feature_flags!(3));
-               assert_eq!(route.paths[0][1].channel_features.le_flags(), &id_to_feature_flags!(4));
+               assert_eq!(route.paths[0][1].node_features.le_flags(), &id_to_feature_flags(3));
+               assert_eq!(route.paths[0][1].channel_features.le_flags(), &id_to_feature_flags(4));
 
-               assert_eq!(route.paths[0][2].pubkey, node5);
+               assert_eq!(route.paths[0][2].pubkey, nodes[4]);
                assert_eq!(route.paths[0][2].short_channel_id, 6);
                assert_eq!(route.paths[0][2].fee_msat, 0);
                assert_eq!(route.paths[0][2].cltv_expiry_delta, (11 << 8) | 1);
-               assert_eq!(route.paths[0][2].node_features.le_flags(), &id_to_feature_flags!(5));
-               assert_eq!(route.paths[0][2].channel_features.le_flags(), &id_to_feature_flags!(6));
+               assert_eq!(route.paths[0][2].node_features.le_flags(), &id_to_feature_flags(5));
+               assert_eq!(route.paths[0][2].channel_features.le_flags(), &id_to_feature_flags(6));
 
-               assert_eq!(route.paths[0][3].pubkey, node4);
+               assert_eq!(route.paths[0][3].pubkey, nodes[3]);
                assert_eq!(route.paths[0][3].short_channel_id, 11);
                assert_eq!(route.paths[0][3].fee_msat, 1000);
                assert_eq!(route.paths[0][3].cltv_expiry_delta, (8 << 8) | 1);
                // If we have a peer in the node map, we'll use their features here since we don't have
                // a way of figuring out their features from the invoice:
-               assert_eq!(route.paths[0][3].node_features.le_flags(), &id_to_feature_flags!(4));
-               assert_eq!(route.paths[0][3].channel_features.le_flags(), &id_to_feature_flags!(11));
+               assert_eq!(route.paths[0][3].node_features.le_flags(), &id_to_feature_flags(4));
+               assert_eq!(route.paths[0][3].channel_features.le_flags(), &id_to_feature_flags(11));
 
-               assert_eq!(route.paths[0][4].pubkey, node7);
+               assert_eq!(route.paths[0][4].pubkey, nodes[6]);
                assert_eq!(route.paths[0][4].short_channel_id, 8);
                assert_eq!(route.paths[0][4].fee_msat, 2000);
                assert_eq!(route.paths[0][4].cltv_expiry_delta, 42);
index 559277d2a68c674948479d329861e2471d719c81..78263ecacad311ff8590d62aa740fc9cbb412794 100644 (file)
@@ -15,7 +15,7 @@ use ln::channelmonitor;
 use ln::features::{ChannelFeatures, InitFeatures};
 use ln::msgs;
 use ln::msgs::OptionalField;
-use ln::channelmonitor::HTLCUpdate;
+use ln::channelmonitor::MonitorEvent;
 use util::enforcing_trait_impls::EnforcingChannelKeys;
 use util::events;
 use util::logger::{Logger, Level, Record};
@@ -129,8 +129,8 @@ impl<'a> channelmonitor::ManyChannelMonitor for TestChannelMonitor<'a> {
                ret
        }
 
-       fn get_and_clear_pending_htlcs_updated(&self) -> Vec<HTLCUpdate> {
-               return self.simple_monitor.get_and_clear_pending_htlcs_updated();
+       fn get_and_clear_pending_monitor_events(&self) -> Vec<MonitorEvent> {
+               return self.simple_monitor.get_and_clear_pending_monitor_events();
        }
 }