3 use core::sync::atomic::Ordering;
5 use bitcoin::blockdata::constants::ChainHash;
6 use bitcoin::secp256k1::PublicKey;
8 use lightning::ln::msgs::{
9 DecodeError, ErrorAction, LightningError, UnsignedChannelUpdate,
11 use lightning::routing::gossip::NetworkGraph;
12 use lightning::util::logger::Logger;
13 use lightning::{log_debug, log_warn, log_trace, log_given_level, log_gossip};
14 use lightning::util::ser::{BigSize, Readable};
17 use crate::{GraphSyncError, RapidGossipSync};
19 #[cfg(all(feature = "std", not(test)))]
20 use std::time::{SystemTime, UNIX_EPOCH};
22 #[cfg(not(feature = "std"))]
23 use alloc::{vec::Vec, borrow::ToOwned};
25 /// The purpose of this prefix is to identify the serialization format, should other rapid gossip
26 /// sync formats arise in the future.
28 /// The fourth byte is the protocol version in case our format gets updated.
29 const GOSSIP_PREFIX: [u8; 4] = [76, 68, 75, 1];
31 /// Maximum vector allocation capacity for distinct node IDs. This constraint is necessary to
32 /// avoid malicious updates being able to trigger excessive memory allocation.
33 const MAX_INITIAL_NODE_ID_VECTOR_CAPACITY: u32 = 50_000;
35 /// We disallow gossip data that's more than two weeks old, per BOLT 7's
37 const STALE_RGS_UPDATE_AGE_LIMIT_SECS: u64 = 60 * 60 * 24 * 14;
39 impl<NG: Deref<Target=NetworkGraph<L>>, L: Deref> RapidGossipSync<NG, L> where L::Target: Logger {
40 #[cfg(feature = "std")]
41 pub(crate) fn update_network_graph_from_byte_stream<R: io::Read>(
44 ) -> Result<u32, GraphSyncError> {
45 #[allow(unused_mut, unused_assignments)]
46 let mut current_time_unix = None;
49 // Note that many tests rely on being able to set arbitrarily old timestamps, thus we
50 // disable this check during tests!
51 current_time_unix = Some(SystemTime::now().duration_since(UNIX_EPOCH).expect("Time must be > 1970").as_secs());
53 self.update_network_graph_from_byte_stream_no_std(read_cursor, current_time_unix)
56 pub(crate) fn update_network_graph_from_byte_stream_no_std<R: io::Read>(
58 mut read_cursor: &mut R,
59 current_time_unix: Option<u64>
60 ) -> Result<u32, GraphSyncError> {
61 log_trace!(self.logger, "Processing RGS data...");
62 let mut prefix = [0u8; 4];
63 read_cursor.read_exact(&mut prefix)?;
65 if prefix != GOSSIP_PREFIX {
66 return Err(DecodeError::UnknownVersion.into());
69 let chain_hash: ChainHash = Readable::read(read_cursor)?;
70 let ng_chain_hash = self.network_graph.get_chain_hash();
71 if chain_hash != ng_chain_hash {
74 err: "Rapid Gossip Sync data's chain hash does not match the network graph's".to_owned(),
75 action: ErrorAction::IgnoreError,
80 let latest_seen_timestamp: u32 = Readable::read(read_cursor)?;
82 if let Some(time) = current_time_unix {
83 if (latest_seen_timestamp as u64) < time.saturating_sub(STALE_RGS_UPDATE_AGE_LIMIT_SECS) {
84 return Err(LightningError{err: "Rapid Gossip Sync data is more than two weeks old".to_owned(), action: ErrorAction::IgnoreError}.into());
88 // backdate the applied timestamp by a week
89 let backdated_timestamp = latest_seen_timestamp.saturating_sub(24 * 3600 * 7);
91 let node_id_count: u32 = Readable::read(read_cursor)?;
92 let mut node_ids: Vec<PublicKey> = Vec::with_capacity(core::cmp::min(
94 MAX_INITIAL_NODE_ID_VECTOR_CAPACITY,
96 for _ in 0..node_id_count {
97 let current_node_id = Readable::read(read_cursor)?;
98 node_ids.push(current_node_id);
101 let network_graph = &self.network_graph;
103 let mut previous_scid: u64 = 0;
104 let announcement_count: u32 = Readable::read(read_cursor)?;
105 for _ in 0..announcement_count {
106 let features = Readable::read(read_cursor)?;
109 let scid_delta: BigSize = Readable::read(read_cursor)?;
110 let short_channel_id = previous_scid
111 .checked_add(scid_delta.0)
112 .ok_or(DecodeError::InvalidValue)?;
113 previous_scid = short_channel_id;
115 let node_id_1_index: BigSize = Readable::read(read_cursor)?;
116 let node_id_2_index: BigSize = Readable::read(read_cursor)?;
118 if max(node_id_1_index.0, node_id_2_index.0) >= node_id_count as u64 {
119 return Err(DecodeError::InvalidValue.into());
121 let node_id_1 = node_ids[node_id_1_index.0 as usize];
122 let node_id_2 = node_ids[node_id_2_index.0 as usize];
124 log_gossip!(self.logger, "Adding channel {} from RGS announcement at {}",
125 short_channel_id, latest_seen_timestamp);
127 let announcement_result = network_graph.add_channel_from_partial_announcement(
129 backdated_timestamp as u64,
134 if let Err(lightning_error) = announcement_result {
135 if let ErrorAction::IgnoreDuplicateGossip = lightning_error.action {
136 // everything is fine, just a duplicate channel announcement
138 log_warn!(self.logger, "Failed to process channel announcement: {:?}", lightning_error);
139 return Err(lightning_error.into());
144 previous_scid = 0; // updates start at a new scid
146 let update_count: u32 = Readable::read(read_cursor)?;
147 log_debug!(self.logger, "Processing RGS update from {} with {} nodes, {} channel announcements and {} channel updates.",
148 latest_seen_timestamp, node_id_count, announcement_count, update_count);
149 if update_count == 0 {
150 return Ok(latest_seen_timestamp);
153 // obtain default values for non-incremental updates
154 let default_cltv_expiry_delta: u16 = Readable::read(&mut read_cursor)?;
155 let default_htlc_minimum_msat: u64 = Readable::read(&mut read_cursor)?;
156 let default_fee_base_msat: u32 = Readable::read(&mut read_cursor)?;
157 let default_fee_proportional_millionths: u32 = Readable::read(&mut read_cursor)?;
158 let default_htlc_maximum_msat: u64 = Readable::read(&mut read_cursor)?;
160 for _ in 0..update_count {
161 let scid_delta: BigSize = Readable::read(read_cursor)?;
162 let short_channel_id = previous_scid
163 .checked_add(scid_delta.0)
164 .ok_or(DecodeError::InvalidValue)?;
165 previous_scid = short_channel_id;
167 let channel_flags: u8 = Readable::read(read_cursor)?;
169 // flags are always sent in full, and hence always need updating
170 let standard_channel_flags = channel_flags & 0b_0000_0011;
172 let mut synthetic_update = UnsignedChannelUpdate {
175 timestamp: backdated_timestamp,
176 flags: standard_channel_flags,
177 cltv_expiry_delta: default_cltv_expiry_delta,
178 htlc_minimum_msat: default_htlc_minimum_msat,
179 htlc_maximum_msat: default_htlc_maximum_msat,
180 fee_base_msat: default_fee_base_msat,
181 fee_proportional_millionths: default_fee_proportional_millionths,
182 excess_data: Vec::new(),
185 let mut skip_update_for_unknown_channel = false;
187 if (channel_flags & 0b_1000_0000) != 0 {
188 // incremental update, field flags will indicate mutated values
189 let read_only_network_graph = network_graph.read_only();
190 if let Some(directional_info) =
191 read_only_network_graph.channels().get(&short_channel_id)
192 .and_then(|channel| channel.get_directional_info(channel_flags))
194 synthetic_update.cltv_expiry_delta = directional_info.cltv_expiry_delta;
195 synthetic_update.htlc_minimum_msat = directional_info.htlc_minimum_msat;
196 synthetic_update.htlc_maximum_msat = directional_info.htlc_maximum_msat;
197 synthetic_update.fee_base_msat = directional_info.fees.base_msat;
198 synthetic_update.fee_proportional_millionths = directional_info.fees.proportional_millionths;
200 log_trace!(self.logger,
201 "Skipping application of channel update for chan {} with flags {} as original data is missing.",
202 short_channel_id, channel_flags);
203 skip_update_for_unknown_channel = true;
207 if channel_flags & 0b_0100_0000 > 0 {
208 let cltv_expiry_delta: u16 = Readable::read(read_cursor)?;
209 synthetic_update.cltv_expiry_delta = cltv_expiry_delta;
212 if channel_flags & 0b_0010_0000 > 0 {
213 let htlc_minimum_msat: u64 = Readable::read(read_cursor)?;
214 synthetic_update.htlc_minimum_msat = htlc_minimum_msat;
217 if channel_flags & 0b_0001_0000 > 0 {
218 let fee_base_msat: u32 = Readable::read(read_cursor)?;
219 synthetic_update.fee_base_msat = fee_base_msat;
222 if channel_flags & 0b_0000_1000 > 0 {
223 let fee_proportional_millionths: u32 = Readable::read(read_cursor)?;
224 synthetic_update.fee_proportional_millionths = fee_proportional_millionths;
227 if channel_flags & 0b_0000_0100 > 0 {
228 let htlc_maximum_msat: u64 = Readable::read(read_cursor)?;
229 synthetic_update.htlc_maximum_msat = htlc_maximum_msat;
232 if skip_update_for_unknown_channel {
236 log_gossip!(self.logger, "Updating channel {} with flags {} from RGS announcement at {}",
237 short_channel_id, channel_flags, latest_seen_timestamp);
238 match network_graph.update_channel_unsigned(&synthetic_update) {
240 Err(LightningError { action: ErrorAction::IgnoreDuplicateGossip, .. }) => {},
241 Err(LightningError { action: ErrorAction::IgnoreAndLog(level), err }) => {
242 log_given_level!(self.logger, level, "Failed to apply channel update: {:?}", err);
244 Err(LightningError { action: ErrorAction::IgnoreError, .. }) => {},
245 Err(e) => return Err(e.into()),
249 self.network_graph.set_last_rapid_gossip_sync_timestamp(latest_seen_timestamp);
251 if let Some(time) = current_time_unix {
252 self.network_graph.remove_stale_channels_and_tracking_with_time(time)
255 self.is_initial_sync_complete.store(true, Ordering::Release);
256 log_trace!(self.logger, "Done processing RGS data from {}", latest_seen_timestamp);
257 Ok(latest_seen_timestamp)
263 use bitcoin::Network;
265 #[cfg(feature = "std")]
266 use lightning::ln::msgs::DecodeError;
268 use lightning::routing::gossip::NetworkGraph;
269 use lightning::util::test_utils::TestLogger;
271 use crate::processing::STALE_RGS_UPDATE_AGE_LIMIT_SECS;
272 use crate::{GraphSyncError, RapidGossipSync};
274 const VALID_RGS_BINARY: [u8; 300] = [
275 76, 68, 75, 1, 111, 226, 140, 10, 182, 241, 179, 114, 193, 166, 162, 70, 174, 99, 247,
276 79, 147, 30, 131, 101, 225, 90, 8, 156, 104, 214, 25, 0, 0, 0, 0, 0, 97, 227, 98, 218,
277 0, 0, 0, 4, 2, 22, 7, 207, 206, 25, 164, 197, 231, 230, 231, 56, 102, 61, 250, 251,
278 187, 172, 38, 46, 79, 247, 108, 44, 155, 48, 219, 238, 252, 53, 192, 6, 67, 2, 36, 125,
279 157, 176, 223, 175, 234, 116, 94, 248, 201, 225, 97, 235, 50, 47, 115, 172, 63, 136,
280 88, 216, 115, 11, 111, 217, 114, 84, 116, 124, 231, 107, 2, 158, 1, 242, 121, 152, 106,
281 204, 131, 186, 35, 93, 70, 216, 10, 237, 224, 183, 89, 95, 65, 3, 83, 185, 58, 138,
282 181, 64, 187, 103, 127, 68, 50, 2, 201, 19, 17, 138, 136, 149, 185, 226, 156, 137, 175,
283 110, 32, 237, 0, 217, 90, 31, 100, 228, 149, 46, 219, 175, 168, 77, 4, 143, 38, 128,
284 76, 97, 0, 0, 0, 2, 0, 0, 255, 8, 153, 192, 0, 2, 27, 0, 0, 0, 1, 0, 0, 255, 2, 68,
285 226, 0, 6, 11, 0, 1, 2, 3, 0, 0, 0, 4, 0, 40, 0, 0, 0, 0, 0, 0, 3, 232, 0, 0, 3, 232,
286 0, 0, 0, 1, 0, 0, 0, 0, 29, 129, 25, 192, 255, 8, 153, 192, 0, 2, 27, 0, 0, 60, 0, 0,
287 0, 0, 0, 0, 0, 1, 0, 0, 0, 100, 0, 0, 2, 224, 0, 0, 0, 0, 58, 85, 116, 216, 0, 29, 0,
288 0, 0, 1, 0, 0, 0, 125, 0, 0, 0, 0, 58, 85, 116, 216, 255, 2, 68, 226, 0, 6, 11, 0, 1,
291 const VALID_BINARY_TIMESTAMP: u64 = 1642291930;
294 #[cfg(feature = "std")]
295 fn network_graph_fails_to_update_from_clipped_input() {
296 let logger = TestLogger::new();
297 let network_graph = NetworkGraph::new(Network::Bitcoin, &logger);
299 let example_input = vec![
300 76, 68, 75, 1, 111, 226, 140, 10, 182, 241, 179, 114, 193, 166, 162, 70, 174, 99, 247,
301 79, 147, 30, 131, 101, 225, 90, 8, 156, 104, 214, 25, 0, 0, 0, 0, 0, 97, 227, 98, 218,
302 0, 0, 0, 4, 2, 22, 7, 207, 206, 25, 164, 197, 231, 230, 231, 56, 102, 61, 250, 251,
303 187, 172, 38, 46, 79, 247, 108, 44, 155, 48, 219, 238, 252, 53, 192, 6, 67, 2, 36, 125,
304 157, 176, 223, 175, 234, 116, 94, 248, 201, 225, 97, 235, 50, 47, 115, 172, 63, 136,
305 88, 216, 115, 11, 111, 217, 114, 84, 116, 124, 231, 107, 2, 158, 1, 242, 121, 152, 106,
306 204, 131, 186, 35, 93, 70, 216, 10, 237, 224, 183, 89, 95, 65, 3, 83, 185, 58, 138,
307 181, 64, 187, 103, 127, 68, 50, 2, 201, 19, 17, 138, 136, 149, 185, 226, 156, 137, 175,
308 110, 32, 237, 0, 217, 90, 31, 100, 228, 149, 46, 219, 175, 168, 77, 4, 143, 38, 128,
309 76, 97, 0, 0, 0, 2, 0, 0, 255, 8, 153, 192, 0, 2, 27, 0, 0, 0, 1, 0, 0, 255, 2, 68,
310 226, 0, 6, 11, 0, 1, 2, 3, 0, 0, 0, 2, 0, 40, 0, 0, 0, 0, 0, 0, 3, 232, 0, 0, 0, 100,
311 0, 0, 2, 224, 0, 0, 0, 0, 29, 129, 25, 192, 255, 8, 153, 192, 0, 2, 27, 0, 0, 36, 0, 0,
312 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 58, 85, 116, 216, 255, 2, 68, 226, 0, 6, 11, 0, 1, 24, 0,
315 let rapid_sync = RapidGossipSync::new(&network_graph, &logger);
316 let update_result = rapid_sync.update_network_graph(&example_input[..]);
317 assert!(update_result.is_err());
318 if let Err(GraphSyncError::DecodeError(DecodeError::ShortRead)) = update_result {
319 // this is the expected error type
321 panic!("Unexpected update result: {:?}", update_result)
326 #[cfg(feature = "std")]
327 fn incremental_only_update_ignores_missing_channel() {
328 let incremental_update_input = vec![
329 76, 68, 75, 1, 111, 226, 140, 10, 182, 241, 179, 114, 193, 166, 162, 70, 174, 99, 247,
330 79, 147, 30, 131, 101, 225, 90, 8, 156, 104, 214, 25, 0, 0, 0, 0, 0, 97, 229, 183, 167,
331 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
332 0, 0, 0, 0, 0, 0, 0, 0, 0, 255, 8, 153, 192, 0, 2, 27, 0, 0, 136, 0, 0, 0, 221, 255, 2,
333 68, 226, 0, 6, 11, 0, 1, 128,
336 let logger = TestLogger::new();
337 let network_graph = NetworkGraph::new(Network::Bitcoin, &logger);
339 assert_eq!(network_graph.read_only().channels().len(), 0);
341 let rapid_sync = RapidGossipSync::new(&network_graph, &logger);
342 let update_result = rapid_sync.update_network_graph(&incremental_update_input[..]);
343 assert!(update_result.is_ok());
347 #[cfg(feature = "std")]
348 fn incremental_only_update_fails_without_prior_updates() {
349 let announced_update_input = vec![
350 76, 68, 75, 1, 111, 226, 140, 10, 182, 241, 179, 114, 193, 166, 162, 70, 174, 99, 247,
351 79, 147, 30, 131, 101, 225, 90, 8, 156, 104, 214, 25, 0, 0, 0, 0, 0, 97, 229, 183, 167,
352 0, 0, 0, 4, 2, 22, 7, 207, 206, 25, 164, 197, 231, 230, 231, 56, 102, 61, 250, 251,
353 187, 172, 38, 46, 79, 247, 108, 44, 155, 48, 219, 238, 252, 53, 192, 6, 67, 2, 36, 125,
354 157, 176, 223, 175, 234, 116, 94, 248, 201, 225, 97, 235, 50, 47, 115, 172, 63, 136,
355 88, 216, 115, 11, 111, 217, 114, 84, 116, 124, 231, 107, 2, 158, 1, 242, 121, 152, 106,
356 204, 131, 186, 35, 93, 70, 216, 10, 237, 224, 183, 89, 95, 65, 3, 83, 185, 58, 138,
357 181, 64, 187, 103, 127, 68, 50, 2, 201, 19, 17, 138, 136, 149, 185, 226, 156, 137, 175,
358 110, 32, 237, 0, 217, 90, 31, 100, 228, 149, 46, 219, 175, 168, 77, 4, 143, 38, 128,
359 76, 97, 0, 0, 0, 2, 0, 0, 255, 8, 153, 192, 0, 2, 27, 0, 0, 0, 1, 0, 0, 255, 2, 68,
360 226, 0, 6, 11, 0, 1, 2, 3, 0, 0, 0, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
361 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 255, 8, 153, 192, 0, 2, 27, 0, 0, 136, 0, 0, 0, 221, 255,
362 2, 68, 226, 0, 6, 11, 0, 1, 128,
365 let logger = TestLogger::new();
366 let network_graph = NetworkGraph::new(Network::Bitcoin, &logger);
368 assert_eq!(network_graph.read_only().channels().len(), 0);
370 let rapid_sync = RapidGossipSync::new(&network_graph, &logger);
371 rapid_sync.update_network_graph(&announced_update_input[..]).unwrap();
375 #[cfg(feature = "std")]
376 fn incremental_only_update_fails_without_prior_same_direction_updates() {
377 let initialization_input = vec![
378 76, 68, 75, 1, 111, 226, 140, 10, 182, 241, 179, 114, 193, 166, 162, 70, 174, 99, 247,
379 79, 147, 30, 131, 101, 225, 90, 8, 156, 104, 214, 25, 0, 0, 0, 0, 0, 97, 227, 98, 218,
380 0, 0, 0, 4, 2, 22, 7, 207, 206, 25, 164, 197, 231, 230, 231, 56, 102, 61, 250, 251,
381 187, 172, 38, 46, 79, 247, 108, 44, 155, 48, 219, 238, 252, 53, 192, 6, 67, 2, 36, 125,
382 157, 176, 223, 175, 234, 116, 94, 248, 201, 225, 97, 235, 50, 47, 115, 172, 63, 136,
383 88, 216, 115, 11, 111, 217, 114, 84, 116, 124, 231, 107, 2, 158, 1, 242, 121, 152, 106,
384 204, 131, 186, 35, 93, 70, 216, 10, 237, 224, 183, 89, 95, 65, 3, 83, 185, 58, 138,
385 181, 64, 187, 103, 127, 68, 50, 2, 201, 19, 17, 138, 136, 149, 185, 226, 156, 137, 175,
386 110, 32, 237, 0, 217, 90, 31, 100, 228, 149, 46, 219, 175, 168, 77, 4, 143, 38, 128,
387 76, 97, 0, 0, 0, 2, 0, 0, 255, 8, 153, 192, 0, 2, 27, 0, 0, 0, 1, 0, 0, 255, 2, 68,
388 226, 0, 6, 11, 0, 1, 2, 3, 0, 0, 0, 2, 0, 40, 0, 0, 0, 0, 0, 0, 3, 232, 0, 0, 3, 232,
389 0, 0, 0, 1, 0, 0, 0, 0, 58, 85, 116, 216, 255, 8, 153, 192, 0, 2, 27, 0, 0, 25, 0, 0,
390 0, 1, 0, 0, 0, 125, 255, 2, 68, 226, 0, 6, 11, 0, 1, 5, 0, 0, 0, 0, 29, 129, 25, 192,
393 let logger = TestLogger::new();
394 let network_graph = NetworkGraph::new(Network::Bitcoin, &logger);
396 assert_eq!(network_graph.read_only().channels().len(), 0);
398 let rapid_sync = RapidGossipSync::new(&network_graph, &logger);
399 let initialization_result = rapid_sync.update_network_graph(&initialization_input[..]);
400 if initialization_result.is_err() {
402 "Unexpected initialization result: {:?}",
403 initialization_result
407 assert_eq!(network_graph.read_only().channels().len(), 2);
408 let initialized = network_graph.to_string();
410 .contains("021607cfce19a4c5e7e6e738663dfafbbbac262e4ff76c2c9b30dbeefc35c00643"));
412 .contains("02247d9db0dfafea745ef8c9e161eb322f73ac3f8858d8730b6fd97254747ce76b"));
414 .contains("029e01f279986acc83ba235d46d80aede0b7595f410353b93a8ab540bb677f4432"));
416 .contains("02c913118a8895b9e29c89af6e20ed00d95a1f64e4952edbafa84d048f26804c61"));
417 assert!(initialized.contains("619737530008010752"));
418 assert!(initialized.contains("783241506229452801"));
420 let opposite_direction_incremental_update_input = vec![
421 76, 68, 75, 1, 111, 226, 140, 10, 182, 241, 179, 114, 193, 166, 162, 70, 174, 99, 247,
422 79, 147, 30, 131, 101, 225, 90, 8, 156, 104, 214, 25, 0, 0, 0, 0, 0, 97, 229, 183, 167,
423 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
424 0, 0, 0, 0, 0, 0, 0, 0, 0, 255, 8, 153, 192, 0, 2, 27, 0, 0, 136, 0, 0, 0, 221, 255, 2,
425 68, 226, 0, 6, 11, 0, 1, 128,
427 rapid_sync.update_network_graph(&opposite_direction_incremental_update_input[..]).unwrap();
431 #[cfg(feature = "std")]
432 fn incremental_update_succeeds_with_prior_announcements_and_full_updates() {
433 let initialization_input = vec![
434 76, 68, 75, 1, 111, 226, 140, 10, 182, 241, 179, 114, 193, 166, 162, 70, 174, 99, 247,
435 79, 147, 30, 131, 101, 225, 90, 8, 156, 104, 214, 25, 0, 0, 0, 0, 0, 97, 227, 98, 218,
436 0, 0, 0, 4, 2, 22, 7, 207, 206, 25, 164, 197, 231, 230, 231, 56, 102, 61, 250, 251,
437 187, 172, 38, 46, 79, 247, 108, 44, 155, 48, 219, 238, 252, 53, 192, 6, 67, 2, 36, 125,
438 157, 176, 223, 175, 234, 116, 94, 248, 201, 225, 97, 235, 50, 47, 115, 172, 63, 136,
439 88, 216, 115, 11, 111, 217, 114, 84, 116, 124, 231, 107, 2, 158, 1, 242, 121, 152, 106,
440 204, 131, 186, 35, 93, 70, 216, 10, 237, 224, 183, 89, 95, 65, 3, 83, 185, 58, 138,
441 181, 64, 187, 103, 127, 68, 50, 2, 201, 19, 17, 138, 136, 149, 185, 226, 156, 137, 175,
442 110, 32, 237, 0, 217, 90, 31, 100, 228, 149, 46, 219, 175, 168, 77, 4, 143, 38, 128,
443 76, 97, 0, 0, 0, 2, 0, 0, 255, 8, 153, 192, 0, 2, 27, 0, 0, 0, 1, 0, 0, 255, 2, 68,
444 226, 0, 6, 11, 0, 1, 2, 3, 0, 0, 0, 4, 0, 40, 0, 0, 0, 0, 0, 0, 3, 232, 0, 0, 3, 232,
445 0, 0, 0, 1, 0, 0, 0, 0, 58, 85, 116, 216, 255, 8, 153, 192, 0, 2, 27, 0, 0, 56, 0, 0,
446 0, 0, 0, 0, 0, 1, 0, 0, 0, 100, 0, 0, 2, 224, 0, 25, 0, 0, 0, 1, 0, 0, 0, 125, 255, 2,
447 68, 226, 0, 6, 11, 0, 1, 4, 0, 0, 0, 0, 29, 129, 25, 192, 0, 5, 0, 0, 0, 0, 29, 129,
451 let logger = TestLogger::new();
452 let network_graph = NetworkGraph::new(Network::Bitcoin, &logger);
454 assert_eq!(network_graph.read_only().channels().len(), 0);
456 let rapid_sync = RapidGossipSync::new(&network_graph, &logger);
457 let initialization_result = rapid_sync.update_network_graph(&initialization_input[..]);
458 assert!(initialization_result.is_ok());
460 let single_direction_incremental_update_input = vec![
461 76, 68, 75, 1, 111, 226, 140, 10, 182, 241, 179, 114, 193, 166, 162, 70, 174, 99, 247,
462 79, 147, 30, 131, 101, 225, 90, 8, 156, 104, 214, 25, 0, 0, 0, 0, 0, 97, 229, 183, 167,
463 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
464 0, 0, 0, 0, 0, 0, 0, 0, 0, 255, 8, 153, 192, 0, 2, 27, 0, 0, 136, 0, 0, 0, 221, 255, 2,
465 68, 226, 0, 6, 11, 0, 1, 128,
467 let update_result = rapid_sync.update_network_graph(&single_direction_incremental_update_input[..]);
468 if update_result.is_err() {
469 panic!("Unexpected update result: {:?}", update_result)
472 assert_eq!(network_graph.read_only().channels().len(), 2);
473 let after = network_graph.to_string();
475 after.contains("021607cfce19a4c5e7e6e738663dfafbbbac262e4ff76c2c9b30dbeefc35c00643")
478 after.contains("02247d9db0dfafea745ef8c9e161eb322f73ac3f8858d8730b6fd97254747ce76b")
481 after.contains("029e01f279986acc83ba235d46d80aede0b7595f410353b93a8ab540bb677f4432")
484 after.contains("02c913118a8895b9e29c89af6e20ed00d95a1f64e4952edbafa84d048f26804c61")
486 assert!(after.contains("619737530008010752"));
487 assert!(after.contains("783241506229452801"));
491 #[cfg(feature = "std")]
492 fn update_succeeds_when_duplicate_gossip_is_applied() {
493 let initialization_input = vec![
494 76, 68, 75, 1, 111, 226, 140, 10, 182, 241, 179, 114, 193, 166, 162, 70, 174, 99, 247,
495 79, 147, 30, 131, 101, 225, 90, 8, 156, 104, 214, 25, 0, 0, 0, 0, 0, 97, 227, 98, 218,
496 0, 0, 0, 4, 2, 22, 7, 207, 206, 25, 164, 197, 231, 230, 231, 56, 102, 61, 250, 251,
497 187, 172, 38, 46, 79, 247, 108, 44, 155, 48, 219, 238, 252, 53, 192, 6, 67, 2, 36, 125,
498 157, 176, 223, 175, 234, 116, 94, 248, 201, 225, 97, 235, 50, 47, 115, 172, 63, 136,
499 88, 216, 115, 11, 111, 217, 114, 84, 116, 124, 231, 107, 2, 158, 1, 242, 121, 152, 106,
500 204, 131, 186, 35, 93, 70, 216, 10, 237, 224, 183, 89, 95, 65, 3, 83, 185, 58, 138,
501 181, 64, 187, 103, 127, 68, 50, 2, 201, 19, 17, 138, 136, 149, 185, 226, 156, 137, 175,
502 110, 32, 237, 0, 217, 90, 31, 100, 228, 149, 46, 219, 175, 168, 77, 4, 143, 38, 128,
503 76, 97, 0, 0, 0, 2, 0, 0, 255, 8, 153, 192, 0, 2, 27, 0, 0, 0, 1, 0, 0, 255, 2, 68,
504 226, 0, 6, 11, 0, 1, 2, 3, 0, 0, 0, 4, 0, 40, 0, 0, 0, 0, 0, 0, 3, 232, 0, 0, 3, 232,
505 0, 0, 0, 1, 0, 0, 0, 0, 58, 85, 116, 216, 255, 8, 153, 192, 0, 2, 27, 0, 0, 56, 0, 0,
506 0, 0, 0, 0, 0, 1, 0, 0, 0, 100, 0, 0, 2, 224, 0, 25, 0, 0, 0, 1, 0, 0, 0, 125, 255, 2,
507 68, 226, 0, 6, 11, 0, 1, 4, 0, 0, 0, 0, 29, 129, 25, 192, 0, 5, 0, 0, 0, 0, 29, 129,
511 let logger = TestLogger::new();
512 let network_graph = NetworkGraph::new(Network::Bitcoin, &logger);
514 assert_eq!(network_graph.read_only().channels().len(), 0);
516 let rapid_sync = RapidGossipSync::new(&network_graph, &logger);
517 let initialization_result = rapid_sync.update_network_graph(&initialization_input[..]);
518 assert!(initialization_result.is_ok());
520 let single_direction_incremental_update_input = vec![
521 76, 68, 75, 1, 111, 226, 140, 10, 182, 241, 179, 114, 193, 166, 162, 70, 174, 99, 247,
522 79, 147, 30, 131, 101, 225, 90, 8, 156, 104, 214, 25, 0, 0, 0, 0, 0, 97, 229, 183, 167,
523 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
524 0, 0, 0, 0, 0, 0, 0, 0, 0, 255, 8, 153, 192, 0, 2, 27, 0, 0, 136, 0, 0, 0, 221, 255, 2,
525 68, 226, 0, 6, 11, 0, 1, 128,
527 let update_result_1 = rapid_sync.update_network_graph(&single_direction_incremental_update_input[..]);
528 // Apply duplicate update
529 let update_result_2 = rapid_sync.update_network_graph(&single_direction_incremental_update_input[..]);
530 assert!(update_result_1.is_ok());
531 assert!(update_result_2.is_ok());
535 #[cfg(feature = "std")]
536 fn full_update_succeeds() {
537 let logger = TestLogger::new();
538 let network_graph = NetworkGraph::new(Network::Bitcoin, &logger);
540 assert_eq!(network_graph.read_only().channels().len(), 0);
542 let rapid_sync = RapidGossipSync::new(&network_graph, &logger);
543 let update_result = rapid_sync.update_network_graph(&VALID_RGS_BINARY);
544 if update_result.is_err() {
545 panic!("Unexpected update result: {:?}", update_result)
548 assert_eq!(network_graph.read_only().channels().len(), 2);
549 let after = network_graph.to_string();
551 after.contains("021607cfce19a4c5e7e6e738663dfafbbbac262e4ff76c2c9b30dbeefc35c00643")
554 after.contains("02247d9db0dfafea745ef8c9e161eb322f73ac3f8858d8730b6fd97254747ce76b")
557 after.contains("029e01f279986acc83ba235d46d80aede0b7595f410353b93a8ab540bb677f4432")
560 after.contains("02c913118a8895b9e29c89af6e20ed00d95a1f64e4952edbafa84d048f26804c61")
562 assert!(after.contains("619737530008010752"));
563 assert!(after.contains("783241506229452801"));
567 fn full_update_succeeds_at_the_beginning_of_the_unix_era() {
568 let logger = TestLogger::new();
569 let network_graph = NetworkGraph::new(Network::Bitcoin, &logger);
571 assert_eq!(network_graph.read_only().channels().len(), 0);
573 let rapid_sync = RapidGossipSync::new(&network_graph, &logger);
574 // this is mostly for checking uint underflow issues before the fuzzer does
575 let update_result = rapid_sync.update_network_graph_no_std(&VALID_RGS_BINARY, Some(0));
576 assert!(update_result.is_ok());
577 assert_eq!(network_graph.read_only().channels().len(), 2);
581 fn prunes_after_update() {
582 // this is the timestamp encoded in the binary data of valid_input below
583 let logger = TestLogger::new();
585 let latest_nonpruning_time = VALID_BINARY_TIMESTAMP + 60 * 60 * 24 * 7;
588 let network_graph = NetworkGraph::new(Network::Bitcoin, &logger);
589 assert_eq!(network_graph.read_only().channels().len(), 0);
591 let rapid_sync = RapidGossipSync::new(&network_graph, &logger);
592 let update_result = rapid_sync.update_network_graph_no_std(&VALID_RGS_BINARY, Some(latest_nonpruning_time));
593 assert!(update_result.is_ok());
594 assert_eq!(network_graph.read_only().channels().len(), 2);
598 let network_graph = NetworkGraph::new(Network::Bitcoin, &logger);
599 assert_eq!(network_graph.read_only().channels().len(), 0);
601 let rapid_sync = RapidGossipSync::new(&network_graph, &logger);
602 let update_result = rapid_sync.update_network_graph_no_std(&VALID_RGS_BINARY, Some(latest_nonpruning_time + 1));
603 assert!(update_result.is_ok());
604 assert_eq!(network_graph.read_only().channels().len(), 0);
609 fn timestamp_edge_cases_are_handled_correctly() {
610 // this is the timestamp encoded in the binary data of valid_input below
611 let logger = TestLogger::new();
613 let latest_succeeding_time = VALID_BINARY_TIMESTAMP + STALE_RGS_UPDATE_AGE_LIMIT_SECS;
614 let earliest_failing_time = latest_succeeding_time + 1;
617 let network_graph = NetworkGraph::new(Network::Bitcoin, &logger);
618 assert_eq!(network_graph.read_only().channels().len(), 0);
620 let rapid_sync = RapidGossipSync::new(&network_graph, &logger);
621 let update_result = rapid_sync.update_network_graph_no_std(&VALID_RGS_BINARY, Some(latest_succeeding_time));
622 assert!(update_result.is_ok());
623 assert_eq!(network_graph.read_only().channels().len(), 0);
627 let network_graph = NetworkGraph::new(Network::Bitcoin, &logger);
628 assert_eq!(network_graph.read_only().channels().len(), 0);
630 let rapid_sync = RapidGossipSync::new(&network_graph, &logger);
631 let update_result = rapid_sync.update_network_graph_no_std(&VALID_RGS_BINARY, Some(earliest_failing_time));
632 assert!(update_result.is_err());
633 if let Err(GraphSyncError::LightningError(lightning_error)) = update_result {
636 "Rapid Gossip Sync data is more than two weeks old"
639 panic!("Unexpected update result: {:?}", update_result)
645 #[cfg(feature = "std")]
646 pub fn update_fails_with_unknown_version() {
647 let unknown_version_input = vec![
648 76, 68, 75, 2, 111, 226, 140, 10, 182, 241, 179, 114, 193, 166, 162, 70, 174, 99, 247,
649 79, 147, 30, 131, 101, 225, 90, 8, 156, 104, 214, 25, 0, 0, 0, 0, 0, 97, 227, 98, 218,
650 0, 0, 0, 4, 2, 22, 7, 207, 206, 25, 164, 197, 231, 230, 231, 56, 102, 61, 250, 251,
651 187, 172, 38, 46, 79, 247, 108, 44, 155, 48, 219, 238, 252, 53, 192, 6, 67, 2, 36, 125,
652 157, 176, 223, 175, 234, 116, 94, 248, 201, 225, 97, 235, 50, 47, 115, 172, 63, 136,
653 88, 216, 115, 11, 111, 217, 114, 84, 116, 124, 231, 107, 2, 158, 1, 242, 121, 152, 106,
654 204, 131, 186, 35, 93, 70, 216, 10, 237, 224, 183, 89, 95, 65, 3, 83, 185, 58, 138,
655 181, 64, 187, 103, 127, 68, 50, 2, 201, 19, 17, 138, 136, 149, 185, 226, 156, 137, 175,
656 110, 32, 237, 0, 217, 90, 31, 100, 228, 149, 46, 219, 175, 168, 77, 4, 143, 38, 128,
657 76, 97, 0, 0, 0, 2, 0, 0, 255, 8, 153, 192, 0, 2, 27, 0, 0, 0, 1, 0, 0, 255, 2, 68,
658 226, 0, 6, 11, 0, 1, 2, 3, 0, 0, 0, 4, 0, 40, 0, 0, 0, 0, 0, 0, 3, 232, 0, 0, 3, 232,
659 0, 0, 0, 1, 0, 0, 0, 0, 29, 129, 25, 192, 255, 8, 153, 192, 0, 2, 27, 0, 0, 60, 0, 0,
660 0, 0, 0, 0, 0, 1, 0, 0, 0, 100, 0, 0, 2, 224, 0, 0, 0, 0, 58, 85, 116, 216, 0, 29, 0,
661 0, 0, 1, 0, 0, 0, 125, 0, 0, 0, 0, 58, 85, 116, 216, 255, 2, 68, 226, 0, 6, 11, 0, 1,
665 let logger = TestLogger::new();
666 let network_graph = NetworkGraph::new(Network::Bitcoin, &logger);
667 let rapid_sync = RapidGossipSync::new(&network_graph, &logger);
668 let update_result = rapid_sync.update_network_graph(&unknown_version_input[..]);
670 assert!(update_result.is_err());
672 if let Err(GraphSyncError::DecodeError(DecodeError::UnknownVersion)) = update_result {
673 // this is the expected error type
675 panic!("Unexpected update result: {:?}", update_result)
680 fn fails_early_on_chain_hash_mismatch() {
681 let logger = TestLogger::new();
682 // Set to testnet so that the VALID_RGS_BINARY chain hash of mainnet does not match.
683 let network_graph = NetworkGraph::new(Network::Testnet, &logger);
685 assert_eq!(network_graph.read_only().channels().len(), 0);
687 let rapid_sync = RapidGossipSync::new(&network_graph, &logger);
688 let update_result = rapid_sync.update_network_graph_no_std(&VALID_RGS_BINARY, Some(0));
689 assert!(update_result.is_err());
690 if let Err(GraphSyncError::LightningError(err)) = update_result {
691 assert_eq!(err.err, "Rapid Gossip Sync data's chain hash does not match the network graph's");
693 panic!("Unexpected update result: {:?}", update_result)