@@ -2780,28 +2780,43 @@ func (l *channelLink) UpdateForwardingPolicy(
27802780func (l * channelLink ) CheckHtlcForward (payHash [32 ]byte ,
27812781 incomingHtlcAmt , amtToForward lnwire.MilliSatoshi ,
27822782 incomingTimeout , outgoingTimeout uint32 ,
2783+ inboundFee models.InboundFee ,
27832784 heightNow uint32 , originalScid lnwire.ShortChannelID ) * LinkError {
27842785
27852786 l .RLock ()
27862787 policy := l .cfg .FwrdingPolicy
27872788 l .RUnlock ()
27882789
2789- // Using the amount of the incoming HTLC, we'll calculate the expected
2790- // fee this incoming HTLC must carry in order to satisfy the
2791- // constraints of the outgoing link.
2792- expectedFee := ExpectedFee (policy , amtToForward )
2790+ // Using the outgoing HTLC amount, we'll calculate the outgoing
2791+ // fee this incoming HTLC must carry in order to satisfy the constraints
2792+ // of the outgoing link.
2793+ outFee := ExpectedFee (policy , amtToForward )
2794+
2795+ // Then calculate the inbound fee that we charge based on the sum of
2796+ // outgoing HTLC amount and outgoing fee.
2797+ inFee := inboundFee .CalcFee (amtToForward + outFee )
2798+
2799+ // Add up both fee components. It is important to calculate both fees
2800+ // separately. An alternative way of calculating is to first determine
2801+ // an aggregate fee and apply that to the outgoing HTLC amount. However,
2802+ // rounding may cause the result to be slightly higher than in the case
2803+ // of separately rounded fee components. This potentially causes failed
2804+ // forwards for senders and is something to be avoided.
2805+ expectedFee := inFee + int64 (outFee )
27932806
27942807 // If the actual fee is less than our expected fee, then we'll reject
27952808 // this HTLC as it didn't provide a sufficient amount of fees, or the
27962809 // values have been tampered with, or the send used incorrect/dated
27972810 // information to construct the forwarding information for this hop. In
2798- // any case, we'll cancel this HTLC. We're checking for this case first
2799- // to leak as little information as possible.
2800- actualFee := incomingHtlcAmt - amtToForward
2811+ // any case, we'll cancel this HTLC.
2812+ actualFee := int64 (incomingHtlcAmt ) - int64 (amtToForward )
28012813 if incomingHtlcAmt < amtToForward || actualFee < expectedFee {
28022814 l .log .Warnf ("outgoing htlc(%x) has insufficient fee: " +
2803- "expected %v, got %v" ,
2804- payHash [:], int64 (expectedFee ), int64 (actualFee ))
2815+ "expected %v, got %v: incoming=%v, outgoing=%v, " +
2816+ "inboundFee=%v" ,
2817+ payHash [:], expectedFee , actualFee ,
2818+ incomingHtlcAmt , amtToForward , inboundFee ,
2819+ )
28052820
28062821 // As part of the returned error, we'll send our latest routing
28072822 // policy so the sending node obtains the most up to date data.
@@ -3330,6 +3345,8 @@ func (l *channelLink) processRemoteAdds(fwdPkg *channeldb.FwdPkg,
33303345 // round of processing.
33313346 chanIterator .EncodeNextHop (buf )
33323347
3348+ inboundFee := l .cfg .FwrdingPolicy .InboundFee
3349+
33333350 updatePacket := & htlcPacket {
33343351 incomingChanID : l .ShortChanID (),
33353352 incomingHTLCID : pd .HtlcIndex ,
@@ -3342,6 +3359,7 @@ func (l *channelLink) processRemoteAdds(fwdPkg *channeldb.FwdPkg,
33423359 incomingTimeout : pd .Timeout ,
33433360 outgoingTimeout : fwdInfo .OutgoingCTLV ,
33443361 customRecords : pld .CustomRecords (),
3362+ inboundFee : inboundFee ,
33453363 }
33463364 switchPackets = append (
33473365 switchPackets , updatePacket ,
@@ -3394,6 +3412,8 @@ func (l *channelLink) processRemoteAdds(fwdPkg *channeldb.FwdPkg,
33943412 // have been added to switchPackets at the top of this
33953413 // section.
33963414 if fwdPkg .State == channeldb .FwdStateLockedIn {
3415+ inboundFee := l .cfg .FwrdingPolicy .InboundFee
3416+
33973417 updatePacket := & htlcPacket {
33983418 incomingChanID : l .ShortChanID (),
33993419 incomingHTLCID : pd .HtlcIndex ,
@@ -3406,6 +3426,7 @@ func (l *channelLink) processRemoteAdds(fwdPkg *channeldb.FwdPkg,
34063426 incomingTimeout : pd .Timeout ,
34073427 outgoingTimeout : fwdInfo .OutgoingCTLV ,
34083428 customRecords : pld .CustomRecords (),
3429+ inboundFee : inboundFee ,
34093430 }
34103431
34113432 fwdPkg .FwdFilter .Set (idx )
0 commit comments