Expose manual-update methods in NetworkGraph.
authorMatt Corallo <git@bluematt.me>
Thu, 12 Nov 2020 22:16:14 +0000 (17:16 -0500)
committerMatt Corallo <git@bluematt.me>
Tue, 24 Nov 2020 16:04:11 +0000 (11:04 -0500)
These functions were created but previously not exported, however
they are useful if we want to skip signature checking when accepting
routing messages (which we really should be doing in the routing
fuzzer).

lightning/src/routing/network_graph.rs

index e7431502f0e477a7660147a0ea3ec855ca774a18..932f3779deff99d4456a4d81f3ec6c43310810da 100644 (file)
@@ -562,9 +562,14 @@ impl NetworkGraph {
                }
        }
 
-       /// For an already known node (from channel announcements), update its stored properties from a given node announcement
+       /// For an already known node (from channel announcements), update its stored properties from a given node announcement.
+       ///
+       /// You probably don't want to call this directly, instead relying on a NetGraphMsgHandler's
+       /// RoutingMessageHandler implementation to call it indirectly. This may be useful to accept
+       /// routing messages without checking their signatures.
+       ///
        /// Announcement signatures are checked here only if Secp256k1 object is provided.
-       fn update_node_from_announcement(&mut self, msg: &msgs::NodeAnnouncement, secp_ctx: Option<&Secp256k1<secp256k1::VerifyOnly>>) -> Result<bool, LightningError> {
+       pub fn update_node_from_announcement<T: secp256k1::Verification>(&mut self, msg: &msgs::NodeAnnouncement, secp_ctx: Option<&Secp256k1<T>>) -> Result<bool, LightningError> {
                if let Some(sig_verifier) = secp_ctx {
                        let msg_hash = hash_to_message!(&Sha256dHash::hash(&msg.contents.encode()[..])[..]);
                        secp_verify_sig!(sig_verifier, &msg_hash, &msg.signature, &msg.contents.node_id);
@@ -594,13 +599,27 @@ impl NetworkGraph {
                }
        }
 
-       /// For a new or already known (from previous announcement) channel, store or update channel info.
-       /// Also store nodes (if not stored yet) the channel is between, and make node aware of this channel.
-       /// Checking utxo on-chain is useful if we receive an update for already known channel id,
-       /// which is probably result of a reorg. In that case, we update channel info only if the
-       /// utxo was checked, otherwise stick to the existing update, to prevent DoS risks.
+       /// Store or update channel info from a channel announcement.
+       ///
+       /// You probably don't want to call this directly, instead relying on a NetGraphMsgHandler's
+       /// RoutingMessageHandler implementation to call it indirectly. This may be useful to accept
+       /// routing messages without checking their signatures.
+       ///
+       /// If the channel has been confirmed to exist on chain (with correctly-formatted scripts on
+       /// chain), set utxo_value to the value of the output on chain, otherwise leave it as None.
+       /// The UTXO value is then used in routing calculation if we have no better information on the
+       /// maximum HTLC value that can be sent over the channel.
+       ///
+       /// Further, setting utxo_value to Some indicates that the announcement message is genuine,
+       /// allowing us to update existing channel data in the case of reorgs or to replace bogus
+       /// channel data generated by a DoS attacker.
+       ///
        /// Announcement signatures are checked here only if Secp256k1 object is provided.
-       fn update_channel_from_announcement(&mut self, msg: &msgs::ChannelAnnouncement, utxo_value: Option<u64>, secp_ctx: Option<&Secp256k1<secp256k1::VerifyOnly>>) -> Result<bool, LightningError> {
+       pub fn update_channel_from_announcement<T: secp256k1::Verification>(&mut self, msg: &msgs::ChannelAnnouncement, utxo_value: Option<u64>, secp_ctx: Option<&Secp256k1<T>>) -> Result<bool, LightningError> {
+               if msg.contents.node_id_1 == msg.contents.node_id_2 || msg.contents.bitcoin_key_1 == msg.contents.bitcoin_key_2 {
+                       return Err(LightningError{err: "Channel announcement node had a channel with itself".to_owned(), action: ErrorAction::IgnoreError});
+               }
+
                if let Some(sig_verifier) = secp_ctx {
                        let msg_hash = hash_to_message!(&Sha256dHash::hash(&msg.contents.encode()[..])[..]);
                        secp_verify_sig!(sig_verifier, &msg_hash, &msg.node_signature_1, &msg.contents.node_id_1);
@@ -699,8 +718,13 @@ impl NetworkGraph {
        }
 
        /// For an already known (from announcement) channel, update info about one of the directions of a channel.
+       ///
+       /// You probably don't want to call this directly, instead relying on a NetGraphMsgHandler's
+       /// RoutingMessageHandler implementation to call it indirectly. This may be useful to accept
+       /// routing messages without checking their signatures.
+       ///
        /// Announcement signatures are checked here only if Secp256k1 object is provided.
-       fn update_channel(&mut self, msg: &msgs::ChannelUpdate, secp_ctx: Option<&Secp256k1<secp256k1::VerifyOnly>>) -> Result<bool, LightningError> {
+       pub fn update_channel(&mut self, msg: &msgs::ChannelUpdate, secp_ctx: Option<&Secp256k1<secp256k1::VerifyOnly>>) -> Result<bool, LightningError> {
                let dest_node_id;
                let chan_enabled = msg.contents.flags & (1 << 1) != (1 << 1);
                let chan_was_enabled;