Skip to content
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
37 changes: 23 additions & 14 deletions lightning/src/ln/channelmanager.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1267,22 +1267,30 @@ impl<Signer: Sign, M: Deref, T: Deref, K: Deref, F: Deref, L: Deref> ChannelMana

/// Creates a new outbound channel to the given remote node and with the given value.
///
/// user_id will be provided back as user_channel_id in FundingGenerationReady events to allow
/// tracking of which events correspond with which create_channel call. Note that the
/// user_channel_id defaults to 0 for inbound channels, so you may wish to avoid using 0 for
/// user_id here. user_id has no meaning inside of LDK, it is simply copied to events and
/// otherwise ignored.
/// `user_id` will be provided back as `user_channel_id` in [`Event::FundingGenerationReady`]
/// to allow tracking of which events correspond with which `create_channel` call. Note that
/// the `user_channel_id` defaults to 0 for inbound channels, so you may wish to avoid using 0
/// for `user_id` here. `user_id` has no meaning inside of LDK, it is simply copied to events
/// and otherwise ignored.
///
/// If successful, will generate a SendOpenChannel message event, so you should probably poll
/// PeerManager::process_events afterwards.
///
/// Raises APIError::APIMisuseError when channel_value_satoshis > 2**24 or push_msat is
/// greater than channel_value_satoshis * 1k or channel_value_satoshis is < 1000.
/// Raises [`APIError::APIMisuseError`] when `channel_value_satoshis` > 2**24 or `push_msat` is
/// greater than `channel_value_satoshis * 1k` or `channel_value_satoshis < 1000`.
///
/// Note that we do not check if you are currently connected to the given peer. If no
/// connection is available, the outbound `open_channel` message may fail to send, resulting in
/// the channel eventually being silently forgotten.
pub fn create_channel(&self, their_network_key: PublicKey, channel_value_satoshis: u64, push_msat: u64, user_id: u64, override_config: Option<UserConfig>) -> Result<(), APIError> {
/// the channel eventually being silently forgotten (dropped on reload).
///
/// Returns the new Channel's temporary `channel_id`. This ID will appear as
/// [`Event::FundingGenerationReady::temporary_channel_id`] and in
/// [`ChannelDetails::channel_id`] until after
/// [`ChannelManager::funding_transaction_generated`] is called, swapping the Channel's ID for
/// one derived from the funding transaction's TXID. If the counterparty rejects the channel
/// immediately, this temporary ID will appear in [`Event::ChannelClosed::channel_id`].
///
/// [`Event::FundingGenerationReady`]: events::Event::FundingGenerationReady
/// [`Event::FundingGenerationReady::temporary_channel_id`]: events::Event::FundingGenerationReady::temporary_channel_id
/// [`Event::ChannelClosed::channel_id`]: events::Event::ChannelClosed::channel_id
pub fn create_channel(&self, their_network_key: PublicKey, channel_value_satoshis: u64, push_msat: u64, user_id: u64, override_config: Option<UserConfig>) -> Result<[u8; 32], APIError> {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Would it make sense to create a type alias for the channel id here instead of just [u8; 32]?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yea, maybe lets do that as a part of addressing #105? We'll want to separate the types out between temporary channel ids and permanent ones, I think.

if channel_value_satoshis < 1000 {
return Err(APIError::APIMisuseError { err: format!("Channel value must be at least 1000 satoshis. It was {}", channel_value_satoshis) });
}
Expand All @@ -1305,8 +1313,9 @@ impl<Signer: Sign, M: Deref, T: Deref, K: Deref, F: Deref, L: Deref> ChannelMana
// We want to make sure the lock is actually acquired by PersistenceNotifierGuard.
debug_assert!(&self.total_consistency_lock.try_write().is_err());

let temporary_channel_id = channel.channel_id();
let mut channel_state = self.channel_state.lock().unwrap();
match channel_state.by_id.entry(channel.channel_id()) {
match channel_state.by_id.entry(temporary_channel_id) {
hash_map::Entry::Occupied(_) => {
if cfg!(feature = "fuzztarget") {
return Err(APIError::APIMisuseError { err: "Fuzzy bad RNG".to_owned() });
Expand All @@ -1320,7 +1329,7 @@ impl<Signer: Sign, M: Deref, T: Deref, K: Deref, F: Deref, L: Deref> ChannelMana
node_id: their_network_key,
msg: res,
});
Ok(())
Ok(temporary_channel_id)
}

fn list_channels_with_filter<Fn: FnMut(&(&[u8; 32], &Channel<Signer>)) -> bool>(&self, f: Fn) -> Vec<ChannelDetails> {
Expand Down
3 changes: 2 additions & 1 deletion lightning/src/ln/functional_test_utils.rs
Original file line number Diff line number Diff line change
Expand Up @@ -512,11 +512,12 @@ pub fn create_funding_transaction<'a, 'b, 'c>(node: &Node<'a, 'b, 'c>, expected_
}

pub fn create_chan_between_nodes_with_value_init<'a, 'b, 'c>(node_a: &Node<'a, 'b, 'c>, node_b: &Node<'a, 'b, 'c>, channel_value: u64, push_msat: u64, a_flags: InitFeatures, b_flags: InitFeatures) -> Transaction {
node_a.node.create_channel(node_b.node.get_our_node_id(), channel_value, push_msat, 42, None).unwrap();
let create_chan_id = node_a.node.create_channel(node_b.node.get_our_node_id(), channel_value, push_msat, 42, None).unwrap();
node_b.node.handle_open_channel(&node_a.node.get_our_node_id(), a_flags, &get_event_msg!(node_a, MessageSendEvent::SendOpenChannel, node_b.node.get_our_node_id()));
node_a.node.handle_accept_channel(&node_b.node.get_our_node_id(), b_flags, &get_event_msg!(node_b, MessageSendEvent::SendAcceptChannel, node_a.node.get_our_node_id()));

let (temporary_channel_id, tx, funding_output) = create_funding_transaction(node_a, channel_value, 42);
assert_eq!(temporary_channel_id, create_chan_id);

node_a.node.funding_transaction_generated(&temporary_channel_id, tx.clone()).unwrap();
check_added_monitors!(node_a, 0);
Expand Down