Skip to content

Commit bd87452

Browse files
committed
sim-node: validate channel policy and enforce unique scid
1 parent d8b5971 commit bd87452

File tree

1 file changed

+48
-2
lines changed

1 file changed

+48
-2
lines changed

sim-lib/src/sim_node.rs

Lines changed: 48 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -122,6 +122,25 @@ pub struct ChannelPolicy {
122122
pub fee_rate_prop: u64,
123123
}
124124

125+
impl ChannelPolicy {
126+
/// Validates that the channel policy is acceptable for the size of the channel.
127+
fn validate(&self, capacity_msat: u64) -> Result<(), SimulationError> {
128+
if self.max_in_flight_msat > capacity_msat {
129+
return Err(SimulationError::SimulatedNetworkError(format!(
130+
"max_in_flight_msat {} > capacity {}",
131+
self.max_in_flight_msat, capacity_msat
132+
)));
133+
}
134+
if self.max_htlc_size_msat > capacity_msat {
135+
return Err(SimulationError::SimulatedNetworkError(format!(
136+
"max_htlc_size_msat {} > capacity {}",
137+
self.max_htlc_size_msat, capacity_msat
138+
)));
139+
}
140+
Ok(())
141+
}
142+
}
143+
125144
/// Fails with the forwarding error provided if the value provided fails its inequality check.
126145
macro_rules! fail_forwarding_inequality {
127146
($value_1:expr, $op:tt, $value_2:expr, $error_variant:ident $(, $opt:expr)*) => {
@@ -291,6 +310,21 @@ impl SimulatedChannel {
291310
}
292311
}
293312

313+
/// Validates that a simulated channel has distinct node pairs and valid routing policies.
314+
fn validate(&self) -> Result<(), SimulationError> {
315+
if self.node_1.policy.pubkey == self.node_2.policy.pubkey {
316+
return Err(SimulationError::SimulatedNetworkError(format!(
317+
"Channel should have distinct node pubkeys, got: {} for both nodes.",
318+
self.node_1.policy.pubkey
319+
)));
320+
}
321+
322+
self.node_1.policy.validate(self.capacity_msat)?;
323+
self.node_2.policy.validate(self.capacity_msat)?;
324+
325+
Ok(())
326+
}
327+
294328
fn get_node_mut(&mut self, pubkey: &PublicKey) -> Result<&mut ChannelState, ForwardingError> {
295329
if pubkey == &self.node_1.policy.pubkey {
296330
Ok(&mut self.node_1)
@@ -617,13 +651,25 @@ impl SimGraph {
617651
pub fn new(
618652
graph_channels: Vec<SimulatedChannel>,
619653
shutdown_trigger: Trigger,
620-
) -> Result<Self, LdkError> {
654+
) -> Result<Self, SimulationError> {
621655
let mut nodes: HashMap<PublicKey, Vec<u64>> = HashMap::new();
622656
let mut channels = HashMap::new();
623657

624658
for channel in graph_channels.iter() {
625-
channels.insert(channel.short_channel_id, channel.clone());
659+
// Assert that the channel is valid and that its short channel ID is unique within the simulation, required
660+
// because we use scid to identify the channel.
661+
channel.validate()?;
662+
match channels.entry(channel.short_channel_id) {
663+
Entry::Occupied(_) => {
664+
return Err(SimulationError::SimulatedNetworkError(format!(
665+
"Simulated short channel ID should be unique: {} duplicated",
666+
channel.short_channel_id
667+
)))
668+
},
669+
Entry::Vacant(v) => v.insert(channel.clone()),
670+
};
626671

672+
// It's okay to have duplicate pubkeys because one node can have many channels.
627673
for pubkey in [channel.node_1.policy.pubkey, channel.node_2.policy.pubkey] {
628674
match nodes.entry(pubkey) {
629675
Entry::Occupied(o) => o.into_mut().push(channel.capacity_msat),

0 commit comments

Comments
 (0)