X-Git-Url: http://git.bitcoin.ninja/index.cgi?a=blobdiff_plain;f=src%2Fmain%2Fjava%2Forg%2Fldk%2Fbatteries%2FChannelManagerConstructor.java;h=cca20f355349fbb18c389ba9bf85d02b9dc47421;hb=07d5d868dfe064aadb28a7f7ca6002c16be9723d;hp=db37118dfd71cb10f43dda02d21789d6facad658;hpb=b479a721c55c876e716319c5074c7d150a59aa5c;p=ldk-java diff --git a/src/main/java/org/ldk/batteries/ChannelManagerConstructor.java b/src/main/java/org/ldk/batteries/ChannelManagerConstructor.java index db37118d..cca20f35 100644 --- a/src/main/java/org/ldk/batteries/ChannelManagerConstructor.java +++ b/src/main/java/org/ldk/batteries/ChannelManagerConstructor.java @@ -78,7 +78,8 @@ public class ChannelManagerConstructor { */ private final ProbabilisticScorer prob_scorer; private final Logger logger; - private final KeysManager keys_manager; + private final EntropySource entropy_source; + private final NodeSigner node_signer; /** * Exposes the `ProbabilisticScorer` wrapped inside a lock. Don't forget to `close` this lock when you're done with @@ -102,41 +103,81 @@ public class ChannelManagerConstructor { return new ScorerWrapper(this.scorer.as_LockableScore().lock(), this.prob_scorer); } + /** + * A simple interface to provide routes to LDK. + */ + public interface RouterWrapper { + /** + * Gets a route for the given payment. + * + * @param payment_hash is non-null for this-node-originated payments, however in the future trampoline or other + * HTLC re-routing may cause it to be null as we find routes for payments which we did not + * originate. + * @param payment_id is non-null for this-node-originated payments, however in the future trampoline or other + * HTLC re-routing may cause it to be null as we find routes for payments which we did not + * originate. + * @param default_router Provides a router which uses the LDK route-finder and a ProbabilisticScorer using the + * provided ProbabilisticScoringParameters. You may use this to fetch a "default" route, + * modifying or storing it as you wish before returning the route to LDK. + */ + Result_RouteLightningErrorZ find_route(byte[] payer_node_id, RouteParameters route_params, ChannelDetails[] first_hops, + InFlightHtlcs inflight_htlcs, @Nullable byte[] payment_hash, @Nullable byte[] payment_id, DefaultRouter default_router); + } + /** * Deserializes a channel manager and a set of channel monitors from the given serialized copies and interface implementations * * @param filter If provided, the outputs which were previously registered to be monitored for will be loaded into the filter. * Note that if the provided Watch is a ChainWatch and has an associated filter, the previously registered * outputs will be loaded when chain_sync_completed is called. + * @param router_wrapper If provided, routes will be fetched by calling the given router rather than an LDK `DefaultRouter`. */ public ChannelManagerConstructor(byte[] channel_manager_serialized, byte[][] channel_monitors_serialized, UserConfig config, - KeysManager keys_manager, FeeEstimator fee_estimator, ChainMonitor chain_monitor, + EntropySource entropy_source, NodeSigner node_signer, SignerProvider signer_provider, + FeeEstimator fee_estimator, ChainMonitor chain_monitor, @Nullable Filter filter, byte[] net_graph_serialized, - ProbabilisticScoringParameters scoring_params, byte[] probabilistic_scorer_bytes, + ProbabilisticScoringDecayParameters scoring_decay_params, + ProbabilisticScoringFeeParameters scoring_fee_params, + byte[] probabilistic_scorer_bytes, @Nullable RouterWrapper router_wrapper, BroadcasterInterface tx_broadcaster, Logger logger) throws InvalidSerializedDataException { - this.keys_manager = keys_manager; - EntropySource entropy_source = keys_manager.as_EntropySource(); + this.entropy_source = entropy_source; + this.node_signer = node_signer; Result_NetworkGraphDecodeErrorZ graph_res = NetworkGraph.read(net_graph_serialized, logger); if (!graph_res.is_ok()) { throw new InvalidSerializedDataException("Serialized Network Graph was corrupt"); } this.net_graph = ((Result_NetworkGraphDecodeErrorZ.Result_NetworkGraphDecodeErrorZ_OK)graph_res).res; - assert(scoring_params != null); + assert(scoring_decay_params != null); assert(probabilistic_scorer_bytes != null); - Result_ProbabilisticScorerDecodeErrorZ scorer_res = ProbabilisticScorer.read(probabilistic_scorer_bytes, scoring_params, net_graph, logger); + Result_ProbabilisticScorerDecodeErrorZ scorer_res = ProbabilisticScorer.read(probabilistic_scorer_bytes, scoring_decay_params, net_graph, logger); if (!scorer_res.is_ok()) { throw new InvalidSerializedDataException("Serialized ProbabilisticScorer was corrupt"); } this.prob_scorer = ((Result_ProbabilisticScorerDecodeErrorZ.Result_ProbabilisticScorerDecodeErrorZ_OK)scorer_res).res; this.scorer = MultiThreadedLockableScore.of(this.prob_scorer.as_Score()); - DefaultRouter router = DefaultRouter.of(this.net_graph, logger, entropy_source.get_secure_random_bytes(), scorer.as_LockableScore()); + + assert(scoring_fee_params != null); + DefaultRouter default_router = DefaultRouter.of(this.net_graph, logger, entropy_source.get_secure_random_bytes(), scorer.as_LockableScore(), scoring_fee_params); + Router router; + if (router_wrapper != null) { + router = Router.new_impl(new Router.RouterInterface() { + @Override public Result_RouteLightningErrorZ find_route(byte[] payer, RouteParameters route_params, ChannelDetails[] first_hops, InFlightHtlcs inflight_htlcs) { + return router_wrapper.find_route(payer, route_params, first_hops, inflight_htlcs, null, null, default_router); + } + @Override public Result_RouteLightningErrorZ find_route_with_id(byte[] payer, RouteParameters route_params, ChannelDetails[] first_hops, InFlightHtlcs inflight_htlcs, byte[] payment_hash, byte[] payment_id) { + return router_wrapper.find_route(payer, route_params, first_hops, inflight_htlcs, payment_hash, payment_id, default_router); + } + }); + } else { + router = default_router.as_Router(); + } final ChannelMonitor[] monitors = new ChannelMonitor[channel_monitors_serialized.length]; this.channel_monitors = new TwoTuple_BlockHashChannelMonitorZ[monitors.length]; HashSet monitor_funding_set = new HashSet(); for (int i = 0; i < monitors.length; i++) { - Result_C2Tuple_BlockHashChannelMonitorZDecodeErrorZ res = UtilMethods.C2Tuple_BlockHashChannelMonitorZ_read(channel_monitors_serialized[i], entropy_source, keys_manager.as_SignerProvider()); + Result_C2Tuple_BlockHashChannelMonitorZDecodeErrorZ res = UtilMethods.C2Tuple_BlockHashChannelMonitorZ_read(channel_monitors_serialized[i], entropy_source, signer_provider); if (res instanceof Result_C2Tuple_BlockHashChannelMonitorZDecodeErrorZ.Result_C2Tuple_BlockHashChannelMonitorZDecodeErrorZ_Err) { throw new InvalidSerializedDataException("Serialized ChannelMonitor was corrupt"); } @@ -147,9 +188,9 @@ public class ChannelManagerConstructor { throw new InvalidSerializedDataException("Set of ChannelMonitors contained duplicates (ie the same funding_txo was set on multiple monitors)"); } Result_C2Tuple_BlockHashChannelManagerZDecodeErrorZ res = - UtilMethods.C2Tuple_BlockHashChannelManagerZ_read(channel_manager_serialized, keys_manager.as_EntropySource(), - keys_manager.as_NodeSigner(), keys_manager.as_SignerProvider(), fee_estimator, chain_monitor.as_Watch(), - tx_broadcaster, router.as_Router(), logger, config, monitors); + UtilMethods.C2Tuple_BlockHashChannelManagerZ_read(channel_manager_serialized, entropy_source, + node_signer, signer_provider, fee_estimator, chain_monitor.as_Watch(), + tx_broadcaster, router, logger, config, monitors); if (!res.is_ok()) { throw new InvalidSerializedDataException("Serialized ChannelManager was corrupt"); } @@ -166,27 +207,45 @@ public class ChannelManagerConstructor { /** * Constructs a channel manager from the given interface implementations + * + * @param router_wrapper If provided, routes will be fetched by calling the given router rather than an LDK `DefaultRouter`. */ public ChannelManagerConstructor(Network network, UserConfig config, byte[] current_blockchain_tip_hash, int current_blockchain_tip_height, - KeysManager keys_manager, FeeEstimator fee_estimator, ChainMonitor chain_monitor, - NetworkGraph net_graph, ProbabilisticScoringParameters scoring_params, + EntropySource entropy_source, NodeSigner node_signer, SignerProvider signer_provider, + FeeEstimator fee_estimator, ChainMonitor chain_monitor, + NetworkGraph net_graph, ProbabilisticScoringDecayParameters scoring_decay_params, + ProbabilisticScoringFeeParameters scoring_fee_params, + @Nullable RouterWrapper router_wrapper, BroadcasterInterface tx_broadcaster, Logger logger) { - this.keys_manager = keys_manager; - EntropySource entropy_source = keys_manager.as_EntropySource(); - + this.entropy_source = entropy_source; + this.node_signer = node_signer; this.net_graph = net_graph; - assert(scoring_params != null); - this.prob_scorer = ProbabilisticScorer.of(scoring_params, net_graph, logger); + assert(scoring_decay_params != null); + this.prob_scorer = ProbabilisticScorer.of(scoring_decay_params, net_graph, logger); this.scorer = MultiThreadedLockableScore.of(this.prob_scorer.as_Score()); - DefaultRouter router = DefaultRouter.of(this.net_graph, logger, entropy_source.get_secure_random_bytes(), scorer.as_LockableScore()); + assert(scoring_fee_params != null); + DefaultRouter default_router = DefaultRouter.of(this.net_graph, logger, entropy_source.get_secure_random_bytes(), scorer.as_LockableScore(), scoring_fee_params); + Router router; + if (router_wrapper != null) { + router = Router.new_impl(new Router.RouterInterface() { + @Override public Result_RouteLightningErrorZ find_route(byte[] payer, RouteParameters route_params, ChannelDetails[] first_hops, InFlightHtlcs inflight_htlcs) { + return router_wrapper.find_route(payer, route_params, first_hops, inflight_htlcs, null, null, default_router); + } + @Override public Result_RouteLightningErrorZ find_route_with_id(byte[] payer, RouteParameters route_params, ChannelDetails[] first_hops, InFlightHtlcs inflight_htlcs, byte[] payment_hash, byte[] payment_id) { + return router_wrapper.find_route(payer, route_params, first_hops, inflight_htlcs, payment_hash, payment_id, default_router); + } + }); + } else { + router = default_router.as_Router(); + } channel_monitors = new TwoTuple_BlockHashChannelMonitorZ[0]; channel_manager_latest_block_hash = null; this.chain_monitor = chain_monitor; BestBlock block = BestBlock.of(current_blockchain_tip_hash, current_blockchain_tip_height); ChainParameters params = ChainParameters.of(network, block); - channel_manager = ChannelManager.of(fee_estimator, chain_monitor.as_Watch(), tx_broadcaster, router.as_Router(), logger, - keys_manager.as_EntropySource(), keys_manager.as_NodeSigner(), keys_manager.as_SignerProvider(), config, params); + channel_manager = ChannelManager.of(fee_estimator, chain_monitor.as_Watch(), tx_broadcaster, router, logger, + entropy_source, node_signer, signer_provider, config, params, (int) (System.currentTimeMillis() / 1000)); this.logger = logger; } @@ -224,10 +283,15 @@ public class ChannelManagerConstructor { final IgnoringMessageHandler ignoring_handler = IgnoringMessageHandler.of(); P2PGossipSync graph_msg_handler = P2PGossipSync.of(net_graph, Option_UtxoLookupZ.none(), logger); + RoutingMessageHandler routing_msg_handler; + if (use_p2p_graph_sync) + routing_msg_handler = graph_msg_handler.as_RoutingMessageHandler(); + else + routing_msg_handler = ignoring_handler.as_RoutingMessageHandler(); this.peer_manager = PeerManager.of(channel_manager.as_ChannelMessageHandler(), - ignoring_handler.as_RoutingMessageHandler(), ignoring_handler.as_OnionMessageHandler(), - (int)(System.currentTimeMillis() / 1000), this.keys_manager.as_EntropySource().get_secure_random_bytes(), - logger, ignoring_handler.as_CustomMessageHandler(), keys_manager.as_NodeSigner()); + routing_msg_handler, ignoring_handler.as_OnionMessageHandler(), + ignoring_handler.as_CustomMessageHandler(), (int)(System.currentTimeMillis() / 1000), + this.entropy_source.get_secure_random_bytes(), logger, this.node_signer); try { this.nio_peer_handler = new NioPeerHandler(peer_manager); @@ -237,9 +301,9 @@ public class ChannelManagerConstructor { GossipSync gossip_sync; if (use_p2p_graph_sync) - gossip_sync = GossipSync.none(); - else gossip_sync = GossipSync.p2_p(graph_msg_handler); + else + gossip_sync = GossipSync.none(); Option_WriteableScoreZ writeable_score = Option_WriteableScoreZ.some(scorer.as_WriteableScore());