@@ -14,6 +14,7 @@ import (
14
14
"github.com/lightningnetwork/lnd/graph/db/models"
15
15
"github.com/lightningnetwork/lnd/htlcswitch"
16
16
"github.com/lightningnetwork/lnd/lntypes"
17
+ "github.com/lightningnetwork/lnd/lnutils"
17
18
"github.com/lightningnetwork/lnd/lnwire"
18
19
"github.com/lightningnetwork/lnd/routing/route"
19
20
"github.com/lightningnetwork/lnd/routing/shards"
@@ -500,7 +501,8 @@ func (p *paymentLifecycle) collectResultAsync(attempt *channeldb.HTLCAttempt) {
500
501
func (p * paymentLifecycle ) collectResult (
501
502
attempt * channeldb.HTLCAttempt ) (* htlcswitch.PaymentResult , error ) {
502
503
503
- log .Tracef ("Collecting result for attempt %v" , spew .Sdump (attempt ))
504
+ log .Tracef ("Collecting result for attempt %v" ,
505
+ lnutils .SpewLogClosure (attempt ))
504
506
505
507
result := & htlcswitch.PaymentResult {}
506
508
@@ -1060,6 +1062,38 @@ func marshallError(sendError error, time time.Time) *channeldb.HTLCFailInfo {
1060
1062
return response
1061
1063
}
1062
1064
1065
+ // patchLegacyPaymentHash will make a copy of the passed attempt and sets its
1066
+ // Hash field to be the payment hash if it's nil.
1067
+ //
1068
+ // NOTE: For legacy payments, which were created before the AMP feature was
1069
+ // enabled, the `Hash` field in their HTLC attempts is nil. In that case, we use
1070
+ // the payment hash as the `attempt.Hash` as they are identical.
1071
+ func (p * paymentLifecycle ) patchLegacyPaymentHash (
1072
+ a channeldb.HTLCAttempt ) channeldb.HTLCAttempt {
1073
+
1074
+ // Exit early if this is not a legacy attempt.
1075
+ if a .Hash != nil {
1076
+ return a
1077
+ }
1078
+
1079
+ // Log a warning if the user is still using legacy payments, which has
1080
+ // weaker support.
1081
+ log .Warnf ("Found legacy htlc attempt %v in payment %v" , a .AttemptID ,
1082
+ p .identifier )
1083
+
1084
+ // Set the attempt's hash to be the payment hash, which is the payment's
1085
+ // `PaymentHash`` in the `PaymentCreationInfo`. For legacy payments
1086
+ // before AMP feature, the `Hash` field was not set so we use the
1087
+ // payment hash instead.
1088
+ //
1089
+ // NOTE: During the router's startup, we have a similar logic in
1090
+ // `resumePayments`, in which we will use the payment hash instead if
1091
+ // the attempt's hash is nil.
1092
+ a .Hash = & p .identifier
1093
+
1094
+ return a
1095
+ }
1096
+
1063
1097
// reloadInflightAttempts is called when the payment lifecycle is resumed after
1064
1098
// a restart. It reloads all inflight attempts from the control tower and
1065
1099
// collects the results of the attempts that have been sent before.
@@ -1075,6 +1109,10 @@ func (p *paymentLifecycle) reloadInflightAttempts() (DBMPPayment, error) {
1075
1109
log .Infof ("Resuming HTLC attempt %v for payment %v" ,
1076
1110
a .AttemptID , p .identifier )
1077
1111
1112
+ // Potentially attach the payment hash to the `Hash` field if
1113
+ // it's a legacy payment.
1114
+ a = p .patchLegacyPaymentHash (a )
1115
+
1078
1116
p .resultCollector (& a )
1079
1117
}
1080
1118
0 commit comments