Skip to content

Commit 30c3fba

Browse files
committed
Update to new upstream rust-lightning with impl Futures
In `rust-lightning` we dropped the `Pin<Box<dyn ...>>` in favor of `impl Future`s on most traits to make the traits native-async-ish. Here we update to implement that change here. However, because we avoid generics in ldk-node through concrete dyn indirections, and having implict associated types on `rust-lightning` traits makes them not-object-safe, we have to do a bit of indirection. Instead, we define a `DynStoreTrait` which re-concretizes the `rust-lightning` storage traits, allowing us to use them `dyn`.
1 parent 9f091bf commit 30c3fba

File tree

16 files changed

+308
-166
lines changed

16 files changed

+308
-166
lines changed

Cargo.toml

Lines changed: 12 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -39,17 +39,17 @@ default = []
3939
#lightning-liquidity = { version = "0.2.0", features = ["std"] }
4040
#lightning-macros = { version = "0.2.0" }
4141

42-
lightning = { git = "https://github.com/lightningdevkit/rust-lightning", rev = "bb5504ec62d4b7e9d5626d8b1a6de60d71e8d370", features = ["std"] }
43-
lightning-types = { git = "https://github.com/lightningdevkit/rust-lightning", rev = "bb5504ec62d4b7e9d5626d8b1a6de60d71e8d370" }
44-
lightning-invoice = { git = "https://github.com/lightningdevkit/rust-lightning", rev = "bb5504ec62d4b7e9d5626d8b1a6de60d71e8d370", features = ["std"] }
45-
lightning-net-tokio = { git = "https://github.com/lightningdevkit/rust-lightning", rev = "bb5504ec62d4b7e9d5626d8b1a6de60d71e8d370" }
46-
lightning-persister = { git = "https://github.com/lightningdevkit/rust-lightning", rev = "bb5504ec62d4b7e9d5626d8b1a6de60d71e8d370", features = ["tokio"] }
47-
lightning-background-processor = { git = "https://github.com/lightningdevkit/rust-lightning", rev = "bb5504ec62d4b7e9d5626d8b1a6de60d71e8d370" }
48-
lightning-rapid-gossip-sync = { git = "https://github.com/lightningdevkit/rust-lightning", rev = "bb5504ec62d4b7e9d5626d8b1a6de60d71e8d370" }
49-
lightning-block-sync = { git = "https://github.com/lightningdevkit/rust-lightning", rev = "bb5504ec62d4b7e9d5626d8b1a6de60d71e8d370", features = ["rest-client", "rpc-client", "tokio"] }
50-
lightning-transaction-sync = { git = "https://github.com/lightningdevkit/rust-lightning", rev = "bb5504ec62d4b7e9d5626d8b1a6de60d71e8d370", features = ["esplora-async-https", "time", "electrum-rustls-ring"] }
51-
lightning-liquidity = { git = "https://github.com/lightningdevkit/rust-lightning", rev = "bb5504ec62d4b7e9d5626d8b1a6de60d71e8d370", features = ["std"] }
52-
lightning-macros = { git = "https://github.com/lightningdevkit/rust-lightning", rev = "bb5504ec62d4b7e9d5626d8b1a6de60d71e8d370" }
42+
lightning = { git = "https://github.com/lightningdevkit/rust-lightning", rev = "5bf0d1e2427d759fc1ba4108ddc7e9b32e8bacfc", features = ["std"] }
43+
lightning-types = { git = "https://github.com/lightningdevkit/rust-lightning", rev = "5bf0d1e2427d759fc1ba4108ddc7e9b32e8bacfc" }
44+
lightning-invoice = { git = "https://github.com/lightningdevkit/rust-lightning", rev = "5bf0d1e2427d759fc1ba4108ddc7e9b32e8bacfc", features = ["std"] }
45+
lightning-net-tokio = { git = "https://github.com/lightningdevkit/rust-lightning", rev = "5bf0d1e2427d759fc1ba4108ddc7e9b32e8bacfc" }
46+
lightning-persister = { git = "https://github.com/lightningdevkit/rust-lightning", rev = "5bf0d1e2427d759fc1ba4108ddc7e9b32e8bacfc", features = ["tokio"] }
47+
lightning-background-processor = { git = "https://github.com/lightningdevkit/rust-lightning", rev = "5bf0d1e2427d759fc1ba4108ddc7e9b32e8bacfc" }
48+
lightning-rapid-gossip-sync = { git = "https://github.com/lightningdevkit/rust-lightning", rev = "5bf0d1e2427d759fc1ba4108ddc7e9b32e8bacfc" }
49+
lightning-block-sync = { git = "https://github.com/lightningdevkit/rust-lightning", rev = "5bf0d1e2427d759fc1ba4108ddc7e9b32e8bacfc", features = ["rest-client", "rpc-client", "tokio"] }
50+
lightning-transaction-sync = { git = "https://github.com/lightningdevkit/rust-lightning", rev = "5bf0d1e2427d759fc1ba4108ddc7e9b32e8bacfc", features = ["esplora-async-https", "time", "electrum-rustls-ring"] }
51+
lightning-liquidity = { git = "https://github.com/lightningdevkit/rust-lightning", rev = "5bf0d1e2427d759fc1ba4108ddc7e9b32e8bacfc", features = ["std"] }
52+
lightning-macros = { git = "https://github.com/lightningdevkit/rust-lightning", rev = "5bf0d1e2427d759fc1ba4108ddc7e9b32e8bacfc" }
5353

5454
bdk_chain = { version = "0.23.0", default-features = false, features = ["std"] }
5555
bdk_esplora = { version = "0.22.0", default-features = false, features = ["async-https-rustls", "tokio"]}
@@ -82,7 +82,7 @@ prost = { version = "0.11.6", default-features = false}
8282
winapi = { version = "0.3", features = ["winbase"] }
8383

8484
[dev-dependencies]
85-
lightning = { git = "https://github.com/lightningdevkit/rust-lightning", rev = "bb5504ec62d4b7e9d5626d8b1a6de60d71e8d370", features = ["std", "_test_utils"] }
85+
lightning = { git = "https://github.com/lightningdevkit/rust-lightning", rev = "5bf0d1e2427d759fc1ba4108ddc7e9b32e8bacfc", features = ["std", "_test_utils"] }
8686
proptest = "1.0.0"
8787
regex = "1.5.6"
8888
criterion = { version = "0.7.0", features = ["async_tokio"] }

src/builder.rs

Lines changed: 19 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -70,8 +70,8 @@ use crate::peer_store::PeerStore;
7070
use crate::runtime::Runtime;
7171
use crate::tx_broadcaster::TransactionBroadcaster;
7272
use crate::types::{
73-
ChainMonitor, ChannelManager, DynStore, GossipSync, Graph, KeysManager, MessageRouter,
74-
OnionMessenger, PaymentStore, PeerManager, Persister,
73+
ChainMonitor, ChannelManager, DynStore, DynStoreWrapper, GossipSync, Graph, KeysManager,
74+
MessageRouter, OnionMessenger, PaymentStore, PeerManager, Persister, SyncAndAsyncKVStore,
7575
};
7676
use crate::wallet::persist::KVStoreWalletPersister;
7777
use crate::wallet::Wallet;
@@ -544,14 +544,12 @@ impl NodeBuilder {
544544
let storage_dir_path = self.config.storage_dir_path.clone();
545545
fs::create_dir_all(storage_dir_path.clone())
546546
.map_err(|_| BuildError::StoragePathAccessFailed)?;
547-
let kv_store = Arc::new(
548-
SqliteStore::new(
549-
storage_dir_path.into(),
550-
Some(io::sqlite_store::SQLITE_DB_FILE_NAME.to_string()),
551-
Some(io::sqlite_store::KV_TABLE_NAME.to_string()),
552-
)
553-
.map_err(|_| BuildError::KVStoreSetupFailed)?,
554-
);
547+
let kv_store = SqliteStore::new(
548+
storage_dir_path.into(),
549+
Some(io::sqlite_store::SQLITE_DB_FILE_NAME.to_string()),
550+
Some(io::sqlite_store::KV_TABLE_NAME.to_string()),
551+
)
552+
.map_err(|_| BuildError::KVStoreSetupFailed)?;
555553
self.build_with_store(node_entropy, kv_store)
556554
}
557555

@@ -563,7 +561,7 @@ impl NodeBuilder {
563561

564562
fs::create_dir_all(storage_dir_path.clone())
565563
.map_err(|_| BuildError::StoragePathAccessFailed)?;
566-
let kv_store = Arc::new(FilesystemStore::new(storage_dir_path));
564+
let kv_store = FilesystemStore::new(storage_dir_path);
567565
self.build_with_store(node_entropy, kv_store)
568566
}
569567

@@ -595,7 +593,7 @@ impl NodeBuilder {
595593
BuildError::KVStoreSetupFailed
596594
})?;
597595

598-
self.build_with_store(node_entropy, Arc::new(vss_store))
596+
self.build_with_store(node_entropy, vss_store)
599597
}
600598

601599
/// Builds a [`Node`] instance with a [VSS] backend and according to the options
@@ -622,7 +620,7 @@ impl NodeBuilder {
622620
BuildError::KVStoreSetupFailed
623621
})?;
624622

625-
self.build_with_store(node_entropy, Arc::new(vss_store))
623+
self.build_with_store(node_entropy, vss_store)
626624
}
627625

628626
/// Builds a [`Node`] instance with a [VSS] backend and according to the options
@@ -647,12 +645,12 @@ impl NodeBuilder {
647645
BuildError::KVStoreSetupFailed
648646
})?;
649647

650-
self.build_with_store(node_entropy, Arc::new(vss_store))
648+
self.build_with_store(node_entropy, vss_store)
651649
}
652650

653651
/// Builds a [`Node`] instance according to the options previously configured.
654-
pub fn build_with_store(
655-
&self, node_entropy: NodeEntropy, kv_store: Arc<DynStore>,
652+
pub fn build_with_store<S: SyncAndAsyncKVStore + Send + Sync + 'static>(
653+
&self, node_entropy: NodeEntropy, kv_store: S,
656654
) -> Result<Node, BuildError> {
657655
let logger = setup_logger(&self.log_writer_config, &self.config)?;
658656

@@ -678,7 +676,7 @@ impl NodeBuilder {
678676
seed_bytes,
679677
runtime,
680678
logger,
681-
kv_store,
679+
Arc::new(DynStoreWrapper(kv_store)),
682680
)
683681
}
684682
}
@@ -1014,8 +1012,10 @@ impl ArcedNodeBuilder {
10141012
}
10151013

10161014
/// Builds a [`Node`] instance according to the options previously configured.
1017-
pub fn build_with_store(
1018-
&self, node_entropy: Arc<NodeEntropy>, kv_store: Arc<DynStore>,
1015+
// Note that the generics here don't actually work for Uniffi, but we don't currently expose
1016+
// this so its not needed.
1017+
pub fn build_with_store<S: SyncAndAsyncKVStore + Send + Sync + 'static>(
1018+
&self, node_entropy: Arc<NodeEntropy>, kv_store: S,
10191019
) -> Result<Arc<Node>, BuildError> {
10201020
self.inner.read().unwrap().build_with_store(*node_entropy, kv_store).map(Arc::new)
10211021
}

src/chain/bitcoind.rs

Lines changed: 62 additions & 45 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66
// accordance with one or both of these licenses.
77

88
use std::collections::{HashMap, VecDeque};
9+
use std::future::Future;
910
use std::sync::atomic::{AtomicU64, Ordering};
1011
use std::sync::{Arc, Mutex, RwLock};
1112
use std::time::{Duration, Instant, SystemTime, UNIX_EPOCH};
@@ -23,7 +24,7 @@ use lightning_block_sync::poll::{ChainPoller, ChainTip, ValidatedBlockHeader};
2324
use lightning_block_sync::rest::RestClient;
2425
use lightning_block_sync::rpc::{RpcClient, RpcError};
2526
use lightning_block_sync::{
26-
AsyncBlockSourceResult, BlockData, BlockHeaderData, BlockSource, BlockSourceErrorKind, Cache,
27+
BlockData, BlockHeaderData, BlockSource, BlockSourceError, BlockSourceErrorKind, Cache,
2728
SpvClient,
2829
};
2930
use serde::Serialize;
@@ -655,44 +656,58 @@ impl std::ops::Deref for UtxoSourceClient {
655656
impl BlockSource for UtxoSourceClient {
656657
fn get_header<'a>(
657658
&'a self, header_hash: &'a BlockHash, height_hint: Option<u32>,
658-
) -> AsyncBlockSourceResult<'a, BlockHeaderData> {
659-
match self {
660-
Self::Rpc(client) => client.get_header(header_hash, height_hint),
661-
Self::Rest(client) => client.get_header(header_hash, height_hint),
659+
) -> impl Future<Output = Result<BlockHeaderData, BlockSourceError>> + 'a {
660+
async move {
661+
match self {
662+
Self::Rpc(client) => client.get_header(header_hash, height_hint).await,
663+
Self::Rest(client) => client.get_header(header_hash, height_hint).await,
664+
}
662665
}
663666
}
664667

665668
fn get_block<'a>(
666669
&'a self, header_hash: &'a BlockHash,
667-
) -> AsyncBlockSourceResult<'a, BlockData> {
668-
match self {
669-
Self::Rpc(client) => client.get_block(header_hash),
670-
Self::Rest(client) => client.get_block(header_hash),
670+
) -> impl Future<Output = Result<BlockData, BlockSourceError>> + 'a {
671+
async move {
672+
match self {
673+
Self::Rpc(client) => client.get_block(header_hash).await,
674+
Self::Rest(client) => client.get_block(header_hash).await,
675+
}
671676
}
672677
}
673678

674-
fn get_best_block(&self) -> AsyncBlockSourceResult<'_, (BlockHash, Option<u32>)> {
675-
match self {
676-
Self::Rpc(client) => client.get_best_block(),
677-
Self::Rest(client) => client.get_best_block(),
679+
fn get_best_block<'a>(
680+
&'a self,
681+
) -> impl Future<Output = Result<(BlockHash, Option<u32>), BlockSourceError>> + 'a {
682+
async move {
683+
match self {
684+
Self::Rpc(client) => client.get_best_block().await,
685+
Self::Rest(client) => client.get_best_block().await,
686+
}
678687
}
679688
}
680689
}
681690

682691
impl UtxoSource for UtxoSourceClient {
683692
fn get_block_hash_by_height<'a>(
684693
&'a self, block_height: u32,
685-
) -> AsyncBlockSourceResult<'a, BlockHash> {
686-
match self {
687-
Self::Rpc(client) => client.get_block_hash_by_height(block_height),
688-
Self::Rest(client) => client.get_block_hash_by_height(block_height),
694+
) -> impl Future<Output = Result<BlockHash, BlockSourceError>> + 'a {
695+
async move {
696+
match self {
697+
Self::Rpc(client) => client.get_block_hash_by_height(block_height).await,
698+
Self::Rest(client) => client.get_block_hash_by_height(block_height).await,
699+
}
689700
}
690701
}
691702

692-
fn is_output_unspent<'a>(&'a self, outpoint: OutPoint) -> AsyncBlockSourceResult<'a, bool> {
693-
match self {
694-
Self::Rpc(client) => client.is_output_unspent(outpoint),
695-
Self::Rest(client) => client.is_output_unspent(outpoint),
703+
fn is_output_unspent<'a>(
704+
&'a self, outpoint: OutPoint,
705+
) -> impl Future<Output = Result<bool, BlockSourceError>> + 'a {
706+
async move {
707+
match self {
708+
Self::Rpc(client) => client.is_output_unspent(outpoint).await,
709+
Self::Rest(client) => client.is_output_unspent(outpoint).await,
710+
}
696711
}
697712
}
698713
}
@@ -1245,38 +1260,40 @@ impl BitcoindClient {
12451260
impl BlockSource for BitcoindClient {
12461261
fn get_header<'a>(
12471262
&'a self, header_hash: &'a bitcoin::BlockHash, height_hint: Option<u32>,
1248-
) -> AsyncBlockSourceResult<'a, BlockHeaderData> {
1249-
match self {
1250-
BitcoindClient::Rpc { rpc_client, .. } => {
1251-
Box::pin(async move { rpc_client.get_header(header_hash, height_hint).await })
1252-
},
1253-
BitcoindClient::Rest { rest_client, .. } => {
1254-
Box::pin(async move { rest_client.get_header(header_hash, height_hint).await })
1255-
},
1263+
) -> impl Future<Output = Result<BlockHeaderData, BlockSourceError>> + 'a {
1264+
async move {
1265+
match self {
1266+
BitcoindClient::Rpc { rpc_client, .. } => {
1267+
rpc_client.get_header(header_hash, height_hint).await
1268+
},
1269+
BitcoindClient::Rest { rest_client, .. } => {
1270+
rest_client.get_header(header_hash, height_hint).await
1271+
},
1272+
}
12561273
}
12571274
}
12581275

12591276
fn get_block<'a>(
12601277
&'a self, header_hash: &'a bitcoin::BlockHash,
1261-
) -> AsyncBlockSourceResult<'a, BlockData> {
1262-
match self {
1263-
BitcoindClient::Rpc { rpc_client, .. } => {
1264-
Box::pin(async move { rpc_client.get_block(header_hash).await })
1265-
},
1266-
BitcoindClient::Rest { rest_client, .. } => {
1267-
Box::pin(async move { rest_client.get_block(header_hash).await })
1268-
},
1278+
) -> impl Future<Output = Result<BlockData, BlockSourceError>> + 'a {
1279+
async move {
1280+
match self {
1281+
BitcoindClient::Rpc { rpc_client, .. } => rpc_client.get_block(header_hash).await,
1282+
BitcoindClient::Rest { rest_client, .. } => {
1283+
rest_client.get_block(header_hash).await
1284+
},
1285+
}
12691286
}
12701287
}
12711288

1272-
fn get_best_block(&self) -> AsyncBlockSourceResult<'_, (bitcoin::BlockHash, Option<u32>)> {
1273-
match self {
1274-
BitcoindClient::Rpc { rpc_client, .. } => {
1275-
Box::pin(async move { rpc_client.get_best_block().await })
1276-
},
1277-
BitcoindClient::Rest { rest_client, .. } => {
1278-
Box::pin(async move { rest_client.get_best_block().await })
1279-
},
1289+
fn get_best_block<'a>(
1290+
&'a self,
1291+
) -> impl Future<Output = Result<(bitcoin::BlockHash, Option<u32>), BlockSourceError>> + 'a {
1292+
async move {
1293+
match self {
1294+
BitcoindClient::Rpc { rpc_client, .. } => rpc_client.get_best_block().await,
1295+
BitcoindClient::Rest { rest_client, .. } => rest_client.get_best_block().await,
1296+
}
12801297
}
12811298
}
12821299
}

src/data_store.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -177,6 +177,7 @@ mod tests {
177177
use super::*;
178178
use crate::hex_utils;
179179
use crate::io::test_utils::InMemoryStore;
180+
use crate::types::DynStoreWrapper;
180181

181182
#[derive(Clone, Copy, Debug, Eq, Hash, PartialEq)]
182183
struct TestObjectId {
@@ -235,7 +236,7 @@ mod tests {
235236

236237
#[test]
237238
fn data_is_persisted() {
238-
let store: Arc<DynStore> = Arc::new(InMemoryStore::new());
239+
let store: Arc<DynStore> = Arc::new(DynStoreWrapper(InMemoryStore::new()));
239240
let logger = Arc::new(TestLogger::new());
240241
let primary_namespace = "datastore_test_primary".to_string();
241242
let secondary_namespace = "datastore_test_secondary".to_string();

src/event.rs

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1801,10 +1801,11 @@ mod tests {
18011801

18021802
use super::*;
18031803
use crate::io::test_utils::InMemoryStore;
1804+
use crate::types::DynStoreWrapper;
18041805

18051806
#[tokio::test]
18061807
async fn event_queue_persistence() {
1807-
let store: Arc<DynStore> = Arc::new(InMemoryStore::new());
1808+
let store: Arc<DynStore> = Arc::new(DynStoreWrapper(InMemoryStore::new()));
18081809
let logger = Arc::new(TestLogger::new());
18091810
let event_queue = Arc::new(EventQueue::new(Arc::clone(&store), Arc::clone(&logger)));
18101811
assert_eq!(event_queue.next_event(), None);
@@ -1842,7 +1843,7 @@ mod tests {
18421843

18431844
#[tokio::test]
18441845
async fn event_queue_concurrency() {
1845-
let store: Arc<DynStore> = Arc::new(InMemoryStore::new());
1846+
let store: Arc<DynStore> = Arc::new(DynStoreWrapper(InMemoryStore::new()));
18461847
let logger = Arc::new(TestLogger::new());
18471848
let event_queue = Arc::new(EventQueue::new(Arc::clone(&store), Arc::clone(&logger)));
18481849
assert_eq!(event_queue.next_event(), None);

0 commit comments

Comments
 (0)