Add a new method `read_chan_signer` to `KeysInterface`
authorMatt Corallo <git@bluematt.me>
Wed, 25 Nov 2020 17:23:47 +0000 (12:23 -0500)
committerMatt Corallo <git@bluematt.me>
Mon, 4 Jan 2021 17:40:40 +0000 (12:40 -0500)
This adds a new method to the general cross-channel `KeysInterface`
which requires it to handle the deserialization of per-channel
signer objects. This allows the deserialization of per-channel
signers to have more context available, which, in the case of the
C bindings, includes the actual KeysInterface information itself.

fuzz/src/chanmon_consistency.rs
fuzz/src/full_stack.rs
lightning/src/chain/keysinterface.rs
lightning/src/ln/channel.rs
lightning/src/ln/functional_tests.rs
lightning/src/util/test_utils.rs

index 732f0f5b1832028608ecab5b022ea22d446bc07c..06bcfa4b7c80003a435f13f2595b26f69b810371 100644 (file)
@@ -37,7 +37,7 @@ use lightning::chain::chaininterface::{BroadcasterInterface, ConfirmationTarget,
 use lightning::chain::keysinterface::{KeysInterface, InMemoryChannelKeys};
 use lightning::ln::channelmanager::{ChannelManager, PaymentHash, PaymentPreimage, PaymentSecret, PaymentSendFailure, ChannelManagerReadArgs};
 use lightning::ln::features::{ChannelFeatures, InitFeatures, NodeFeatures};
-use lightning::ln::msgs::{CommitmentUpdate, ChannelMessageHandler, ErrorAction, UpdateAddHTLC, Init};
+use lightning::ln::msgs::{CommitmentUpdate, ChannelMessageHandler, DecodeError, ErrorAction, UpdateAddHTLC, Init};
 use lightning::util::enforcing_trait_impls::EnforcingChannelKeys;
 use lightning::util::errors::APIError;
 use lightning::util::events;
@@ -184,6 +184,10 @@ impl KeysInterface for KeyProvider {
                let id = self.rand_bytes_id.fetch_add(1, atomic::Ordering::Relaxed);
                [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, id, 11, self.node_id]
        }
+
+       fn read_chan_signer(&self, data: &[u8]) -> Result<EnforcingChannelKeys, DecodeError> {
+               EnforcingChannelKeys::read(&mut std::io::Cursor::new(data))
+       }
 }
 
 #[inline]
index 6375d0765d76a3d4a7940d4781ef2b574b90b564..915a6cba1ea618fa576bed1d59fcff705c7516c4 100644 (file)
@@ -33,12 +33,14 @@ use lightning::chain::transaction::OutPoint;
 use lightning::chain::keysinterface::{InMemoryChannelKeys, KeysInterface};
 use lightning::ln::channelmanager::{ChannelManager, PaymentHash, PaymentPreimage, PaymentSecret};
 use lightning::ln::peer_handler::{MessageHandler,PeerManager,SocketDescriptor};
+use lightning::ln::msgs::DecodeError;
 use lightning::routing::router::get_route;
 use lightning::routing::network_graph::NetGraphMsgHandler;
+use lightning::util::config::UserConfig;
 use lightning::util::events::{EventsProvider,Event};
 use lightning::util::enforcing_trait_impls::EnforcingChannelKeys;
 use lightning::util::logger::Logger;
-use lightning::util::config::UserConfig;
+use lightning::util::ser::Readable;
 
 use utils::test_logger;
 use utils::test_persister::TestPersister;
@@ -299,6 +301,10 @@ impl KeysInterface for KeyProvider {
                [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
                (ctr >> 8*7) as u8, (ctr >> 8*6) as u8, (ctr >> 8*5) as u8, (ctr >> 8*4) as u8, (ctr >> 8*3) as u8, (ctr >> 8*2) as u8, (ctr >> 8*1) as u8, 14, (ctr >> 8*0) as u8]
        }
+
+       fn read_chan_signer(&self, data: &[u8]) -> Result<EnforcingChannelKeys, DecodeError> {
+               EnforcingChannelKeys::read(&mut std::io::Cursor::new(data))
+       }
 }
 
 #[inline]
index 47ad84bbc596f1de3e0e387df7add2a67ad859a8..4a3a937a5c4586824ce0b875525b737ca39bdd67 100644 (file)
@@ -344,6 +344,14 @@ pub trait KeysInterface: Send + Sync {
        /// onion packets and for temporary channel IDs. There is no requirement that these be
        /// persisted anywhere, though they must be unique across restarts.
        fn get_secure_random_bytes(&self) -> [u8; 32];
+
+       /// Reads a `ChanKeySigner` for this `KeysInterface` from the given input stream.
+       /// This is only called during deserialization of other objects which contain
+       /// `ChannelKeys`-implementing objects (ie `ChannelMonitor`s and `ChannelManager`s).
+       /// The bytes are exactly those which `<Self::ChanKeySigner as Writeable>::write()` writes, and
+       /// contain no versioning scheme. You may wish to include your own version prefix and ensure
+       /// you've read all of the provided bytes to ensure no corruption occurred.
+       fn read_chan_signer(&self, reader: &[u8]) -> Result<Self::ChanKeySigner, DecodeError>;
 }
 
 #[derive(Clone)]
@@ -809,4 +817,8 @@ impl KeysInterface for KeysManager {
                sha.input(b"Unique Secure Random Bytes Salt");
                Sha256::from_engine(sha).into_inner()
        }
+
+       fn read_chan_signer(&self, reader: &[u8]) -> Result<Self::ChanKeySigner, DecodeError> {
+               InMemoryChannelKeys::read(&mut std::io::Cursor::new(reader))
+       }
 }
index 5477485d5a16ee74e9bcb22472b99e627e07ef56..62d3968fd755c1a1531012316debfc18ec677249 100644 (file)
@@ -4472,7 +4472,7 @@ mod tests {
        use ln::channel::{Channel,ChannelKeys,InboundHTLCOutput,OutboundHTLCOutput,InboundHTLCState,OutboundHTLCState,HTLCOutputInCommitment,TxCreationKeys};
        use ln::channel::MAX_FUNDING_SATOSHIS;
        use ln::features::InitFeatures;
-       use ln::msgs::{OptionalField, DataLossProtect};
+       use ln::msgs::{OptionalField, DataLossProtect, DecodeError};
        use ln::chan_utils;
        use ln::chan_utils::{ChannelPublicKeys, HolderCommitmentTransaction, CounterpartyChannelTransactionParameters};
        use chain::chaininterface::{FeeEstimator,ConfirmationTarget};
@@ -4528,6 +4528,7 @@ mod tests {
                        self.chan_keys.clone()
                }
                fn get_secure_random_bytes(&self) -> [u8; 32] { [0; 32] }
+               fn read_chan_signer(&self, data: &[u8]) -> Result<Self::ChanKeySigner, DecodeError> { panic!(); }
        }
 
        fn public_from_secret_hex(secp_ctx: &Secp256k1<All>, hex: &str) -> PublicKey {
index 98b166285a3991ee13b1d131eee3fdda9916c297..8077d644a9e28c2881b18b233fd86a41208a2269 100644 (file)
@@ -7322,7 +7322,7 @@ fn test_user_configurable_csv_delay() {
        let nodes = create_network(2, &node_cfgs, &node_chanmgrs);
 
        // We test config.our_to_self > BREAKDOWN_TIMEOUT is enforced in Channel::new_outbound()
-       let keys_manager: Arc<KeysInterface<ChanKeySigner = EnforcingChannelKeys>> = Arc::new(test_utils::TestKeysInterface::new(&nodes[0].node_seed, Network::Testnet));
+       let keys_manager = Arc::new(test_utils::TestKeysInterface::new(&nodes[0].node_seed, Network::Testnet));
        if let Err(error) = Channel::new_outbound(&&test_utils::TestFeeEstimator { sat_per_kw: 253 }, &keys_manager, nodes[1].node.get_our_node_id(), 1000000, 1000000, 0, &low_our_to_self_config) {
                match error {
                        APIError::APIMisuseError { err } => { assert!(regex::Regex::new(r"Configured with an unreasonable our_to_self_delay \(\d+\) putting user funds at risks").unwrap().is_match(err.as_str())); },
index 6e27e0431dfe335ae5651021bcebd4ba83860c71..abeb5de2601a3aca1b370af732eea2a065f0b16a 100644 (file)
@@ -430,6 +430,10 @@ impl keysinterface::KeysInterface for TestKeysInterface {
                }
                self.backing.get_secure_random_bytes()
        }
+
+       fn read_chan_signer(&self, reader: &[u8]) -> Result<Self::ChanKeySigner, msgs::DecodeError> {
+               EnforcingChannelKeys::read(&mut std::io::Cursor::new(reader))
+       }
 }
 
 impl TestKeysInterface {