Skip to content

Commit 3d13ccd

Browse files
committed
introduce DynSigner and TestSignerFactory
1 parent 1c0625d commit 3d13ccd

File tree

7 files changed

+547
-90
lines changed

7 files changed

+547
-90
lines changed

lightning-invoice/src/payment.rs

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -91,6 +91,8 @@ mod tests {
9191
use core::time::Duration;
9292
#[cfg(feature = "std")]
9393
use std::time::SystemTime;
94+
use bech32::ToBase32;
95+
use lightning::sign::{NodeSigner, Recipient};
9496

9597
fn duration_since_epoch() -> Duration {
9698
#[cfg(feature = "std")]
@@ -194,11 +196,10 @@ mod tests {
194196
.min_final_cltv_expiry_delta(144)
195197
.amount_milli_satoshis(50_000)
196198
.payment_metadata(payment_metadata.clone())
197-
.build_signed(|hash| {
198-
Secp256k1::new().sign_ecdsa_recoverable(hash,
199-
&nodes[1].keys_manager.backing.get_node_secret_key())
200-
})
201-
.unwrap();
199+
.build_raw().unwrap();
200+
let sig = nodes[1].keys_manager.backing.sign_invoice(invoice.hrp.to_string().as_bytes(), &invoice.data.to_base32(), Recipient::Node).unwrap();
201+
let invoice = invoice.sign::<_, ()>(|_| Ok(sig)).unwrap();
202+
let invoice = Bolt11Invoice::from_signed(invoice).unwrap();
202203

203204
let (hash, onion, params) = payment_parameters_from_invoice(&invoice).unwrap();
204205
nodes[0].node.send_payment(hash, onion, PaymentId(hash.0), params, Retry::Attempts(0)).unwrap();

lightning-invoice/src/utils.rs

Lines changed: 32 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -835,6 +835,7 @@ mod test {
835835
use lightning::util::config::UserConfig;
836836
use crate::utils::{create_invoice_from_channelmanager_and_duration_since_epoch, rotate_through_iterators};
837837
use std::collections::HashSet;
838+
use lightning::util::dyn_signer::{DynKeysInterface, DynPhantomKeysInterface};
838839
use lightning::util::string::UntrustedString;
839840

840841
#[test]
@@ -1295,6 +1296,13 @@ mod test {
12951296
do_test_multi_node_receive(false);
12961297
}
12971298

1299+
fn make_dyn_keys_interface(seed: &[u8; 32]) -> DynKeysInterface {
1300+
let cross_node_seed = [44u8; 32];
1301+
let inner = PhantomKeysManager::new(&seed, 43, 44, &cross_node_seed);
1302+
let dyn_inner = DynPhantomKeysInterface::new(inner);
1303+
DynKeysInterface::new(Box::new(dyn_inner))
1304+
}
1305+
12981306
#[cfg(feature = "std")]
12991307
fn do_test_multi_node_receive(user_generated_pmt_hash: bool) {
13001308
use lightning::events::{Event, EventsProvider};
@@ -1303,9 +1311,8 @@ mod test {
13031311
let mut chanmon_cfgs = create_chanmon_cfgs(3);
13041312
let seed_1 = [42u8; 32];
13051313
let seed_2 = [43u8; 32];
1306-
let cross_node_seed = [44u8; 32];
1307-
chanmon_cfgs[1].keys_manager.backing = PhantomKeysManager::new(&seed_1, 43, 44, &cross_node_seed);
1308-
chanmon_cfgs[2].keys_manager.backing = PhantomKeysManager::new(&seed_2, 43, 44, &cross_node_seed);
1314+
chanmon_cfgs[1].keys_manager.backing = make_dyn_keys_interface(&seed_1);
1315+
chanmon_cfgs[2].keys_manager.backing = make_dyn_keys_interface(&seed_2);
13091316
let node_cfgs = create_node_cfgs(3, &chanmon_cfgs);
13101317
let node_chanmgrs = create_node_chanmgrs(3, &node_cfgs, &[None, None, None]);
13111318
let nodes = create_network(3, &node_cfgs, &node_chanmgrs);
@@ -1407,9 +1414,8 @@ mod test {
14071414
let mut chanmon_cfgs = create_chanmon_cfgs(3);
14081415
let seed_1 = [42u8; 32];
14091416
let seed_2 = [43u8; 32];
1410-
let cross_node_seed = [44u8; 32];
1411-
chanmon_cfgs[1].keys_manager.backing = PhantomKeysManager::new(&seed_1, 43, 44, &cross_node_seed);
1412-
chanmon_cfgs[2].keys_manager.backing = PhantomKeysManager::new(&seed_2, 43, 44, &cross_node_seed);
1417+
chanmon_cfgs[1].keys_manager.backing = make_dyn_keys_interface(&seed_1);
1418+
chanmon_cfgs[2].keys_manager.backing = make_dyn_keys_interface(&seed_2);
14131419
let node_cfgs = create_node_cfgs(3, &chanmon_cfgs);
14141420
let node_chanmgrs = create_node_chanmgrs(3, &node_cfgs, &[None, None, None]);
14151421
let nodes = create_network(3, &node_cfgs, &node_chanmgrs);
@@ -1501,9 +1507,8 @@ mod test {
15011507
let mut chanmon_cfgs = create_chanmon_cfgs(3);
15021508
let seed_1 = [42u8; 32];
15031509
let seed_2 = [43u8; 32];
1504-
let cross_node_seed = [44u8; 32];
1505-
chanmon_cfgs[1].keys_manager.backing = PhantomKeysManager::new(&seed_1, 43, 44, &cross_node_seed);
1506-
chanmon_cfgs[2].keys_manager.backing = PhantomKeysManager::new(&seed_2, 43, 44, &cross_node_seed);
1510+
chanmon_cfgs[1].keys_manager.backing = make_dyn_keys_interface(&seed_1);
1511+
chanmon_cfgs[2].keys_manager.backing = make_dyn_keys_interface(&seed_2);
15071512
let node_cfgs = create_node_cfgs(3, &chanmon_cfgs);
15081513
let node_chanmgrs = create_node_chanmgrs(3, &node_cfgs, &[None, None, None]);
15091514
let nodes = create_network(3, &node_cfgs, &node_chanmgrs);
@@ -1530,9 +1535,8 @@ mod test {
15301535
let mut chanmon_cfgs = create_chanmon_cfgs(4);
15311536
let seed_1 = [42u8; 32];
15321537
let seed_2 = [43u8; 32];
1533-
let cross_node_seed = [44u8; 32];
1534-
chanmon_cfgs[2].keys_manager.backing = PhantomKeysManager::new(&seed_1, 43, 44, &cross_node_seed);
1535-
chanmon_cfgs[3].keys_manager.backing = PhantomKeysManager::new(&seed_2, 43, 44, &cross_node_seed);
1538+
chanmon_cfgs[2].keys_manager.backing = make_dyn_keys_interface(&seed_1);
1539+
chanmon_cfgs[3].keys_manager.backing = make_dyn_keys_interface(&seed_2);
15361540
let node_cfgs = create_node_cfgs(4, &chanmon_cfgs);
15371541
let node_chanmgrs = create_node_chanmgrs(4, &node_cfgs, &[None, None, None, None]);
15381542
let nodes = create_network(4, &node_cfgs, &node_chanmgrs);
@@ -1561,9 +1565,8 @@ mod test {
15611565
let mut chanmon_cfgs = create_chanmon_cfgs(4);
15621566
let seed_1 = [42u8; 32];
15631567
let seed_2 = [43u8; 32];
1564-
let cross_node_seed = [44u8; 32];
1565-
chanmon_cfgs[2].keys_manager.backing = PhantomKeysManager::new(&seed_1, 43, 44, &cross_node_seed);
1566-
chanmon_cfgs[3].keys_manager.backing = PhantomKeysManager::new(&seed_2, 43, 44, &cross_node_seed);
1568+
chanmon_cfgs[2].keys_manager.backing = make_dyn_keys_interface(&seed_1);
1569+
chanmon_cfgs[3].keys_manager.backing = make_dyn_keys_interface(&seed_2);
15671570
let node_cfgs = create_node_cfgs(4, &chanmon_cfgs);
15681571
let node_chanmgrs = create_node_chanmgrs(4, &node_cfgs, &[None, None, None, None]);
15691572
let nodes = create_network(4, &node_cfgs, &node_chanmgrs);
@@ -1619,9 +1622,8 @@ mod test {
16191622
let mut chanmon_cfgs = create_chanmon_cfgs(3);
16201623
let seed_1 = [42u8; 32];
16211624
let seed_2 = [43u8; 32];
1622-
let cross_node_seed = [44u8; 32];
1623-
chanmon_cfgs[1].keys_manager.backing = PhantomKeysManager::new(&seed_1, 43, 44, &cross_node_seed);
1624-
chanmon_cfgs[2].keys_manager.backing = PhantomKeysManager::new(&seed_2, 43, 44, &cross_node_seed);
1625+
chanmon_cfgs[1].keys_manager.backing = make_dyn_keys_interface(&seed_1);
1626+
chanmon_cfgs[2].keys_manager.backing = make_dyn_keys_interface(&seed_2);
16251627
let node_cfgs = create_node_cfgs(3, &chanmon_cfgs);
16261628
let node_chanmgrs = create_node_chanmgrs(3, &node_cfgs, &[None, None, None]);
16271629
let nodes = create_network(3, &node_cfgs, &node_chanmgrs);
@@ -1652,9 +1654,8 @@ mod test {
16521654
let mut chanmon_cfgs = create_chanmon_cfgs(4);
16531655
let seed_1 = [42u8; 32];
16541656
let seed_2 = [43u8; 32];
1655-
let cross_node_seed = [44u8; 32];
1656-
chanmon_cfgs[1].keys_manager.backing = PhantomKeysManager::new(&seed_1, 43, 44, &cross_node_seed);
1657-
chanmon_cfgs[2].keys_manager.backing = PhantomKeysManager::new(&seed_2, 43, 44, &cross_node_seed);
1657+
chanmon_cfgs[1].keys_manager.backing = make_dyn_keys_interface(&seed_1);
1658+
chanmon_cfgs[2].keys_manager.backing = make_dyn_keys_interface(&seed_2);
16581659
let node_cfgs = create_node_cfgs(4, &chanmon_cfgs);
16591660
let node_chanmgrs = create_node_chanmgrs(4, &node_cfgs, &[None, None, None, None]);
16601661
let nodes = create_network(4, &node_cfgs, &node_chanmgrs);
@@ -1686,9 +1687,8 @@ mod test {
16861687
let mut chanmon_cfgs = create_chanmon_cfgs(3);
16871688
let seed_1 = [42u8; 32];
16881689
let seed_2 = [43u8; 32];
1689-
let cross_node_seed = [44u8; 32];
1690-
chanmon_cfgs[1].keys_manager.backing = PhantomKeysManager::new(&seed_1, 43, 44, &cross_node_seed);
1691-
chanmon_cfgs[2].keys_manager.backing = PhantomKeysManager::new(&seed_2, 43, 44, &cross_node_seed);
1690+
chanmon_cfgs[1].keys_manager.backing = make_dyn_keys_interface(&seed_1);
1691+
chanmon_cfgs[2].keys_manager.backing = make_dyn_keys_interface(&seed_2);
16921692
let node_cfgs = create_node_cfgs(3, &chanmon_cfgs);
16931693
let node_chanmgrs = create_node_chanmgrs(3, &node_cfgs, &[None, None, None]);
16941694
let nodes = create_network(3, &node_cfgs, &node_chanmgrs);
@@ -1717,9 +1717,8 @@ mod test {
17171717
let mut chanmon_cfgs = create_chanmon_cfgs(4);
17181718
let seed_1 = [42u8; 32];
17191719
let seed_2 = [43u8; 32];
1720-
let cross_node_seed = [44u8; 32];
1721-
chanmon_cfgs[1].keys_manager.backing = PhantomKeysManager::new(&seed_1, 43, 44, &cross_node_seed);
1722-
chanmon_cfgs[2].keys_manager.backing = PhantomKeysManager::new(&seed_2, 43, 44, &cross_node_seed);
1720+
chanmon_cfgs[1].keys_manager.backing = make_dyn_keys_interface(&seed_1);
1721+
chanmon_cfgs[2].keys_manager.backing = make_dyn_keys_interface(&seed_2);
17231722
let node_cfgs = create_node_cfgs(4, &chanmon_cfgs);
17241723
let node_chanmgrs = create_node_chanmgrs(4, &node_cfgs, &[None, None, None, None]);
17251724
let nodes = create_network(4, &node_cfgs, &node_chanmgrs);
@@ -1792,11 +1791,10 @@ mod test {
17921791
let seed_2 = [43 as u8; 32];
17931792
let seed_3 = [44 as u8; 32];
17941793
let seed_4 = [45 as u8; 32];
1795-
let cross_node_seed = [44 as u8; 32];
1796-
chanmon_cfgs[2].keys_manager.backing = PhantomKeysManager::new(&seed_1, 43, 44, &cross_node_seed);
1797-
chanmon_cfgs[3].keys_manager.backing = PhantomKeysManager::new(&seed_2, 43, 44, &cross_node_seed);
1798-
chanmon_cfgs[4].keys_manager.backing = PhantomKeysManager::new(&seed_3, 43, 44, &cross_node_seed);
1799-
chanmon_cfgs[5].keys_manager.backing = PhantomKeysManager::new(&seed_4, 43, 44, &cross_node_seed);
1794+
chanmon_cfgs[2].keys_manager.backing = make_dyn_keys_interface(&seed_1);
1795+
chanmon_cfgs[3].keys_manager.backing = make_dyn_keys_interface(&seed_2);
1796+
chanmon_cfgs[4].keys_manager.backing = make_dyn_keys_interface(&seed_3);
1797+
chanmon_cfgs[4].keys_manager.backing = make_dyn_keys_interface(&seed_4);
18001798
let node_cfgs = create_node_cfgs(6, &chanmon_cfgs);
18011799
let node_chanmgrs = create_node_chanmgrs(6, &node_cfgs, &[None, None, None, None, None, None]);
18021800
let nodes = create_network(6, &node_cfgs, &node_chanmgrs);
@@ -1849,9 +1847,8 @@ mod test {
18491847
let mut chanmon_cfgs = create_chanmon_cfgs(5);
18501848
let seed_1 = [42 as u8; 32];
18511849
let seed_2 = [43 as u8; 32];
1852-
let cross_node_seed = [44 as u8; 32];
1853-
chanmon_cfgs[1].keys_manager.backing = PhantomKeysManager::new(&seed_1, 43, 44, &cross_node_seed);
1854-
chanmon_cfgs[2].keys_manager.backing = PhantomKeysManager::new(&seed_2, 43, 44, &cross_node_seed);
1850+
chanmon_cfgs[1].keys_manager.backing = make_dyn_keys_interface(&seed_1);
1851+
chanmon_cfgs[2].keys_manager.backing = make_dyn_keys_interface(&seed_2);
18551852
let node_cfgs = create_node_cfgs(5, &chanmon_cfgs);
18561853
let node_chanmgrs = create_node_chanmgrs(5, &node_cfgs, &[None, None, None, None, None]);
18571854
let nodes = create_network(5, &node_cfgs, &node_chanmgrs);

lightning/src/chain/channelmonitor.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4868,7 +4868,7 @@ mod tests {
48684868
nodes[1].chain_monitor.chain_monitor.transactions_confirmed(&new_header,
48694869
&[(0, broadcast_tx)], conf_height);
48704870

4871-
let (_, pre_update_monitor) = <(BlockHash, ChannelMonitor<InMemorySigner>)>::read(
4871+
let (_, pre_update_monitor) = <(BlockHash, ChannelMonitor<_>)>::read(
48724872
&mut io::Cursor::new(&get_monitor!(nodes[1], channel.2).encode()),
48734873
(&nodes[1].keys_manager.backing, &nodes[1].keys_manager.backing)).unwrap();
48744874

lightning/src/sign/mod.rs

Lines changed: 62 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -32,9 +32,7 @@ use bitcoin::hashes::{Hash, HashEngine};
3232
use bitcoin::secp256k1::ecdh::SharedSecret;
3333
use bitcoin::secp256k1::ecdsa::{RecoverableSignature, Signature};
3434
use bitcoin::secp256k1::schnorr;
35-
#[cfg(taproot)]
36-
use bitcoin::secp256k1::All;
37-
use bitcoin::secp256k1::{KeyPair, PublicKey, Scalar, Secp256k1, SecretKey, Signing};
35+
use bitcoin::secp256k1::{KeyPair, PublicKey, Scalar, Secp256k1, SecretKey, Signing, All};
3836
use bitcoin::{secp256k1, Sequence, Txid, Witness};
3937

4038
use crate::chain::transaction::OutPoint;
@@ -727,6 +725,32 @@ impl HTLCDescriptor {
727725
/// A trait to handle Lightning channel key material without concretizing the channel type or
728726
/// the signature mechanism.
729727
pub trait ChannelSigner {
728+
/// Returns the commitment seed for the channel.
729+
fn commitment_seed(&self) -> [u8; 32];
730+
/// Returns the counterparty's pubkeys.
731+
///
732+
/// Will return `None` if [`ChannelSigner::provide_channel_parameters`] has not been called.
733+
/// In general, this is safe to `unwrap` only in [`ChannelSigner`] implementation.
734+
fn counterparty_pubkeys(&self) -> Option<&ChannelPublicKeys>;
735+
/// Funding outpoint
736+
///
737+
/// Will return `None` if [`ChannelSigner::provide_channel_parameters`] has not been called.
738+
/// In general, this is safe to `unwrap` only in [`ChannelSigner`] implementation.
739+
fn funding_outpoint(&self) -> Option<&OutPoint>;
740+
/// Returns a [`ChannelTransactionParameters`] for this channel, to be used when verifying or
741+
/// building transactions.
742+
///
743+
/// Will return `None` if [`ChannelSigner::provide_channel_parameters`] has not been called.
744+
/// In general, this is safe to `unwrap` only in [`ChannelSigner`] implementation.
745+
fn get_channel_parameters(&self) -> Option<&ChannelTransactionParameters>;
746+
747+
/// Returns the channel type features of the channel parameters. Should be helpful for
748+
/// determining a channel's category, i. e. legacy/anchors/taproot/etc.
749+
///
750+
/// Will return `None` if [`ChannelSigner::provide_channel_parameters`] has not been called.
751+
/// In general, this is safe to `unwrap` only in [`ChannelSigner`] implementation.
752+
fn channel_type_features(&self) -> Option<&ChannelTypeFeatures>;
753+
730754
/// Gets the per-commitment point for a specific commitment number
731755
///
732756
/// Note that the commitment number starts at `(1 << 48) - 1` and counts backwards.
@@ -914,10 +938,10 @@ pub trait OutputSpender {
914938
/// Returns `Err(())` if the output value is greater than the input value minus required fee,
915939
/// if a descriptor was duplicated, or if an output descriptor `script_pubkey`
916940
/// does not match the one we can spend.
917-
fn spend_spendable_outputs<C: Signing>(
941+
fn spend_spendable_outputs(
918942
&self, descriptors: &[&SpendableOutputDescriptor], outputs: Vec<TxOut>,
919943
change_destination_script: ScriptBuf, feerate_sat_per_1000_weight: u32,
920-
locktime: Option<LockTime>, secp_ctx: &Secp256k1<C>,
944+
locktime: Option<LockTime>, secp_ctx: &Secp256k1<All>,
921945
) -> Result<Transaction, ()>;
922946
}
923947

@@ -1120,16 +1144,6 @@ impl InMemorySigner {
11201144
}
11211145
}
11221146

1123-
/// Returns the counterparty's pubkeys.
1124-
///
1125-
/// Will return `None` if [`ChannelSigner::provide_channel_parameters`] has not been called.
1126-
/// In general, this is safe to `unwrap` only in [`ChannelSigner`] implementation.
1127-
pub fn counterparty_pubkeys(&self) -> Option<&ChannelPublicKeys> {
1128-
self.get_channel_parameters().and_then(|params| {
1129-
params.counterparty_parameters.as_ref().map(|params| &params.pubkeys)
1130-
})
1131-
}
1132-
11331147
/// Returns the `contest_delay` value specified by our counterparty and applied on holder-broadcastable
11341148
/// transactions, i.e., the amount of time that we have to wait to recover our funds if we
11351149
/// broadcast a transaction.
@@ -1160,14 +1174,6 @@ impl InMemorySigner {
11601174
self.get_channel_parameters().map(|params| params.is_outbound_from_holder)
11611175
}
11621176

1163-
/// Funding outpoint
1164-
///
1165-
/// Will return `None` if [`ChannelSigner::provide_channel_parameters`] has not been called.
1166-
/// In general, this is safe to `unwrap` only in [`ChannelSigner`] implementation.
1167-
pub fn funding_outpoint(&self) -> Option<&OutPoint> {
1168-
self.get_channel_parameters().map(|params| params.funding_outpoint.as_ref()).flatten()
1169-
}
1170-
11711177
/// Returns a [`ChannelTransactionParameters`] for this channel, to be used when verifying or
11721178
/// building transactions.
11731179
///
@@ -1177,15 +1183,6 @@ impl InMemorySigner {
11771183
self.channel_parameters.as_ref()
11781184
}
11791185

1180-
/// Returns the channel type features of the channel parameters. Should be helpful for
1181-
/// determining a channel's category, i. e. legacy/anchors/taproot/etc.
1182-
///
1183-
/// Will return `None` if [`ChannelSigner::provide_channel_parameters`] has not been called.
1184-
/// In general, this is safe to `unwrap` only in [`ChannelSigner`] implementation.
1185-
pub fn channel_type_features(&self) -> Option<&ChannelTypeFeatures> {
1186-
self.get_channel_parameters().map(|params| &params.channel_type_features)
1187-
}
1188-
11891186
/// Sign the single input of `spend_tx` at index `input_idx`, which spends the output described
11901187
/// by `descriptor`, returning the witness stack for the input.
11911188
///
@@ -1338,6 +1335,35 @@ impl EntropySource for InMemorySigner {
13381335
}
13391336

13401337
impl ChannelSigner for InMemorySigner {
1338+
fn commitment_seed(&self) -> [u8; 32] {
1339+
self.commitment_seed
1340+
}
1341+
1342+
fn counterparty_pubkeys(&self) -> Option<&ChannelPublicKeys> {
1343+
self.get_channel_parameters().and_then(|params| {
1344+
params.counterparty_parameters.as_ref().map(|params| &params.pubkeys)
1345+
})
1346+
}
1347+
1348+
fn funding_outpoint(&self) -> Option<&OutPoint> {
1349+
self.get_channel_parameters().map(|params| params.funding_outpoint.as_ref()).flatten()
1350+
}
1351+
1352+
fn get_channel_parameters(&self) -> Option<&ChannelTransactionParameters> {
1353+
self.channel_parameters.as_ref()
1354+
}
1355+
1356+
1357+
/// Returns the channel type features of the channel parameters. Should be helpful for
1358+
/// determining a channel's category, i. e. legacy/anchors/taproot/etc.
1359+
///
1360+
/// Will return `None` if [`ChannelSigner::provide_channel_parameters`] has not been called.
1361+
/// In general, this is safe to `unwrap` only in [`ChannelSigner`] implementation.
1362+
fn channel_type_features(&self) -> Option<&ChannelTypeFeatures> {
1363+
self.get_channel_parameters().map(|params| &params.channel_type_features)
1364+
}
1365+
1366+
13411367
fn get_per_commitment_point(
13421368
&self, idx: u64, secp_ctx: &Secp256k1<secp256k1::All>,
13431369
) -> PublicKey {
@@ -2199,10 +2225,10 @@ impl OutputSpender for KeysManager {
21992225
///
22002226
/// May panic if the [`SpendableOutputDescriptor`]s were not generated by channels which used
22012227
/// this [`KeysManager`] or one of the [`InMemorySigner`] created by this [`KeysManager`].
2202-
fn spend_spendable_outputs<C: Signing>(
2228+
fn spend_spendable_outputs(
22032229
&self, descriptors: &[&SpendableOutputDescriptor], outputs: Vec<TxOut>,
22042230
change_destination_script: ScriptBuf, feerate_sat_per_1000_weight: u32,
2205-
locktime: Option<LockTime>, secp_ctx: &Secp256k1<C>,
2231+
locktime: Option<LockTime>, secp_ctx: &Secp256k1<All>,
22062232
) -> Result<Transaction, ()> {
22072233
let (mut psbt, expected_max_weight) =
22082234
SpendableOutputDescriptor::create_spendable_outputs_psbt(
@@ -2363,10 +2389,10 @@ impl NodeSigner for PhantomKeysManager {
23632389
impl OutputSpender for PhantomKeysManager {
23642390
/// See [`OutputSpender::spend_spendable_outputs`] and [`KeysManager::spend_spendable_outputs`]
23652391
/// for documentation on this method.
2366-
fn spend_spendable_outputs<C: Signing>(
2392+
fn spend_spendable_outputs(
23672393
&self, descriptors: &[&SpendableOutputDescriptor], outputs: Vec<TxOut>,
23682394
change_destination_script: ScriptBuf, feerate_sat_per_1000_weight: u32,
2369-
locktime: Option<LockTime>, secp_ctx: &Secp256k1<C>,
2395+
locktime: Option<LockTime>, secp_ctx: &Secp256k1<All>,
23702396
) -> Result<Transaction, ()> {
23712397
self.inner.spend_spendable_outputs(
23722398
descriptors,

0 commit comments

Comments
 (0)