1 // This file is Copyright its original authors, visible in version control
2 // history and in the source files from which this was generated.
4 // This file is licensed under the license available in the LICENSE or LICENSE.md
5 // file in the root of this repository or, if no such file exists, the same
6 // license as that which applies to the original source files from which this
7 // source was automatically generated.
9 //! Utilities to send payments and manage outbound payment information.
11 use alloc::str::FromStr;
12 use core::ffi::c_void;
13 use core::convert::Infallible;
14 use bitcoin::hashes::Hash;
15 use crate::c_types::*;
16 #[cfg(feature="no-std")]
17 use alloc::{vec::Vec, boxed::Box};
19 /// Strategies available to retry payment path failures.
24 /// Max number of attempts to retry payment.
26 /// Each attempt may be multiple HTLCs along multiple paths if the router decides to split up a
27 /// retry, and may retry multiple failed HTLCs at once if they failed around the same time and
28 /// were retried along a route from a single call to [`Router::find_route`].
31 /// Time elapsed before abandoning retries for a payment. At least one attempt at payment is made;
32 /// see [`PaymentParameters::expiry_time`] to avoid any attempt at payment after a specific time.
34 /// [`PaymentParameters::expiry_time`]: crate::routing::router::PaymentParameters::expiry_time
38 use lightning::ln::outbound_payment::Retry as RetryImport;
39 pub(crate) type nativeRetry = RetryImport;
43 pub(crate) fn to_native(&self) -> nativeRetry {
45 Retry::Attempts (ref a, ) => {
46 let mut a_nonref = Clone::clone(a);
47 nativeRetry::Attempts (
51 Retry::Timeout (ref a, ) => {
52 let mut a_nonref = Clone::clone(a);
53 nativeRetry::Timeout (
54 core::time::Duration::from_secs(a_nonref),
60 pub(crate) fn into_native(self) -> nativeRetry {
62 Retry::Attempts (mut a, ) => {
63 nativeRetry::Attempts (
67 Retry::Timeout (mut a, ) => {
68 nativeRetry::Timeout (
69 core::time::Duration::from_secs(a),
75 pub(crate) fn from_native(native: &nativeRetry) -> Self {
77 nativeRetry::Attempts (ref a, ) => {
78 let mut a_nonref = Clone::clone(a);
83 nativeRetry::Timeout (ref a, ) => {
84 let mut a_nonref = Clone::clone(a);
92 pub(crate) fn native_into(native: nativeRetry) -> Self {
94 nativeRetry::Attempts (mut a, ) => {
99 nativeRetry::Timeout (mut a, ) => {
107 /// Frees any resources used by the Retry
109 pub extern "C" fn Retry_free(this_ptr: Retry) { }
110 /// Creates a copy of the Retry
112 pub extern "C" fn Retry_clone(orig: &Retry) -> Retry {
116 /// Utility method to constructs a new Attempts-variant Retry
117 pub extern "C" fn Retry_attempts(a: usize) -> Retry {
121 /// Utility method to constructs a new Timeout-variant Retry
122 pub extern "C" fn Retry_timeout(a: u64) -> Retry {
125 /// Checks if two Retrys contain equal inner contents.
126 /// This ignores pointers and is_owned flags and looks at the values in fields.
128 pub extern "C" fn Retry_eq(a: &Retry, b: &Retry) -> bool {
129 if &a.to_native() == &b.to_native() { true } else { false }
131 /// Checks if two Retrys contain equal inner contents.
133 pub extern "C" fn Retry_hash(o: &Retry) -> u64 {
134 // Note that we'd love to use alloc::collections::hash_map::DefaultHasher but it's not in core
136 let mut hasher = core::hash::SipHasher::new();
137 core::hash::Hash::hash(&o.to_native(), &mut hasher);
138 core::hash::Hasher::finish(&hasher)
140 /// Indicates an immediate error on [`ChannelManager::send_payment_with_retry`]. Further errors
141 /// may be surfaced later via [`Event::PaymentPathFailed`] and [`Event::PaymentFailed`].
143 /// [`ChannelManager::send_payment_with_retry`]: crate::ln::channelmanager::ChannelManager::send_payment_with_retry
144 /// [`Event::PaymentPathFailed`]: crate::util::events::Event::PaymentPathFailed
145 /// [`Event::PaymentFailed`]: crate::util::events::Event::PaymentFailed
149 pub enum RetryableSendFailure {
150 /// The provided [`PaymentParameters::expiry_time`] indicated that the payment has expired. Note
151 /// that this error is *not* caused by [`Retry::Timeout`].
153 /// [`PaymentParameters::expiry_time`]: crate::routing::router::PaymentParameters::expiry_time
155 /// We were unable to find a route to the destination.
157 /// Indicates that a payment for the provided [`PaymentId`] is already in-flight and has not
158 /// yet completed (i.e. generated an [`Event::PaymentSent`] or [`Event::PaymentFailed`]).
160 /// [`PaymentId`]: crate::ln::channelmanager::PaymentId
161 /// [`Event::PaymentSent`]: crate::util::events::Event::PaymentSent
162 /// [`Event::PaymentFailed`]: crate::util::events::Event::PaymentFailed
165 use lightning::ln::outbound_payment::RetryableSendFailure as RetryableSendFailureImport;
166 pub(crate) type nativeRetryableSendFailure = RetryableSendFailureImport;
168 impl RetryableSendFailure {
170 pub(crate) fn to_native(&self) -> nativeRetryableSendFailure {
172 RetryableSendFailure::PaymentExpired => nativeRetryableSendFailure::PaymentExpired,
173 RetryableSendFailure::RouteNotFound => nativeRetryableSendFailure::RouteNotFound,
174 RetryableSendFailure::DuplicatePayment => nativeRetryableSendFailure::DuplicatePayment,
178 pub(crate) fn into_native(self) -> nativeRetryableSendFailure {
180 RetryableSendFailure::PaymentExpired => nativeRetryableSendFailure::PaymentExpired,
181 RetryableSendFailure::RouteNotFound => nativeRetryableSendFailure::RouteNotFound,
182 RetryableSendFailure::DuplicatePayment => nativeRetryableSendFailure::DuplicatePayment,
186 pub(crate) fn from_native(native: &nativeRetryableSendFailure) -> Self {
188 nativeRetryableSendFailure::PaymentExpired => RetryableSendFailure::PaymentExpired,
189 nativeRetryableSendFailure::RouteNotFound => RetryableSendFailure::RouteNotFound,
190 nativeRetryableSendFailure::DuplicatePayment => RetryableSendFailure::DuplicatePayment,
194 pub(crate) fn native_into(native: nativeRetryableSendFailure) -> Self {
196 nativeRetryableSendFailure::PaymentExpired => RetryableSendFailure::PaymentExpired,
197 nativeRetryableSendFailure::RouteNotFound => RetryableSendFailure::RouteNotFound,
198 nativeRetryableSendFailure::DuplicatePayment => RetryableSendFailure::DuplicatePayment,
202 /// Creates a copy of the RetryableSendFailure
204 pub extern "C" fn RetryableSendFailure_clone(orig: &RetryableSendFailure) -> RetryableSendFailure {
208 /// Utility method to constructs a new PaymentExpired-variant RetryableSendFailure
209 pub extern "C" fn RetryableSendFailure_payment_expired() -> RetryableSendFailure {
210 RetryableSendFailure::PaymentExpired}
212 /// Utility method to constructs a new RouteNotFound-variant RetryableSendFailure
213 pub extern "C" fn RetryableSendFailure_route_not_found() -> RetryableSendFailure {
214 RetryableSendFailure::RouteNotFound}
216 /// Utility method to constructs a new DuplicatePayment-variant RetryableSendFailure
217 pub extern "C" fn RetryableSendFailure_duplicate_payment() -> RetryableSendFailure {
218 RetryableSendFailure::DuplicatePayment}
219 /// If a payment fails to send with [`ChannelManager::send_payment`], it can be in one of several
220 /// states. This enum is returned as the Err() type describing which state the payment is in, see
221 /// the description of individual enum states for more.
223 /// [`ChannelManager::send_payment`]: crate::ln::channelmanager::ChannelManager::send_payment
227 pub enum PaymentSendFailure {
228 /// A parameter which was passed to send_payment was invalid, preventing us from attempting to
229 /// send the payment at all.
231 /// You can freely resend the payment in full (with the parameter error fixed).
233 /// Because the payment failed outright, no payment tracking is done and no
234 /// [`Event::PaymentPathFailed`] or [`Event::PaymentFailed`] events will be generated.
236 /// [`Event::PaymentPathFailed`]: crate::util::events::Event::PaymentPathFailed
237 /// [`Event::PaymentFailed`]: crate::util::events::Event::PaymentFailed
239 crate::lightning::util::errors::APIError),
240 /// A parameter in a single path which was passed to send_payment was invalid, preventing us
241 /// from attempting to send the payment at all.
243 /// You can freely resend the payment in full (with the parameter error fixed).
245 /// Because the payment failed outright, no payment tracking is done and no
246 /// [`Event::PaymentPathFailed`] or [`Event::PaymentFailed`] events will be generated.
248 /// The results here are ordered the same as the paths in the route object which was passed to
251 /// [`Event::PaymentPathFailed`]: crate::util::events::Event::PaymentPathFailed
252 /// [`Event::PaymentFailed`]: crate::util::events::Event::PaymentFailed
254 crate::c_types::derived::CVec_CResult_NoneAPIErrorZZ),
255 /// All paths which were attempted failed to send, with no channel state change taking place.
256 /// You can freely resend the payment in full (though you probably want to do so over different
257 /// paths than the ones selected).
259 /// Because the payment failed outright, no payment tracking is done and no
260 /// [`Event::PaymentPathFailed`] or [`Event::PaymentFailed`] events will be generated.
262 /// [`Event::PaymentPathFailed`]: crate::util::events::Event::PaymentPathFailed
263 /// [`Event::PaymentFailed`]: crate::util::events::Event::PaymentFailed
265 crate::c_types::derived::CVec_APIErrorZ),
266 /// Indicates that a payment for the provided [`PaymentId`] is already in-flight and has not
267 /// yet completed (i.e. generated an [`Event::PaymentSent`] or [`Event::PaymentFailed`]).
269 /// [`PaymentId`]: crate::ln::channelmanager::PaymentId
270 /// [`Event::PaymentSent`]: crate::util::events::Event::PaymentSent
271 /// [`Event::PaymentFailed`]: crate::util::events::Event::PaymentFailed
273 /// Some paths that were attempted failed to send, though some paths may have succeeded. At least
274 /// some paths have irrevocably committed to the HTLC.
276 /// The results here are ordered the same as the paths in the route object that was passed to
279 /// Any entries that contain `Err(APIError::MonitorUpdateInprogress)` will send once a
280 /// [`MonitorEvent::Completed`] is provided for the next-hop channel with the latest update_id.
282 /// [`MonitorEvent::Completed`]: crate::chain::channelmonitor::MonitorEvent::Completed
284 /// The errors themselves, in the same order as the paths from the route.
285 results: crate::c_types::derived::CVec_CResult_NoneAPIErrorZZ,
286 /// If some paths failed without irrevocably committing to the new HTLC(s), this will
287 /// contain a [`RouteParameters`] object for the failing paths.
289 /// Note that this (or a relevant inner pointer) may be NULL or all-0s to represent None
290 failed_paths_retry: crate::lightning::routing::router::RouteParameters,
291 /// The payment id for the payment, which is now at least partially pending.
292 payment_id: crate::c_types::ThirtyTwoBytes,
295 use lightning::ln::outbound_payment::PaymentSendFailure as PaymentSendFailureImport;
296 pub(crate) type nativePaymentSendFailure = PaymentSendFailureImport;
298 impl PaymentSendFailure {
300 pub(crate) fn to_native(&self) -> nativePaymentSendFailure {
302 PaymentSendFailure::ParameterError (ref a, ) => {
303 let mut a_nonref = Clone::clone(a);
304 nativePaymentSendFailure::ParameterError (
305 a_nonref.into_native(),
308 PaymentSendFailure::PathParameterError (ref a, ) => {
309 let mut a_nonref = Clone::clone(a);
310 let mut local_a_nonref = Vec::new(); for mut item in a_nonref.into_rust().drain(..) { local_a_nonref.push( { let mut local_a_nonref_0 = match item.result_ok { true => Ok( { () /*(*unsafe { Box::from_raw(<*mut _>::take_ptr(&mut item.contents.result)) })*/ }), false => Err( { (*unsafe { Box::from_raw(<*mut _>::take_ptr(&mut item.contents.err)) }).into_native() })}; local_a_nonref_0 }); };
311 nativePaymentSendFailure::PathParameterError (
315 PaymentSendFailure::AllFailedResendSafe (ref a, ) => {
316 let mut a_nonref = Clone::clone(a);
317 let mut local_a_nonref = Vec::new(); for mut item in a_nonref.into_rust().drain(..) { local_a_nonref.push( { item.into_native() }); };
318 nativePaymentSendFailure::AllFailedResendSafe (
322 PaymentSendFailure::DuplicatePayment => nativePaymentSendFailure::DuplicatePayment,
323 PaymentSendFailure::PartialFailure {ref results, ref failed_paths_retry, ref payment_id, } => {
324 let mut results_nonref = Clone::clone(results);
325 let mut local_results_nonref = Vec::new(); for mut item in results_nonref.into_rust().drain(..) { local_results_nonref.push( { let mut local_results_nonref_0 = match item.result_ok { true => Ok( { () /*(*unsafe { Box::from_raw(<*mut _>::take_ptr(&mut item.contents.result)) })*/ }), false => Err( { (*unsafe { Box::from_raw(<*mut _>::take_ptr(&mut item.contents.err)) }).into_native() })}; local_results_nonref_0 }); };
326 let mut failed_paths_retry_nonref = Clone::clone(failed_paths_retry);
327 let mut local_failed_paths_retry_nonref = if failed_paths_retry_nonref.inner.is_null() { None } else { Some( { *unsafe { Box::from_raw(failed_paths_retry_nonref.take_inner()) } }) };
328 let mut payment_id_nonref = Clone::clone(payment_id);
329 nativePaymentSendFailure::PartialFailure {
330 results: local_results_nonref,
331 failed_paths_retry: local_failed_paths_retry_nonref,
332 payment_id: ::lightning::ln::channelmanager::PaymentId(payment_id_nonref.data),
338 pub(crate) fn into_native(self) -> nativePaymentSendFailure {
340 PaymentSendFailure::ParameterError (mut a, ) => {
341 nativePaymentSendFailure::ParameterError (
345 PaymentSendFailure::PathParameterError (mut a, ) => {
346 let mut local_a = Vec::new(); for mut item in a.into_rust().drain(..) { local_a.push( { let mut local_a_0 = match item.result_ok { true => Ok( { () /*(*unsafe { Box::from_raw(<*mut _>::take_ptr(&mut item.contents.result)) })*/ }), false => Err( { (*unsafe { Box::from_raw(<*mut _>::take_ptr(&mut item.contents.err)) }).into_native() })}; local_a_0 }); };
347 nativePaymentSendFailure::PathParameterError (
351 PaymentSendFailure::AllFailedResendSafe (mut a, ) => {
352 let mut local_a = Vec::new(); for mut item in a.into_rust().drain(..) { local_a.push( { item.into_native() }); };
353 nativePaymentSendFailure::AllFailedResendSafe (
357 PaymentSendFailure::DuplicatePayment => nativePaymentSendFailure::DuplicatePayment,
358 PaymentSendFailure::PartialFailure {mut results, mut failed_paths_retry, mut payment_id, } => {
359 let mut local_results = Vec::new(); for mut item in results.into_rust().drain(..) { local_results.push( { let mut local_results_0 = match item.result_ok { true => Ok( { () /*(*unsafe { Box::from_raw(<*mut _>::take_ptr(&mut item.contents.result)) })*/ }), false => Err( { (*unsafe { Box::from_raw(<*mut _>::take_ptr(&mut item.contents.err)) }).into_native() })}; local_results_0 }); };
360 let mut local_failed_paths_retry = if failed_paths_retry.inner.is_null() { None } else { Some( { *unsafe { Box::from_raw(failed_paths_retry.take_inner()) } }) };
361 nativePaymentSendFailure::PartialFailure {
362 results: local_results,
363 failed_paths_retry: local_failed_paths_retry,
364 payment_id: ::lightning::ln::channelmanager::PaymentId(payment_id.data),
370 pub(crate) fn from_native(native: &nativePaymentSendFailure) -> Self {
372 nativePaymentSendFailure::ParameterError (ref a, ) => {
373 let mut a_nonref = Clone::clone(a);
374 PaymentSendFailure::ParameterError (
375 crate::lightning::util::errors::APIError::native_into(a_nonref),
378 nativePaymentSendFailure::PathParameterError (ref a, ) => {
379 let mut a_nonref = Clone::clone(a);
380 let mut local_a_nonref = Vec::new(); for mut item in a_nonref.drain(..) { local_a_nonref.push( { let mut local_a_nonref_0 = match item { Ok(mut o) => crate::c_types::CResultTempl::ok( { () /*o*/ }).into(), Err(mut e) => crate::c_types::CResultTempl::err( { crate::lightning::util::errors::APIError::native_into(e) }).into() }; local_a_nonref_0 }); };
381 PaymentSendFailure::PathParameterError (
382 local_a_nonref.into(),
385 nativePaymentSendFailure::AllFailedResendSafe (ref a, ) => {
386 let mut a_nonref = Clone::clone(a);
387 let mut local_a_nonref = Vec::new(); for mut item in a_nonref.drain(..) { local_a_nonref.push( { crate::lightning::util::errors::APIError::native_into(item) }); };
388 PaymentSendFailure::AllFailedResendSafe (
389 local_a_nonref.into(),
392 nativePaymentSendFailure::DuplicatePayment => PaymentSendFailure::DuplicatePayment,
393 nativePaymentSendFailure::PartialFailure {ref results, ref failed_paths_retry, ref payment_id, } => {
394 let mut results_nonref = Clone::clone(results);
395 let mut local_results_nonref = Vec::new(); for mut item in results_nonref.drain(..) { local_results_nonref.push( { let mut local_results_nonref_0 = match item { Ok(mut o) => crate::c_types::CResultTempl::ok( { () /*o*/ }).into(), Err(mut e) => crate::c_types::CResultTempl::err( { crate::lightning::util::errors::APIError::native_into(e) }).into() }; local_results_nonref_0 }); };
396 let mut failed_paths_retry_nonref = Clone::clone(failed_paths_retry);
397 let mut local_failed_paths_retry_nonref = crate::lightning::routing::router::RouteParameters { inner: if failed_paths_retry_nonref.is_none() { core::ptr::null_mut() } else { { ObjOps::heap_alloc((failed_paths_retry_nonref.unwrap())) } }, is_owned: true };
398 let mut payment_id_nonref = Clone::clone(payment_id);
399 PaymentSendFailure::PartialFailure {
400 results: local_results_nonref.into(),
401 failed_paths_retry: local_failed_paths_retry_nonref,
402 payment_id: crate::c_types::ThirtyTwoBytes { data: payment_id_nonref.0 },
408 pub(crate) fn native_into(native: nativePaymentSendFailure) -> Self {
410 nativePaymentSendFailure::ParameterError (mut a, ) => {
411 PaymentSendFailure::ParameterError (
412 crate::lightning::util::errors::APIError::native_into(a),
415 nativePaymentSendFailure::PathParameterError (mut a, ) => {
416 let mut local_a = Vec::new(); for mut item in a.drain(..) { local_a.push( { let mut local_a_0 = match item { Ok(mut o) => crate::c_types::CResultTempl::ok( { () /*o*/ }).into(), Err(mut e) => crate::c_types::CResultTempl::err( { crate::lightning::util::errors::APIError::native_into(e) }).into() }; local_a_0 }); };
417 PaymentSendFailure::PathParameterError (
421 nativePaymentSendFailure::AllFailedResendSafe (mut a, ) => {
422 let mut local_a = Vec::new(); for mut item in a.drain(..) { local_a.push( { crate::lightning::util::errors::APIError::native_into(item) }); };
423 PaymentSendFailure::AllFailedResendSafe (
427 nativePaymentSendFailure::DuplicatePayment => PaymentSendFailure::DuplicatePayment,
428 nativePaymentSendFailure::PartialFailure {mut results, mut failed_paths_retry, mut payment_id, } => {
429 let mut local_results = Vec::new(); for mut item in results.drain(..) { local_results.push( { let mut local_results_0 = match item { Ok(mut o) => crate::c_types::CResultTempl::ok( { () /*o*/ }).into(), Err(mut e) => crate::c_types::CResultTempl::err( { crate::lightning::util::errors::APIError::native_into(e) }).into() }; local_results_0 }); };
430 let mut local_failed_paths_retry = crate::lightning::routing::router::RouteParameters { inner: if failed_paths_retry.is_none() { core::ptr::null_mut() } else { { ObjOps::heap_alloc((failed_paths_retry.unwrap())) } }, is_owned: true };
431 PaymentSendFailure::PartialFailure {
432 results: local_results.into(),
433 failed_paths_retry: local_failed_paths_retry,
434 payment_id: crate::c_types::ThirtyTwoBytes { data: payment_id.0 },
440 /// Frees any resources used by the PaymentSendFailure
442 pub extern "C" fn PaymentSendFailure_free(this_ptr: PaymentSendFailure) { }
443 /// Creates a copy of the PaymentSendFailure
445 pub extern "C" fn PaymentSendFailure_clone(orig: &PaymentSendFailure) -> PaymentSendFailure {
449 /// Utility method to constructs a new ParameterError-variant PaymentSendFailure
450 pub extern "C" fn PaymentSendFailure_parameter_error(a: crate::lightning::util::errors::APIError) -> PaymentSendFailure {
451 PaymentSendFailure::ParameterError(a, )
454 /// Utility method to constructs a new PathParameterError-variant PaymentSendFailure
455 pub extern "C" fn PaymentSendFailure_path_parameter_error(a: crate::c_types::derived::CVec_CResult_NoneAPIErrorZZ) -> PaymentSendFailure {
456 PaymentSendFailure::PathParameterError(a, )
459 /// Utility method to constructs a new AllFailedResendSafe-variant PaymentSendFailure
460 pub extern "C" fn PaymentSendFailure_all_failed_resend_safe(a: crate::c_types::derived::CVec_APIErrorZ) -> PaymentSendFailure {
461 PaymentSendFailure::AllFailedResendSafe(a, )
464 /// Utility method to constructs a new DuplicatePayment-variant PaymentSendFailure
465 pub extern "C" fn PaymentSendFailure_duplicate_payment() -> PaymentSendFailure {
466 PaymentSendFailure::DuplicatePayment}
468 /// Utility method to constructs a new PartialFailure-variant PaymentSendFailure
469 pub extern "C" fn PaymentSendFailure_partial_failure(results: crate::c_types::derived::CVec_CResult_NoneAPIErrorZZ, failed_paths_retry: crate::lightning::routing::router::RouteParameters, payment_id: crate::c_types::ThirtyTwoBytes) -> PaymentSendFailure {
470 PaymentSendFailure::PartialFailure {