Use `KeysInterface::read_chan_signer` for all channel keys deser
[rust-lightning] / fuzz / src / chanmon_consistency.rs
index 8a17719f9bbafab5a85c2b0f274cb5a46783d61e..5466414b2cd16560e08949c4ec579b2f32a5b602 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;
@@ -45,6 +45,7 @@ use lightning::util::logger::Logger;
 use lightning::util::config::UserConfig;
 use lightning::util::events::{EventsProvider, MessageSendEventsProvider};
 use lightning::util::ser::{Readable, ReadableArgs, Writeable, Writer};
+use lightning::util::test_utils::OnlyReadsKeysInterface;
 use lightning::routing::router::{Route, RouteHop};
 
 
@@ -112,7 +113,7 @@ impl chain::Watch for TestChainMonitor {
 
        fn watch_channel(&self, funding_txo: OutPoint, monitor: channelmonitor::ChannelMonitor<EnforcingChannelKeys>) -> Result<(), channelmonitor::ChannelMonitorUpdateErr> {
                let mut ser = VecWriter(Vec::new());
-               monitor.serialize_for_disk(&mut ser).unwrap();
+               monitor.write(&mut ser).unwrap();
                if let Some(_) = self.latest_monitors.lock().unwrap().insert(funding_txo, (monitor.get_latest_update_id(), ser.0)) {
                        panic!("Already had monitor pre-watch_channel");
                }
@@ -128,10 +129,10 @@ impl chain::Watch for TestChainMonitor {
                        hash_map::Entry::Vacant(_) => panic!("Didn't have monitor on update call"),
                };
                let mut deserialized_monitor = <(BlockHash, channelmonitor::ChannelMonitor<EnforcingChannelKeys>)>::
-                       read(&mut Cursor::new(&map_entry.get().1)).unwrap().1;
+                       read(&mut Cursor::new(&map_entry.get().1), &OnlyReadsKeysInterface {}).unwrap().1;
                deserialized_monitor.update_monitor(&update, &&TestBroadcaster{}, &&FuzzEstimator{}, &self.logger).unwrap();
                let mut ser = VecWriter(Vec::new());
-               deserialized_monitor.serialize_for_disk(&mut ser).unwrap();
+               deserialized_monitor.write(&mut ser).unwrap();
                map_entry.insert((update.update_id, ser.0));
                self.should_update_manager.store(true, atomic::Ordering::Relaxed);
                self.update_ret.lock().unwrap().clone()
@@ -184,6 +185,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]
@@ -307,7 +312,7 @@ pub fn do_test<Out: test_logger::Output>(data: &[u8], out: Out) {
                        let mut monitors = HashMap::new();
                        let mut old_monitors = $old_monitors.latest_monitors.lock().unwrap();
                        for (outpoint, (update_id, monitor_ser)) in old_monitors.drain() {
-                               monitors.insert(outpoint, <(BlockHash, ChannelMonitor<EnforcingChannelKeys>)>::read(&mut Cursor::new(&monitor_ser)).expect("Failed to read monitor").1);
+                               monitors.insert(outpoint, <(BlockHash, ChannelMonitor<EnforcingChannelKeys>)>::read(&mut Cursor::new(&monitor_ser), &OnlyReadsKeysInterface {}).expect("Failed to read monitor").1);
                                chain_monitor.latest_monitors.lock().unwrap().insert(outpoint, (update_id, monitor_ser));
                        }
                        let mut monitor_refs = HashMap::new();
@@ -542,7 +547,9 @@ pub fn do_test<Out: test_logger::Output>(data: &[u8], out: Out) {
                                        bc_events.clear();
                                        new_events
                                } else { Vec::new() };
+                               let mut had_events = false;
                                for event in events.iter().chain(nodes[$node].get_and_clear_pending_msg_events().iter()) {
+                                       had_events = true;
                                        match event {
                                                events::MessageSendEvent::UpdateHTLCs { ref node_id, updates: CommitmentUpdate { ref update_add_htlcs, ref update_fail_htlcs, ref update_fulfill_htlcs, ref update_fail_malformed_htlcs, ref update_fee, ref commitment_signed } } => {
                                                        for dest in nodes.iter() {
@@ -596,13 +603,10 @@ pub fn do_test<Out: test_logger::Output>(data: &[u8], out: Out) {
                                                        // Can be generated due to a payment forward being rejected due to a
                                                        // channel having previously failed a monitor update
                                                },
-                                               events::MessageSendEvent::HandleError { action: ErrorAction::IgnoreError, .. } => {
-                                                       // Can be generated at any processing step to send back an error, disconnect
-                                                       // peer or just ignore
-                                               },
                                                _ => panic!("Unhandled message event"),
                                        }
                                }
+                               had_events
                        } }
                }
 
@@ -682,6 +686,7 @@ pub fn do_test<Out: test_logger::Output>(data: &[u8], out: Out) {
                                                } else { Ordering::Equal }
                                        } else { Ordering::Equal }
                                });
+                               let had_events = !events.is_empty();
                                for event in events.drain(..) {
                                        match event {
                                                events::Event::PaymentReceived { payment_hash, payment_secret, amt } => {
@@ -701,6 +706,7 @@ pub fn do_test<Out: test_logger::Output>(data: &[u8], out: Out) {
                                                _ => panic!("Unhandled event"),
                                        }
                                }
+                               had_events
                        } }
                }
 
@@ -768,18 +774,18 @@ pub fn do_test<Out: test_logger::Output>(data: &[u8], out: Out) {
                                }
                        },
 
-                       0x10 => process_msg_events!(0, true),
-                       0x11 => process_msg_events!(0, false),
-                       0x12 => process_events!(0, true),
-                       0x13 => process_events!(0, false),
-                       0x14 => process_msg_events!(1, true),
-                       0x15 => process_msg_events!(1, false),
-                       0x16 => process_events!(1, true),
-                       0x17 => process_events!(1, false),
-                       0x18 => process_msg_events!(2, true),
-                       0x19 => process_msg_events!(2, false),
-                       0x1a => process_events!(2, true),
-                       0x1b => process_events!(2, false),
+                       0x10 => { process_msg_events!(0, true); },
+                       0x11 => { process_msg_events!(0, false); },
+                       0x12 => { process_events!(0, true); },
+                       0x13 => { process_events!(0, false); },
+                       0x14 => { process_msg_events!(1, true); },
+                       0x15 => { process_msg_events!(1, false); },
+                       0x16 => { process_events!(1, true); },
+                       0x17 => { process_events!(1, false); },
+                       0x18 => { process_msg_events!(2, true); },
+                       0x19 => { process_msg_events!(2, false); },
+                       0x1a => { process_events!(2, true); },
+                       0x1b => { process_events!(2, false); },
 
                        0x1c => {
                                if !chan_a_disconnected {
@@ -879,6 +885,62 @@ pub fn do_test<Out: test_logger::Output>(data: &[u8], out: Out) {
                        0x5c => { send_hop_payment(&nodes[0], &nodes[1], chan_a, &nodes[2], chan_b, 1, &mut payment_id); },
                        0x5d => { send_hop_payment(&nodes[2], &nodes[1], chan_b, &nodes[0], chan_a, 1, &mut payment_id); },
 
+                       0xff => {
+                               // Test that no channel is in a stuck state where neither party can send funds even
+                               // after we resolve all pending events.
+                               // First make sure there are no pending monitor updates, resetting the error state
+                               // and calling channel_monitor_updated for each monitor.
+                               *monitor_a.update_ret.lock().unwrap() = Ok(());
+                               *monitor_b.update_ret.lock().unwrap() = Ok(());
+                               *monitor_c.update_ret.lock().unwrap() = Ok(());
+
+                               if let Some((id, _)) = monitor_a.latest_monitors.lock().unwrap().get(&chan_1_funding) {
+                                       nodes[0].channel_monitor_updated(&chan_1_funding, *id);
+                               }
+                               if let Some((id, _)) = monitor_b.latest_monitors.lock().unwrap().get(&chan_1_funding) {
+                                       nodes[1].channel_monitor_updated(&chan_1_funding, *id);
+                               }
+                               if let Some((id, _)) = monitor_b.latest_monitors.lock().unwrap().get(&chan_2_funding) {
+                                       nodes[1].channel_monitor_updated(&chan_2_funding, *id);
+                               }
+                               if let Some((id, _)) = monitor_c.latest_monitors.lock().unwrap().get(&chan_2_funding) {
+                                       nodes[2].channel_monitor_updated(&chan_2_funding, *id);
+                               }
+
+                               // Next, make sure peers are all connected to each other
+                               if chan_a_disconnected {
+                                       nodes[0].peer_connected(&nodes[1].get_our_node_id(), &Init { features: InitFeatures::empty() });
+                                       nodes[1].peer_connected(&nodes[0].get_our_node_id(), &Init { features: InitFeatures::empty() });
+                                       chan_a_disconnected = false;
+                               }
+                               if chan_b_disconnected {
+                                       nodes[1].peer_connected(&nodes[2].get_our_node_id(), &Init { features: InitFeatures::empty() });
+                                       nodes[2].peer_connected(&nodes[1].get_our_node_id(), &Init { features: InitFeatures::empty() });
+                                       chan_b_disconnected = false;
+                               }
+
+                               for i in 0..std::usize::MAX {
+                                       if i == 100 { panic!("It may take may iterations to settle the state, but it should not take forever"); }
+                                       // Then, make sure any current forwards make their way to their destination
+                                       if process_msg_events!(0, false) { continue; }
+                                       if process_msg_events!(1, false) { continue; }
+                                       if process_msg_events!(2, false) { continue; }
+                                       // ...making sure any pending PendingHTLCsForwardable events are handled and
+                                       // payments claimed.
+                                       if process_events!(0, false) { continue; }
+                                       if process_events!(1, false) { continue; }
+                                       if process_events!(2, false) { continue; }
+                                       break;
+                               }
+
+                               // Finally, make sure that at least one end of each channel can make a substantial payment.
+                               assert!(
+                                       send_payment(&nodes[0], &nodes[1], chan_a, 10_000_000, &mut payment_id) ||
+                                       send_payment(&nodes[1], &nodes[0], chan_a, 10_000_000, &mut payment_id));
+                               assert!(
+                                       send_payment(&nodes[1], &nodes[2], chan_b, 10_000_000, &mut payment_id) ||
+                                       send_payment(&nodes[2], &nodes[1], chan_b, 10_000_000, &mut payment_id));
+                       },
                        _ => test_return!(),
                }