Skip to content

Commit b99b8b6

Browse files
committed
Support negotiating anchors throughout channel open
1 parent f3d433b commit b99b8b6

File tree

4 files changed

+252
-22
lines changed

4 files changed

+252
-22
lines changed

lightning/src/ln/channel.rs

+214-20
Original file line numberDiff line numberDiff line change
@@ -881,11 +881,20 @@ impl<Signer: Sign> Channel<Signer> {
881881
// The default channel type (ie the first one we try) depends on whether the channel is
882882
// public - if it is, we just go with `only_static_remotekey` as it's the only option
883883
// available. If it's private, we first try `scid_privacy` as it provides better privacy
884-
// with no other changes, and fall back to `only_static_remotekey`
884+
// with no other changes, and fall back to `only_static_remotekey`.
885885
let mut ret = ChannelTypeFeatures::only_static_remote_key();
886886
if !config.channel_handshake_config.announced_channel && config.channel_handshake_config.negotiate_scid_privacy {
887887
ret.set_scid_privacy_required();
888888
}
889+
890+
// Optionally, if the user would like to negotiate the `anchors_zero_fee_htlc_tx` option, we
891+
// set it now. If they don't understand it, we'll fall back to our default of
892+
// `only_static_remotekey`.
893+
#[cfg(anchors)]
894+
if config.channel_handshake_config.negotiate_anchors_zero_fee_htlc_tx {
895+
ret.set_anchors_zero_fee_htlc_tx_required();
896+
}
897+
889898
ret
890899
}
891900

@@ -898,7 +907,17 @@ impl<Signer: Sign> Channel<Signer> {
898907
// We've exhausted our options
899908
return Err(());
900909
}
901-
self.channel_type = ChannelTypeFeatures::only_static_remote_key(); // We only currently support two types
910+
// We support opening a few different types of channels. Try removing our additional
911+
// features one by one until we've either arrived at our default or the counterparty has
912+
// accepted one.
913+
if self.channel_type.supports_anchors_zero_fee_htlc_tx() {
914+
self.channel_type.clear_anchors_zero_fee_htlc_tx();
915+
self.channel_transaction_parameters.opt_anchors = None;
916+
} else if self.channel_type.supports_scid_privacy() {
917+
self.channel_type.clear_scid_privacy();
918+
} else {
919+
self.channel_type = ChannelTypeFeatures::only_static_remote_key();
920+
}
902921
Ok(self.get_open_channel(chain_hash))
903922
}
904923

@@ -911,7 +930,11 @@ impl<Signer: Sign> Channel<Signer> {
911930
where K::Target: KeysInterface<Signer = Signer>,
912931
F::Target: FeeEstimator,
913932
{
914-
let opt_anchors = false; // TODO - should be based on features
933+
#[cfg(anchors)]
934+
let opt_anchors = config.channel_handshake_config.negotiate_anchors_zero_fee_htlc_tx &&
935+
their_features.supports_anchors_zero_fee_htlc_tx();
936+
#[cfg(not(anchors))]
937+
let opt_anchors = false;
915938

916939
let holder_selected_contest_delay = config.channel_handshake_config.our_to_self_delay;
917940
let channel_keys_id = keys_provider.generate_channel_keys_id(false, channel_value_satoshis, user_id);
@@ -1124,7 +1147,6 @@ impl<Signer: Sign> Channel<Signer> {
11241147
F::Target: FeeEstimator,
11251148
L::Target: Logger,
11261149
{
1127-
let opt_anchors = false; // TODO - should be based on features
11281150
let announced_channel = if (msg.channel_flags & 1) == 1 { true } else { false };
11291151

11301152
// First check the channel type is known, failing before we do anything else if we don't
@@ -1138,13 +1160,24 @@ impl<Signer: Sign> Channel<Signer> {
11381160
return Err(ChannelError::Close("Channel Type field contains unknown bits".to_owned()));
11391161
}
11401162

1141-
// We currently only allow four channel types, so write it all out here - we allow
1142-
// `only_static_remote_key` or `static_remote_key | zero_conf` in all contexts, and
1143-
// further allow `static_remote_key | scid_privacy` or
1144-
// `static_remote_key | scid_privacy | zero_conf`, if the channel is not
1145-
// publicly announced.
1163+
// We currently allow 8 channel types, and all must support `static_remote_key`, so
1164+
// write it all out here - we allow
1165+
// - `only_static_remote_key`
1166+
// - `static_remote_key | zero_conf`
1167+
// - `static_remote_key | scid_privacy`
1168+
// - `static_remote_key | scid_privacy | zero_conf`
1169+
// - `static_remote_key | anchors_zero_fee_htlc_tx`
1170+
// - `static_remote_key | anchors_zero_fee_htlc_tx | zero_conf`
1171+
// - `static_remote_key | anchors_zero_fee_htlc_tx | scid_privacy`
1172+
// - `static_remote_key | anchors_zero_fee_htlc_tx | scid_privacy | zero_conf`
1173+
if !channel_type.requires_static_remote_key() {
1174+
return Err(ChannelError::Close("Channel Type was not understood - we require static remote key".to_owned()));
1175+
}
11461176
if *channel_type != ChannelTypeFeatures::only_static_remote_key() {
1147-
if !channel_type.requires_scid_privacy() && !channel_type.requires_zero_conf() {
1177+
// If we have more features than just `static_remote_key`, make sure we only allow
1178+
// those we support.
1179+
if !channel_type.requires_scid_privacy() && !channel_type.requires_zero_conf() &&
1180+
!channel_type.requires_anchors_zero_fee_htlc_tx() {
11481181
return Err(ChannelError::Close("Channel Type was not understood".to_owned()));
11491182
}
11501183

@@ -1154,11 +1187,16 @@ impl<Signer: Sign> Channel<Signer> {
11541187
}
11551188
channel_type.clone()
11561189
} else {
1157-
ChannelTypeFeatures::from_counterparty_init(&their_features)
1190+
let channel_type = ChannelTypeFeatures::from_counterparty_init(&their_features);
1191+
if channel_type != ChannelTypeFeatures::only_static_remote_key() {
1192+
return Err(ChannelError::Close("Only static_remote_key is supported for non-negotiated channel types".to_owned()));
1193+
}
1194+
channel_type
11581195
};
1159-
if !channel_type.supports_static_remote_key() {
1160-
return Err(ChannelError::Close("Channel Type was not understood - we require static remote key".to_owned()));
1161-
}
1196+
#[cfg(anchors)]
1197+
let opt_anchors = channel_type.supports_anchors_zero_fee_htlc_tx();
1198+
#[cfg(not(anchors))]
1199+
let opt_anchors = false;
11621200

11631201
let channel_keys_id = keys_provider.generate_channel_keys_id(true, msg.funding_satoshis, user_id);
11641202
let holder_signer = keys_provider.derive_channel_signer(msg.funding_satoshis, channel_keys_id);
@@ -2128,7 +2166,16 @@ impl<Signer: Sign> Channel<Signer> {
21282166
} else if their_features.supports_channel_type() {
21292167
// Assume they've accepted the channel type as they said they understand it.
21302168
} else {
2131-
self.channel_type = ChannelTypeFeatures::from_counterparty_init(&their_features)
2169+
let channel_type = ChannelTypeFeatures::from_counterparty_init(&their_features);
2170+
if channel_type.requires_unknown_bits() {
2171+
return Err(ChannelError::Close("Peer's features contain unknown ChannelType features".to_owned()));
2172+
}
2173+
self.channel_type = channel_type;
2174+
self.channel_transaction_parameters.opt_anchors = if self.channel_type.supports_anchors_zero_fee_htlc_tx() {
2175+
Some(())
2176+
} else {
2177+
None
2178+
};
21322179
}
21332180

21342181
let counterparty_shutdown_scriptpubkey = if their_features.supports_upfront_shutdown_script() {
@@ -6654,11 +6701,6 @@ impl<'a, K: Deref> ReadableArgs<(&'a K, u32)> for Channel<<K::Target as KeysInte
66546701
return Err(DecodeError::UnknownRequiredFeature);
66556702
}
66566703

6657-
if channel_parameters.opt_anchors.is_some() {
6658-
// Relax this check when ChannelTypeFeatures supports anchors.
6659-
return Err(DecodeError::InvalidValue);
6660-
}
6661-
66626704
let mut secp_ctx = Secp256k1::new();
66636705
secp_ctx.seeded_randomize(&keys_source.get_secure_random_bytes());
66646706

@@ -6793,6 +6835,8 @@ mod tests {
67936835
use hex;
67946836
use crate::ln::PaymentHash;
67956837
use crate::ln::channelmanager::{self, HTLCSource, PaymentId};
6838+
#[cfg(anchors)]
6839+
use crate::ln::channel::InitFeatures;
67966840
use crate::ln::channel::{Channel, InboundHTLCOutput, OutboundHTLCOutput, InboundHTLCState, OutboundHTLCState, HTLCCandidate, HTLCInitiator};
67976841
use crate::ln::channel::{MAX_FUNDING_SATOSHIS_NO_WUMBO, TOTAL_BITCOIN_SUPPLY_SATOSHIS, MIN_THEIR_CHAN_RESERVE_SATOSHIS};
67986842
use crate::ln::features::ChannelTypeFeatures;
@@ -6807,6 +6851,8 @@ mod tests {
68076851
use crate::util::config::UserConfig;
68086852
use crate::util::enforcing_trait_impls::EnforcingSigner;
68096853
use crate::util::errors::APIError;
6854+
#[cfg(anchors)]
6855+
use crate::util::ser::Writeable;
68106856
use crate::util::test_utils;
68116857
use crate::util::test_utils::OnGetShutdownScriptpubkey;
68126858
use bitcoin::secp256k1::{Secp256k1, ecdsa::Signature, Scalar};
@@ -8069,4 +8115,152 @@ mod tests {
80698115
node_b_node_id, &channelmanager::provided_init_features(), &open_channel_msg, 7, &config, 0, &&logger, 42);
80708116
assert!(res.is_ok());
80718117
}
8118+
8119+
#[cfg(anchors)]
8120+
#[test]
8121+
fn test_supports_anchors_zero_htlc_tx_fee() {
8122+
// Tests that if both sides support and negotiate `anchors_zero_fee_htlc_tx`, it is the
8123+
// resulting `channel_type`.
8124+
let secp_ctx = Secp256k1::new();
8125+
let fee_estimator = LowerBoundedFeeEstimator::new(&TestFeeEstimator{fee_est: 15000});
8126+
let network = Network::Testnet;
8127+
let keys_provider = test_utils::TestKeysInterface::new(&[42; 32], network);
8128+
let logger = test_utils::TestLogger::new();
8129+
8130+
let node_id_a = PublicKey::from_secret_key(&secp_ctx, &SecretKey::from_slice(&[1; 32]).unwrap());
8131+
let node_id_b = PublicKey::from_secret_key(&secp_ctx, &SecretKey::from_slice(&[2; 32]).unwrap());
8132+
8133+
let mut config = UserConfig::default();
8134+
config.channel_handshake_config.negotiate_anchors_zero_fee_htlc_tx = true;
8135+
8136+
let mut expected_channel_type = ChannelTypeFeatures::empty();
8137+
expected_channel_type.set_static_remote_key_required();
8138+
expected_channel_type.set_anchors_zero_fee_htlc_tx_required();
8139+
8140+
let channel_a = Channel::<EnforcingSigner>::new_outbound(
8141+
&fee_estimator, &&keys_provider, node_id_b, &channelmanager::provided_init_features(),
8142+
10000000, 100000, 42, &config, 0, 42
8143+
).unwrap();
8144+
8145+
let open_channel_msg = channel_a.get_open_channel(genesis_block(network).header.block_hash());
8146+
let channel_b = Channel::<EnforcingSigner>::new_from_req(
8147+
&fee_estimator, &&keys_provider, node_id_a, &channelmanager::provided_init_features(),
8148+
&open_channel_msg, 7, &config, 0, &&logger, 42
8149+
).unwrap();
8150+
8151+
assert_eq!(channel_a.channel_type, expected_channel_type);
8152+
assert_eq!(channel_b.channel_type, expected_channel_type);
8153+
}
8154+
8155+
#[cfg(anchors)]
8156+
#[test]
8157+
fn test_rejects_implicit_simple_anchors() {
8158+
// Tests that if `option_anchors` is being negotiated implicitly through the intersection of
8159+
// each side's `InitFeatures`, it is rejected.
8160+
let secp_ctx = Secp256k1::new();
8161+
let fee_estimator = LowerBoundedFeeEstimator::new(&TestFeeEstimator{fee_est: 15000});
8162+
let network = Network::Testnet;
8163+
let keys_provider = test_utils::TestKeysInterface::new(&[42; 32], network);
8164+
let logger = test_utils::TestLogger::new();
8165+
8166+
let node_id_a = PublicKey::from_secret_key(&secp_ctx, &SecretKey::from_slice(&[1; 32]).unwrap());
8167+
let node_id_b = PublicKey::from_secret_key(&secp_ctx, &SecretKey::from_slice(&[2; 32]).unwrap());
8168+
8169+
let config = UserConfig::default();
8170+
8171+
// See feature bit assignments: https://github.com/lightning/bolts/blob/master/09-features.md
8172+
let static_remote_key_required: u64 = 1 << 12;
8173+
let simple_anchors_required: u64 = 1 << 20;
8174+
let raw_init_features = static_remote_key_required | simple_anchors_required;
8175+
let init_features_with_simple_anchors = InitFeatures::from_le_bytes(raw_init_features.to_le_bytes().to_vec());
8176+
8177+
let channel_a = Channel::<EnforcingSigner>::new_outbound(
8178+
&fee_estimator, &&keys_provider, node_id_b, &channelmanager::provided_init_features(),
8179+
10000000, 100000, 42, &config, 0, 42
8180+
).unwrap();
8181+
8182+
// Set `channel_type` to `None` to force the implicit feature negotiation.
8183+
let mut open_channel_msg = channel_a.get_open_channel(genesis_block(network).header.block_hash());
8184+
open_channel_msg.channel_type = None;
8185+
8186+
// Since A supports both `static_remote_key` and `option_anchors`, but B only supports
8187+
// `static_remote_key`, the resulting channel will succeed with only `static_remote_key`.
8188+
let channel_b = Channel::<EnforcingSigner>::new_from_req(
8189+
&fee_estimator, &&keys_provider, node_id_a, &init_features_with_simple_anchors,
8190+
&open_channel_msg, 7, &config, 0, &&logger, 42
8191+
).unwrap();
8192+
8193+
// Verify the resulting `channel_type` is indeed only `static_remote_key`.
8194+
let mut encoded_channel_type = [0; 8];
8195+
encoded_channel_type[1..8].copy_from_slice(channel_b.channel_type.encode().as_slice());
8196+
let mut encoded_only_static_remote_key = [0; 8];
8197+
encoded_only_static_remote_key[6..8].copy_from_slice(ChannelTypeFeatures::only_static_remote_key().encode().as_slice());
8198+
assert_eq!(u64::from_be_bytes(encoded_channel_type), u64::from_be_bytes(encoded_only_static_remote_key));
8199+
assert_eq!(u64::from_be_bytes(encoded_channel_type), u64::from_be_bytes(encoded_only_static_remote_key));
8200+
}
8201+
8202+
#[cfg(anchors)]
8203+
#[test]
8204+
fn test_rejects_simple_anchors_channel_type() {
8205+
// Tests that if `option_anchors` is being negotiated through the `channel_type` feature,
8206+
// it is rejected.
8207+
let secp_ctx = Secp256k1::new();
8208+
let fee_estimator = LowerBoundedFeeEstimator::new(&TestFeeEstimator{fee_est: 15000});
8209+
let network = Network::Testnet;
8210+
let keys_provider = test_utils::TestKeysInterface::new(&[42; 32], network);
8211+
let logger = test_utils::TestLogger::new();
8212+
8213+
let node_id_a = PublicKey::from_secret_key(&secp_ctx, &SecretKey::from_slice(&[1; 32]).unwrap());
8214+
let node_id_b = PublicKey::from_secret_key(&secp_ctx, &SecretKey::from_slice(&[2; 32]).unwrap());
8215+
8216+
let config = UserConfig::default();
8217+
8218+
// See feature bit assignments: https://github.com/lightning/bolts/blob/master/09-features.md
8219+
let static_remote_key_required: u64 = 1 << 12;
8220+
let simple_anchors_required: u64 = 1 << 20;
8221+
let simple_anchors_raw_features = static_remote_key_required | simple_anchors_required;
8222+
let simple_anchors_features = InitFeatures::from_le_bytes(simple_anchors_raw_features.to_le_bytes().to_vec());
8223+
let simple_anchors_channel_type = ChannelTypeFeatures::from_counterparty_init(&simple_anchors_features);
8224+
8225+
// First, we'll try to open a channel between A and B where A requests a channel type for
8226+
// the original `option_anchors` feature (non zero fee htlc tx). This should be rejected by
8227+
// B as it's not supported by LDK.
8228+
let channel_a = Channel::<EnforcingSigner>::new_outbound(
8229+
&fee_estimator, &&keys_provider, node_id_b, &channelmanager::provided_init_features(),
8230+
10000000, 100000, 42, &config, 0, 42
8231+
).unwrap();
8232+
8233+
let mut open_channel_msg = channel_a.get_open_channel(genesis_block(network).header.block_hash());
8234+
open_channel_msg.channel_type = Some(simple_anchors_channel_type.clone());
8235+
8236+
let res = Channel::<EnforcingSigner>::new_from_req(
8237+
&fee_estimator, &&keys_provider, node_id_a, &simple_anchors_features, &open_channel_msg,
8238+
7, &config, 0, &&logger, 42
8239+
);
8240+
assert!(res.is_err());
8241+
8242+
// Then, we'll try to open another channel where A requests a channel type for
8243+
// `anchors_zero_fee_htlc_tx`. B is malicious and tries to downgrade the channel type to the
8244+
// original `option_anchors` feature, which should be rejected by A as it's not supported by
8245+
// LDK.
8246+
let mut channel_a = Channel::<EnforcingSigner>::new_outbound(
8247+
&fee_estimator, &&keys_provider, node_id_b, &simple_anchors_features,
8248+
10000000, 100000, 42, &config, 0, 42
8249+
).unwrap();
8250+
8251+
let open_channel_msg = channel_a.get_open_channel(genesis_block(network).header.block_hash());
8252+
8253+
let channel_b = Channel::<EnforcingSigner>::new_from_req(
8254+
&fee_estimator, &&keys_provider, node_id_a, &channelmanager::provided_init_features(),
8255+
&open_channel_msg, 7, &config, 0, &&logger, 42
8256+
).unwrap();
8257+
8258+
let mut accept_channel_msg = channel_b.get_accept_channel_message();
8259+
accept_channel_msg.channel_type = Some(simple_anchors_channel_type.clone());
8260+
8261+
let res = channel_a.accept_channel(
8262+
&accept_channel_msg, &config.channel_handshake_limits, &simple_anchors_features
8263+
);
8264+
assert!(res.is_err());
8265+
}
80728266
}

lightning/src/ln/channelmanager.rs

+1
Original file line numberDiff line numberDiff line change
@@ -6559,6 +6559,7 @@ pub fn provided_init_features() -> InitFeatures {
65596559
features.set_channel_type_optional();
65606560
features.set_scid_privacy_optional();
65616561
features.set_zero_conf_optional();
6562+
#[cfg(anchors)]
65626563
features.set_anchors_zero_fee_htlc_tx_optional();
65636564
features
65646565
}

lightning/src/ln/features.rs

+13
Original file line numberDiff line numberDiff line change
@@ -698,6 +698,18 @@ impl<T: sealed::Wumbo> Features<T> {
698698
}
699699
}
700700

701+
impl<T: sealed::SCIDPrivacy> Features<T> {
702+
pub(crate) fn clear_scid_privacy(&mut self) {
703+
<T as sealed::SCIDPrivacy>::clear_bits(&mut self.flags);
704+
}
705+
}
706+
707+
impl<T: sealed::AnchorsZeroFeeHtlcTx> Features<T> {
708+
pub(crate) fn clear_anchors_zero_fee_htlc_tx(&mut self) {
709+
<T as sealed::AnchorsZeroFeeHtlcTx>::clear_bits(&mut self.flags);
710+
}
711+
}
712+
701713
#[cfg(test)]
702714
impl<T: sealed::UnknownFeature> Features<T> {
703715
pub(crate) fn unknown() -> Self {
@@ -787,6 +799,7 @@ mod tests {
787799
init_features.set_channel_type_optional();
788800
init_features.set_scid_privacy_optional();
789801
init_features.set_zero_conf_optional();
802+
init_features.set_anchors_zero_fee_htlc_tx_optional();
790803

791804
assert!(init_features.initial_routing_sync());
792805
assert!(!init_features.supports_upfront_shutdown_script());

lightning/src/util/config.rs

+24-2
Original file line numberDiff line numberDiff line change
@@ -126,7 +126,6 @@ pub struct ChannelHandshakeConfig {
126126
///
127127
/// [`KeysInterface::get_shutdown_scriptpubkey`]: crate::chain::keysinterface::KeysInterface::get_shutdown_scriptpubkey
128128
pub commit_upfront_shutdown_pubkey: bool,
129-
130129
/// The Proportion of the channel value to configure as counterparty's channel reserve,
131130
/// i.e., `their_channel_reserve_satoshis` for both outbound and inbound channels.
132131
///
@@ -149,7 +148,28 @@ pub struct ChannelHandshakeConfig {
149148
/// as 1000 sats instead, which is a safe implementation-specific lower bound.
150149
/// Maximum value: 1,000,000, any values larger than 1 Million will be treated as 1 Million (or 100%)
151150
/// instead, although channel negotiations will fail in that case.
152-
pub their_channel_reserve_proportional_millionths: u32
151+
pub their_channel_reserve_proportional_millionths: u32,
152+
#[cfg(anchors)]
153+
/// If set, we attempt to negotiate the `anchors_zero_fee_htlc_tx`option for outbound channels.
154+
///
155+
/// If this option is set, channels may be created that will not be readable by LDK versions
156+
/// prior to 0.0.114, causing [`ChannelManager`]'s read method to return a
157+
/// [`DecodeError::InvalidValue`].
158+
///
159+
/// Note that setting this to true does *not* prevent us from opening channels with
160+
/// counterparties that do not support the `anchors_zero_fee_htlc_tx` option; we will simply
161+
/// fall back to a `static_remote_key` channel.
162+
///
163+
/// LDK will not support the legacy `option_anchors` commitment version due to a discovered
164+
/// vulnerability after its deployment. For more context, see the [`SIGHASH_SINGLE + update_fee
165+
/// Considered Harmful`] mailing list post.
166+
///
167+
/// Default value: false. This value is likely to change to true in the future.
168+
///
169+
/// [`ChannelManager`]: crate::ln::channelmanager::ChannelManager
170+
/// [`DecodeError::InvalidValue`]: crate::ln::msgs::DecodeError::InvalidValue
171+
/// [`SIGHASH_SINGLE + update_fee Considered Harmful`]: https://lists.linuxfoundation.org/pipermail/lightning-dev/2020-September/002796.html
172+
pub negotiate_anchors_zero_fee_htlc_tx: bool,
153173
}
154174

155175
impl Default for ChannelHandshakeConfig {
@@ -163,6 +183,8 @@ impl Default for ChannelHandshakeConfig {
163183
announced_channel: false,
164184
commit_upfront_shutdown_pubkey: true,
165185
their_channel_reserve_proportional_millionths: 10_000,
186+
#[cfg(anchors)]
187+
negotiate_anchors_zero_fee_htlc_tx: false,
166188
}
167189
}
168190
}

0 commit comments

Comments
 (0)