X-Git-Url: http://git.bitcoin.ninja/index.cgi?a=blobdiff_plain;f=fuzz%2Fsrc%2Fchanmon_consistency.rs;h=8ff741c720a4c3fc475ecd2f43ec086979d6d7b5;hb=210b887d7c31a2a6e1c9a770218a99155eb18ab7;hp=3feeaf46d5e1636d01736a904c9a52aeb8f2b5fa;hpb=3f2efcdfa73ee703093107f908cc7eeb0aa467e8;p=rust-lightning diff --git a/fuzz/src/chanmon_consistency.rs b/fuzz/src/chanmon_consistency.rs index 3feeaf46..8ff741c7 100644 --- a/fuzz/src/chanmon_consistency.rs +++ b/fuzz/src/chanmon_consistency.rs @@ -30,13 +30,14 @@ use bitcoin::hashes::sha256::Hash as Sha256; use bitcoin::hash_types::{BlockHash, WPubkeyHash}; use lightning::chain; +use lightning::chain::Confirm; use lightning::chain::chainmonitor; use lightning::chain::channelmonitor; use lightning::chain::channelmonitor::{ChannelMonitor, ChannelMonitorUpdateErr, MonitorEvent}; use lightning::chain::transaction::OutPoint; use lightning::chain::chaininterface::{BroadcasterInterface, ConfirmationTarget, FeeEstimator}; use lightning::chain::keysinterface::{KeysInterface, InMemorySigner}; -use lightning::ln::channelmanager::{ChainParameters, ChannelManager, PaymentHash, PaymentPreimage, PaymentSecret, PaymentSendFailure, ChannelManagerReadArgs}; +use lightning::ln::channelmanager::{BestBlock, ChainParameters, ChannelManager, PaymentHash, PaymentPreimage, PaymentSecret, PaymentSendFailure, ChannelManagerReadArgs}; use lightning::ln::features::{ChannelFeatures, InitFeatures, NodeFeatures}; use lightning::ln::msgs::{CommitmentUpdate, ChannelMessageHandler, DecodeError, ErrorAction, UpdateAddHTLC, Init}; use lightning::util::enforcing_trait_impls::{EnforcingSigner, INITIAL_REVOKED_COMMITMENT_NUMBER}; @@ -234,7 +235,7 @@ fn check_api_err(api_err: APIError) { _ if err.starts_with("Cannot send value that would put our balance under counterparty-announced channel reserve value") => {}, _ if err.starts_with("Cannot send value that would overdraw remaining funds.") => {}, _ if err.starts_with("Cannot send value that would not leave enough to pay for fees.") => {}, - _ => panic!(err), + _ => panic!("{}", err), } }, APIError::MonitorUpdateFailed => { @@ -260,45 +261,58 @@ fn check_payment_err(send_err: PaymentSendFailure) { type ChanMan = ChannelManager, Arc, Arc, Arc, Arc>; +#[inline] +fn get_payment_secret_hash(dest: &ChanMan, payment_id: &mut u8) -> Option<(PaymentSecret, PaymentHash)> { + let mut payment_hash; + for _ in 0..256 { + payment_hash = PaymentHash(Sha256::hash(&[*payment_id; 1]).into_inner()); + if let Ok(payment_secret) = dest.create_inbound_payment_for_hash(payment_hash, None, 7200, 0) { + return Some((payment_secret, payment_hash)); + } + *payment_id = payment_id.wrapping_add(1); + } + None +} + #[inline] fn send_payment(source: &ChanMan, dest: &ChanMan, dest_chan_id: u64, amt: u64, payment_id: &mut u8) -> bool { - let payment_hash = Sha256::hash(&[*payment_id; 1]); - *payment_id = payment_id.wrapping_add(1); + let (payment_secret, payment_hash) = + if let Some((secret, hash)) = get_payment_secret_hash(dest, payment_id) { (secret, hash) } else { return true; }; if let Err(err) = source.send_payment(&Route { paths: vec![vec![RouteHop { pubkey: dest.get_our_node_id(), - node_features: NodeFeatures::empty(), + node_features: NodeFeatures::known(), short_channel_id: dest_chan_id, - channel_features: ChannelFeatures::empty(), + channel_features: ChannelFeatures::known(), fee_msat: amt, cltv_expiry_delta: 200, }]], - }, PaymentHash(payment_hash.into_inner()), &None) { + }, payment_hash, &Some(payment_secret)) { check_payment_err(err); false } else { true } } #[inline] fn send_hop_payment(source: &ChanMan, middle: &ChanMan, middle_chan_id: u64, dest: &ChanMan, dest_chan_id: u64, amt: u64, payment_id: &mut u8) -> bool { - let payment_hash = Sha256::hash(&[*payment_id; 1]); - *payment_id = payment_id.wrapping_add(1); + let (payment_secret, payment_hash) = + if let Some((secret, hash)) = get_payment_secret_hash(dest, payment_id) { (secret, hash) } else { return true; }; if let Err(err) = source.send_payment(&Route { paths: vec![vec![RouteHop { pubkey: middle.get_our_node_id(), - node_features: NodeFeatures::empty(), + node_features: NodeFeatures::known(), short_channel_id: middle_chan_id, - channel_features: ChannelFeatures::empty(), + channel_features: ChannelFeatures::known(), fee_msat: 50000, cltv_expiry_delta: 100, },RouteHop { pubkey: dest.get_our_node_id(), - node_features: NodeFeatures::empty(), + node_features: NodeFeatures::known(), short_channel_id: dest_chan_id, - channel_features: ChannelFeatures::empty(), + channel_features: ChannelFeatures::known(), fee_msat: amt, cltv_expiry_delta: 200, }]], - }, PaymentHash(payment_hash.into_inner()), &None) { + }, payment_hash, &Some(payment_secret)) { check_payment_err(err); false } else { true } @@ -322,8 +336,7 @@ pub fn do_test(data: &[u8], out: Out) { let network = Network::Bitcoin; let params = ChainParameters { network, - latest_hash: genesis_block(network).block_hash(), - latest_height: 0, + best_block: BestBlock::from_genesis(network), }; (ChannelManager::new(fee_est.clone(), monitor.clone(), broadcast.clone(), Arc::clone(&logger), keys_manager.clone(), config, params), monitor, keys_manager) @@ -429,11 +442,11 @@ pub fn do_test(data: &[u8], out: Out) { let chain_hash = genesis_block(Network::Bitcoin).block_hash(); let mut header = BlockHeader { version: 0x20000000, prev_blockhash: chain_hash, merkle_root: Default::default(), time: 42, bits: 42, nonce: 42 }; let txdata: Vec<_> = channel_txn.iter().enumerate().map(|(i, tx)| (i + 1, tx)).collect(); - $node.block_connected(&header, &txdata, 1); - for i in 2..100 { + $node.transactions_confirmed(&header, &txdata, 1); + for _ in 2..100 { header = BlockHeader { version: 0x20000000, prev_blockhash: header.block_hash(), merkle_root: Default::default(), time: 42, bits: 42, nonce: 42 }; - $node.block_connected(&header, &[], i); } + $node.best_block_updated(&header, 99); } } } @@ -523,48 +536,6 @@ pub fn do_test(data: &[u8], out: Out) { } loop { - macro_rules! send_payment_with_secret { - ($source: expr, $middle: expr, $dest: expr) => { { - let payment_hash = Sha256::hash(&[payment_id; 1]); - payment_id = payment_id.wrapping_add(1); - let payment_secret = Sha256::hash(&[payment_id; 1]); - payment_id = payment_id.wrapping_add(1); - if let Err(err) = $source.send_payment(&Route { - paths: vec![vec![RouteHop { - pubkey: $middle.0.get_our_node_id(), - node_features: NodeFeatures::empty(), - short_channel_id: $middle.1, - channel_features: ChannelFeatures::empty(), - fee_msat: 50_000, - cltv_expiry_delta: 100, - },RouteHop { - pubkey: $dest.0.get_our_node_id(), - node_features: NodeFeatures::empty(), - short_channel_id: $dest.1, - channel_features: ChannelFeatures::empty(), - fee_msat: 10_000_000, - cltv_expiry_delta: 200, - }],vec![RouteHop { - pubkey: $middle.0.get_our_node_id(), - node_features: NodeFeatures::empty(), - short_channel_id: $middle.1, - channel_features: ChannelFeatures::empty(), - fee_msat: 50_000, - cltv_expiry_delta: 100, - },RouteHop { - pubkey: $dest.0.get_our_node_id(), - node_features: NodeFeatures::empty(), - short_channel_id: $dest.1, - channel_features: ChannelFeatures::empty(), - fee_msat: 10_000_000, - cltv_expiry_delta: 200, - }]], - }, PaymentHash(payment_hash.into_inner()), &Some(PaymentSecret(payment_secret.into_inner()))) { - check_payment_err(err); - } - } } - } - macro_rules! process_msg_events { ($node: expr, $corrupt_forward: expr) => { { let events = if $node == 1 { @@ -716,7 +687,7 @@ pub fn do_test(data: &[u8], out: Out) { let had_events = !events.is_empty(); for event in events.drain(..) { match event { - events::Event::PaymentReceived { payment_hash, payment_secret, amt } => { + events::Event::PaymentReceived { payment_hash, payment_secret, amt, user_payment_id: _ } => { if claim_set.insert(payment_hash.0) { if $fail { assert!(nodes[$node].fail_htlc_backwards(&payment_hash, &payment_secret)); @@ -788,15 +759,15 @@ pub fn do_test(data: &[u8], out: Out) { }, 0x0e => { 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() }); + nodes[0].peer_connected(&nodes[1].get_our_node_id(), &Init { features: InitFeatures::known() }); + nodes[1].peer_connected(&nodes[0].get_our_node_id(), &Init { features: InitFeatures::known() }); chan_a_disconnected = false; } }, 0x0f => { 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() }); + nodes[1].peer_connected(&nodes[2].get_our_node_id(), &Init { features: InitFeatures::known() }); + nodes[2].peer_connected(&nodes[1].get_our_node_id(), &Init { features: InitFeatures::known() }); chan_b_disconnected = false; } }, @@ -860,9 +831,6 @@ pub fn do_test(data: &[u8], out: Out) { 0x24 => { send_hop_payment(&nodes[0], &nodes[1], chan_a, &nodes[2], chan_b, 10_000_000, &mut payment_id); }, 0x25 => { send_hop_payment(&nodes[2], &nodes[1], chan_b, &nodes[0], chan_a, 10_000_000, &mut payment_id); }, - 0x26 => { send_payment_with_secret!(nodes[0], (&nodes[1], chan_a), (&nodes[2], chan_b)); }, - 0x27 => { send_payment_with_secret!(nodes[2], (&nodes[1], chan_b), (&nodes[0], chan_a)); }, - 0x28 => { send_payment(&nodes[0], &nodes[1], chan_a, 1_000_000, &mut payment_id); }, 0x29 => { send_payment(&nodes[1], &nodes[0], chan_a, 1_000_000, &mut payment_id); }, 0x2a => { send_payment(&nodes[1], &nodes[2], chan_b, 1_000_000, &mut payment_id); }, @@ -936,13 +904,13 @@ pub fn do_test(data: &[u8], out: Out) { // 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() }); + nodes[0].peer_connected(&nodes[1].get_our_node_id(), &Init { features: InitFeatures::known() }); + nodes[1].peer_connected(&nodes[0].get_our_node_id(), &Init { features: InitFeatures::known() }); 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() }); + nodes[1].peer_connected(&nodes[2].get_our_node_id(), &Init { features: InitFeatures::known() }); + nodes[2].peer_connected(&nodes[1].get_our_node_id(), &Init { features: InitFeatures::known() }); chan_b_disconnected = false; }