@@ -30,7 +30,6 @@ mod fwd_batch;
30
30
31
31
use fwd_batch:: BatchDelay ;
32
32
33
- use crate :: lightning:: util:: ser:: Writeable ;
34
33
use lightning:: chain;
35
34
use lightning:: chain:: chaininterface:: { BroadcasterInterface , FeeEstimator } ;
36
35
use lightning:: chain:: chainmonitor:: { ChainMonitor , Persist } ;
@@ -40,6 +39,7 @@ use lightning::events::EventHandler;
40
39
use lightning:: events:: EventsProvider ;
41
40
use lightning:: events:: ReplayEvent ;
42
41
use lightning:: events:: { Event , PathFailure } ;
42
+ use lightning:: util:: ser:: Writeable ;
43
43
44
44
use lightning:: ln:: channelmanager:: AChannelManager ;
45
45
use lightning:: ln:: msgs:: OnionMessageHandler ;
@@ -55,11 +55,11 @@ use lightning::sign::EntropySource;
55
55
use lightning:: sign:: OutputSpender ;
56
56
use lightning:: util:: logger:: Logger ;
57
57
use lightning:: util:: persist:: {
58
- KVStoreSync , CHANNEL_MANAGER_PERSISTENCE_KEY , CHANNEL_MANAGER_PERSISTENCE_PRIMARY_NAMESPACE ,
59
- CHANNEL_MANAGER_PERSISTENCE_SECONDARY_NAMESPACE , NETWORK_GRAPH_PERSISTENCE_KEY ,
60
- NETWORK_GRAPH_PERSISTENCE_PRIMARY_NAMESPACE , NETWORK_GRAPH_PERSISTENCE_SECONDARY_NAMESPACE ,
61
- SCORER_PERSISTENCE_KEY , SCORER_PERSISTENCE_PRIMARY_NAMESPACE ,
62
- SCORER_PERSISTENCE_SECONDARY_NAMESPACE ,
58
+ KVStore , KVStoreSync , KVStoreSyncWrapper , CHANNEL_MANAGER_PERSISTENCE_KEY ,
59
+ CHANNEL_MANAGER_PERSISTENCE_PRIMARY_NAMESPACE , CHANNEL_MANAGER_PERSISTENCE_SECONDARY_NAMESPACE ,
60
+ NETWORK_GRAPH_PERSISTENCE_KEY , NETWORK_GRAPH_PERSISTENCE_PRIMARY_NAMESPACE ,
61
+ NETWORK_GRAPH_PERSISTENCE_SECONDARY_NAMESPACE , SCORER_PERSISTENCE_KEY ,
62
+ SCORER_PERSISTENCE_PRIMARY_NAMESPACE , SCORER_PERSISTENCE_SECONDARY_NAMESPACE ,
63
63
} ;
64
64
use lightning:: util:: sweep:: OutputSweeper ;
65
65
#[ cfg( feature = "std" ) ]
@@ -331,6 +331,15 @@ fn update_scorer<'a, S: 'static + Deref<Target = SC> + Send + Sync, SC: 'a + Wri
331
331
true
332
332
}
333
333
334
+ macro_rules! maybe_await {
335
+ ( true , $e: expr) => {
336
+ $e. await
337
+ } ;
338
+ ( false , $e: expr) => {
339
+ $e
340
+ } ;
341
+ }
342
+
334
343
macro_rules! define_run_body {
335
344
(
336
345
$kv_store: ident,
@@ -340,7 +349,7 @@ macro_rules! define_run_body {
340
349
$peer_manager: ident, $gossip_sync: ident,
341
350
$process_sweeper: expr,
342
351
$logger: ident, $scorer: ident, $loop_exit_check: expr, $await: expr, $get_timer: expr,
343
- $timer_elapsed: expr, $check_slow_await: expr, $time_fetch: expr, $batch_delay: expr,
352
+ $timer_elapsed: expr, $check_slow_await: expr, $time_fetch: expr, $batch_delay: expr, $async_persist : tt ,
344
353
) => { {
345
354
log_trace!( $logger, "Calling ChannelManager's timer_tick_occurred on startup" ) ;
346
355
$channel_manager. get_cm( ) . timer_tick_occurred( ) ;
@@ -412,12 +421,12 @@ macro_rules! define_run_body {
412
421
413
422
if $channel_manager. get_cm( ) . get_and_clear_needs_persistence( ) {
414
423
log_trace!( $logger, "Persisting ChannelManager..." ) ;
415
- $kv_store. write(
424
+ maybe_await! ( $async_persist , $kv_store. write(
416
425
CHANNEL_MANAGER_PERSISTENCE_PRIMARY_NAMESPACE ,
417
426
CHANNEL_MANAGER_PERSISTENCE_SECONDARY_NAMESPACE ,
418
427
CHANNEL_MANAGER_PERSISTENCE_KEY ,
419
428
& $channel_manager. get_cm( ) . encode( ) ,
420
- ) ?;
429
+ ) ) ?;
421
430
log_trace!( $logger, "Done persisting ChannelManager." ) ;
422
431
}
423
432
if $timer_elapsed( & mut last_freshness_call, FRESHNESS_TIMER ) {
@@ -478,12 +487,12 @@ macro_rules! define_run_body {
478
487
log_trace!( $logger, "Persisting network graph." ) ;
479
488
}
480
489
481
- if let Err ( e) = $kv_store. write(
490
+ if let Err ( e) = maybe_await! ( $async_persist , $kv_store. write(
482
491
NETWORK_GRAPH_PERSISTENCE_PRIMARY_NAMESPACE ,
483
492
NETWORK_GRAPH_PERSISTENCE_SECONDARY_NAMESPACE ,
484
493
NETWORK_GRAPH_PERSISTENCE_KEY ,
485
494
& network_graph. encode( ) ,
486
- ) {
495
+ ) ) {
487
496
log_error!( $logger, "Error: Failed to persist network graph, check your disk and permissions {}" , e)
488
497
}
489
498
@@ -511,12 +520,12 @@ macro_rules! define_run_body {
511
520
} else {
512
521
log_trace!( $logger, "Persisting scorer" ) ;
513
522
}
514
- if let Err ( e) = $kv_store. write(
523
+ if let Err ( e) = maybe_await! ( $async_persist , $kv_store. write(
515
524
SCORER_PERSISTENCE_PRIMARY_NAMESPACE ,
516
525
SCORER_PERSISTENCE_SECONDARY_NAMESPACE ,
517
526
SCORER_PERSISTENCE_KEY ,
518
527
& scorer. encode( ) ,
519
- ) {
528
+ ) ) {
520
529
log_error!( $logger, "Error: Failed to persist scorer, check your disk and permissions {}" , e)
521
530
}
522
531
}
@@ -539,31 +548,31 @@ macro_rules! define_run_body {
539
548
// After we exit, ensure we persist the ChannelManager one final time - this avoids
540
549
// some races where users quit while channel updates were in-flight, with
541
550
// ChannelMonitor update(s) persisted without a corresponding ChannelManager update.
542
- $kv_store. write(
551
+ maybe_await! ( $async_persist , $kv_store. write(
543
552
CHANNEL_MANAGER_PERSISTENCE_PRIMARY_NAMESPACE ,
544
553
CHANNEL_MANAGER_PERSISTENCE_SECONDARY_NAMESPACE ,
545
554
CHANNEL_MANAGER_PERSISTENCE_KEY ,
546
555
& $channel_manager. get_cm( ) . encode( ) ,
547
- ) ?;
556
+ ) ) ?;
548
557
549
558
// Persist Scorer on exit
550
559
if let Some ( ref scorer) = $scorer {
551
- $kv_store. write(
560
+ maybe_await! ( $async_persist , $kv_store. write(
552
561
SCORER_PERSISTENCE_PRIMARY_NAMESPACE ,
553
562
SCORER_PERSISTENCE_SECONDARY_NAMESPACE ,
554
563
SCORER_PERSISTENCE_KEY ,
555
564
& scorer. encode( ) ,
556
- ) ?;
565
+ ) ) ?;
557
566
}
558
567
559
568
// Persist NetworkGraph on exit
560
569
if let Some ( network_graph) = $gossip_sync. network_graph( ) {
561
- $kv_store. write(
570
+ maybe_await! ( $async_persist , $kv_store. write(
562
571
NETWORK_GRAPH_PERSISTENCE_PRIMARY_NAMESPACE ,
563
572
NETWORK_GRAPH_PERSISTENCE_SECONDARY_NAMESPACE ,
564
573
NETWORK_GRAPH_PERSISTENCE_KEY ,
565
574
& network_graph. encode( ) ,
566
- ) ?;
575
+ ) ) ?;
567
576
}
568
577
569
578
Ok ( ( ) )
@@ -720,11 +729,12 @@ use futures_util::{dummy_waker, OptionalSelector, Selector, SelectorOutput};
720
729
/// ```
721
730
/// # use lightning::io;
722
731
/// # use lightning::events::ReplayEvent;
723
- /// # use lightning::util::sweep::OutputSweeper;
724
732
/// # use std::sync::{Arc, RwLock};
725
733
/// # use std::sync::atomic::{AtomicBool, Ordering};
726
734
/// # use std::time::SystemTime;
727
735
/// # use lightning_background_processor::{process_events_async, GossipSync};
736
+ /// # use core::future::Future;
737
+ /// # use core::pin::Pin;
728
738
/// # struct Logger {}
729
739
/// # impl lightning::util::logger::Logger for Logger {
730
740
/// # fn log(&self, _record: lightning::util::logger::Record) {}
@@ -736,6 +746,13 @@ use futures_util::{dummy_waker, OptionalSelector, Selector, SelectorOutput};
736
746
/// # fn remove(&self, primary_namespace: &str, secondary_namespace: &str, key: &str, lazy: bool) -> io::Result<()> { Ok(()) }
737
747
/// # fn list(&self, primary_namespace: &str, secondary_namespace: &str) -> io::Result<Vec<String>> { Ok(Vec::new()) }
738
748
/// # }
749
+ /// # struct Store {}
750
+ /// # impl lightning::util::persist::KVStore for Store {
751
+ /// # fn read(&self, primary_namespace: &str, secondary_namespace: &str, key: &str) -> Pin<Box<dyn Future<Output = Result<Vec<u8>, io::Error>> + 'static + Send>> { todo!() }
752
+ /// # fn write(&self, primary_namespace: &str, secondary_namespace: &str, key: &str, buf: &[u8]) -> Pin<Box<dyn Future<Output = Result<(), io::Error>> + 'static + Send>> { todo!() }
753
+ /// # fn remove(&self, primary_namespace: &str, secondary_namespace: &str, key: &str, lazy: bool) -> Pin<Box<dyn Future<Output = Result<(), io::Error>> + 'static + Send>> { todo!() }
754
+ /// # fn list(&self, primary_namespace: &str, secondary_namespace: &str) -> Pin<Box<dyn Future<Output = Result<Vec<String>, io::Error>> + 'static + Send>> { todo!() }
755
+ /// # }
739
756
/// # struct EventHandler {}
740
757
/// # impl EventHandler {
741
758
/// # async fn handle_event(&self, _: lightning::events::Event) -> Result<(), ReplayEvent> { Ok(()) }
@@ -754,7 +771,8 @@ use futures_util::{dummy_waker, OptionalSelector, Selector, SelectorOutput};
754
771
/// # type LiquidityManager<B, F, FE> = lightning_liquidity::LiquidityManager<Arc<lightning::sign::KeysManager>, Arc<ChannelManager<B, F, FE>>, Arc<F>>;
755
772
/// # type Scorer = RwLock<lightning::routing::scoring::ProbabilisticScorer<Arc<NetworkGraph>, Arc<Logger>>>;
756
773
/// # type PeerManager<B, F, FE, UL> = lightning::ln::peer_handler::SimpleArcPeerManager<SocketDescriptor, ChainMonitor<B, F, FE>, B, FE, Arc<UL>, Logger, F, StoreSync>;
757
- /// #
774
+ /// # type OutputSweeper<B, D, FE, F, O> = lightning::util::sweep::OutputSweeper<Arc<B>, Arc<D>, Arc<FE>, Arc<F>, Arc<Store>, Arc<Logger>, Arc<O>>;
775
+ ///
758
776
/// # struct Node<
759
777
/// # B: lightning::chain::chaininterface::BroadcasterInterface + Send + Sync + 'static,
760
778
/// # F: lightning::chain::Filter + Send + Sync + 'static,
@@ -770,10 +788,10 @@ use futures_util::{dummy_waker, OptionalSelector, Selector, SelectorOutput};
770
788
/// # liquidity_manager: Arc<LiquidityManager<B, F, FE>>,
771
789
/// # chain_monitor: Arc<ChainMonitor<B, F, FE>>,
772
790
/// # gossip_sync: Arc<P2PGossipSync<UL>>,
773
- /// # persister: Arc<StoreSync >,
791
+ /// # persister: Arc<Store >,
774
792
/// # logger: Arc<Logger>,
775
793
/// # scorer: Arc<Scorer>,
776
- /// # sweeper: Arc<OutputSweeper<Arc<B>, Arc<D>, Arc<FE>, Arc<F>, Arc<StoreSync>, Arc<Logger>, Arc<O> >>,
794
+ /// # sweeper: Arc<OutputSweeper<B, D, FE, F, O >>,
777
795
/// # }
778
796
/// #
779
797
/// # async fn setup_background_processing<
@@ -895,7 +913,7 @@ where
895
913
LM :: Target : ALiquidityManager ,
896
914
O :: Target : ' static + OutputSpender ,
897
915
D :: Target : ' static + ChangeDestinationSource ,
898
- K :: Target : ' static + KVStoreSync ,
916
+ K :: Target : ' static + KVStore ,
899
917
{
900
918
let mut should_break = false ;
901
919
let async_event_handler = |event| {
@@ -914,12 +932,15 @@ where
914
932
if let Some ( duration_since_epoch) = fetch_time ( ) {
915
933
if update_scorer ( scorer, & event, duration_since_epoch) {
916
934
log_trace ! ( logger, "Persisting scorer after update" ) ;
917
- if let Err ( e) = kv_store. write (
918
- SCORER_PERSISTENCE_PRIMARY_NAMESPACE ,
919
- SCORER_PERSISTENCE_SECONDARY_NAMESPACE ,
920
- SCORER_PERSISTENCE_KEY ,
921
- & scorer. encode ( ) ,
922
- ) {
935
+ if let Err ( e) = kv_store
936
+ . write (
937
+ SCORER_PERSISTENCE_PRIMARY_NAMESPACE ,
938
+ SCORER_PERSISTENCE_SECONDARY_NAMESPACE ,
939
+ SCORER_PERSISTENCE_KEY ,
940
+ & scorer. encode ( ) ,
941
+ )
942
+ . await
943
+ {
923
944
log_error ! ( logger, "Error: Failed to persist scorer, check your disk and permissions {}" , e) ;
924
945
// We opt not to abort early on persistence failure here as persisting
925
946
// the scorer is non-critical and we still hope that it will have
@@ -1007,7 +1028,82 @@ where
1007
1028
mobile_interruptable_platform,
1008
1029
fetch_time,
1009
1030
batch_delay,
1031
+ true ,
1032
+ )
1033
+ }
1034
+
1035
+ /// Async events processor that is based on [`process_events_async`] but allows for [`KVStoreSync`] to be used for
1036
+ /// synchronous background persistence.
1037
+ pub async fn process_events_async_with_kv_store_sync <
1038
+ UL : ' static + Deref ,
1039
+ CF : ' static + Deref ,
1040
+ T : ' static + Deref ,
1041
+ F : ' static + Deref ,
1042
+ G : ' static + Deref < Target = NetworkGraph < L > > ,
1043
+ L : ' static + Deref + Send + Sync ,
1044
+ P : ' static + Deref ,
1045
+ EventHandlerFuture : core:: future:: Future < Output = Result < ( ) , ReplayEvent > > ,
1046
+ EventHandler : Fn ( Event ) -> EventHandlerFuture ,
1047
+ ES : ' static + Deref + Send ,
1048
+ M : ' static
1049
+ + Deref < Target = ChainMonitor < <CM :: Target as AChannelManager >:: Signer , CF , T , F , L , P , ES > >
1050
+ + Send
1051
+ + Sync ,
1052
+ CM : ' static + Deref + Send + Sync ,
1053
+ OM : ' static + Deref ,
1054
+ PGS : ' static + Deref < Target = P2PGossipSync < G , UL , L > > ,
1055
+ RGS : ' static + Deref < Target = RapidGossipSync < G , L > > ,
1056
+ PM : ' static + Deref ,
1057
+ LM : ' static + Deref ,
1058
+ D : ' static + Deref ,
1059
+ O : ' static + Deref ,
1060
+ K : ' static + Deref ,
1061
+ OS : ' static + Deref < Target = OutputSweeper < T , D , F , CF , KVStoreSyncWrapper < K > , L , O > > ,
1062
+ S : ' static + Deref < Target = SC > + Send + Sync ,
1063
+ SC : for < ' b > WriteableScore < ' b > ,
1064
+ SleepFuture : core:: future:: Future < Output = bool > + core:: marker:: Unpin ,
1065
+ Sleeper : Fn ( Duration ) -> SleepFuture ,
1066
+ FetchTime : Fn ( ) -> Option < Duration > ,
1067
+ > (
1068
+ kv_store : K , event_handler : EventHandler , chain_monitor : M , channel_manager : CM ,
1069
+ onion_messenger : Option < OM > , gossip_sync : GossipSync < PGS , RGS , G , UL , L > , peer_manager : PM ,
1070
+ liquidity_manager : Option < LM > , sweeper : Option < OS > , logger : L , scorer : Option < S > ,
1071
+ sleeper : Sleeper , mobile_interruptable_platform : bool , fetch_time : FetchTime ,
1072
+ ) -> Result < ( ) , lightning:: io:: Error >
1073
+ where
1074
+ UL :: Target : ' static + UtxoLookup ,
1075
+ CF :: Target : ' static + chain:: Filter ,
1076
+ T :: Target : ' static + BroadcasterInterface ,
1077
+ F :: Target : ' static + FeeEstimator ,
1078
+ L :: Target : ' static + Logger ,
1079
+ P :: Target : ' static + Persist < <CM :: Target as AChannelManager >:: Signer > ,
1080
+ ES :: Target : ' static + EntropySource ,
1081
+ CM :: Target : AChannelManager ,
1082
+ OM :: Target : AOnionMessenger ,
1083
+ PM :: Target : APeerManager ,
1084
+ LM :: Target : ALiquidityManager ,
1085
+ O :: Target : ' static + OutputSpender ,
1086
+ D :: Target : ' static + ChangeDestinationSource ,
1087
+ K :: Target : ' static + KVStoreSync ,
1088
+ {
1089
+ let kv_store = KVStoreSyncWrapper ( kv_store) ;
1090
+ process_events_async (
1091
+ kv_store,
1092
+ event_handler,
1093
+ chain_monitor,
1094
+ channel_manager,
1095
+ onion_messenger,
1096
+ gossip_sync,
1097
+ peer_manager,
1098
+ liquidity_manager,
1099
+ sweeper,
1100
+ logger,
1101
+ scorer,
1102
+ sleeper,
1103
+ mobile_interruptable_platform,
1104
+ fetch_time,
1010
1105
)
1106
+ . await
1011
1107
}
1012
1108
1013
1109
#[ cfg( feature = "std" ) ]
@@ -1195,6 +1291,7 @@ impl BackgroundProcessor {
1195
1291
)
1196
1292
} ,
1197
1293
batch_delay,
1294
+ false ,
1198
1295
)
1199
1296
} ) ;
1200
1297
Self { stop_thread : stop_thread_clone, thread_handle : Some ( handle) }
@@ -1283,7 +1380,7 @@ mod tests {
1283
1380
use lightning:: types:: payment:: PaymentHash ;
1284
1381
use lightning:: util:: config:: UserConfig ;
1285
1382
use lightning:: util:: persist:: {
1286
- KVStoreSync , CHANNEL_MANAGER_PERSISTENCE_KEY ,
1383
+ KVStoreSync , KVStoreSyncWrapper , CHANNEL_MANAGER_PERSISTENCE_KEY ,
1287
1384
CHANNEL_MANAGER_PERSISTENCE_PRIMARY_NAMESPACE ,
1288
1385
CHANNEL_MANAGER_PERSISTENCE_SECONDARY_NAMESPACE , NETWORK_GRAPH_PERSISTENCE_KEY ,
1289
1386
NETWORK_GRAPH_PERSISTENCE_PRIMARY_NAMESPACE , NETWORK_GRAPH_PERSISTENCE_SECONDARY_NAMESPACE ,
@@ -2209,12 +2306,13 @@ mod tests {
2209
2306
open_channel ! ( nodes[ 0 ] , nodes[ 1 ] , 100000 ) ;
2210
2307
2211
2308
let data_dir = nodes[ 0 ] . kv_store . get_data_dir ( ) ;
2212
- let persister = Arc :: new (
2309
+ let kv_store_sync = Arc :: new (
2213
2310
Persister :: new ( data_dir) . with_manager_error ( std:: io:: ErrorKind :: Other , "test" ) ,
2214
2311
) ;
2312
+ let kv_store = Arc :: new ( KVStoreSyncWrapper ( kv_store_sync) ) ;
2215
2313
2216
2314
let bp_future = super :: process_events_async (
2217
- persister ,
2315
+ kv_store ,
2218
2316
|_: _ | async { Ok ( ( ) ) } ,
2219
2317
Arc :: clone ( & nodes[ 0 ] . chain_monitor ) ,
2220
2318
Arc :: clone ( & nodes[ 0 ] . node ) ,
@@ -2717,11 +2815,13 @@ mod tests {
2717
2815
let ( _, nodes) =
2718
2816
create_nodes ( 2 , "test_not_pruning_network_graph_until_graph_sync_completion_async" ) ;
2719
2817
let data_dir = nodes[ 0 ] . kv_store . get_data_dir ( ) ;
2720
- let persister = Arc :: new ( Persister :: new ( data_dir) . with_graph_persistence_notifier ( sender) ) ;
2818
+ let kv_store_sync =
2819
+ Arc :: new ( Persister :: new ( data_dir) . with_graph_persistence_notifier ( sender) ) ;
2820
+ let kv_store = Arc :: new ( KVStoreSyncWrapper ( kv_store_sync) ) ;
2721
2821
2722
2822
let ( exit_sender, exit_receiver) = tokio:: sync:: watch:: channel ( ( ) ) ;
2723
2823
let bp_future = super :: process_events_async (
2724
- persister ,
2824
+ kv_store ,
2725
2825
|_: _ | async { Ok ( ( ) ) } ,
2726
2826
Arc :: clone ( & nodes[ 0 ] . chain_monitor ) ,
2727
2827
Arc :: clone ( & nodes[ 0 ] . node ) ,
@@ -2930,12 +3030,13 @@ mod tests {
2930
3030
2931
3031
let ( _, nodes) = create_nodes ( 1 , "test_payment_path_scoring_async" ) ;
2932
3032
let data_dir = nodes[ 0 ] . kv_store . get_data_dir ( ) ;
2933
- let persister = Arc :: new ( Persister :: new ( data_dir) ) ;
3033
+ let kv_store_sync = Arc :: new ( Persister :: new ( data_dir) ) ;
3034
+ let kv_store = Arc :: new ( KVStoreSyncWrapper ( kv_store_sync) ) ;
2934
3035
2935
3036
let ( exit_sender, exit_receiver) = tokio:: sync:: watch:: channel ( ( ) ) ;
2936
3037
2937
3038
let bp_future = super :: process_events_async (
2938
- persister ,
3039
+ kv_store ,
2939
3040
event_handler,
2940
3041
Arc :: clone ( & nodes[ 0 ] . chain_monitor ) ,
2941
3042
Arc :: clone ( & nodes[ 0 ] . node ) ,
0 commit comments