Hey Joost and Z, I brought up the question about the amounts because it could be that > amounts high enough to thwart attacks are too high for honest users or > certain uses.
I don't think this is a concern for this proposal, unless there's an attack vector I missed. The reason I claim that is that the backwards upfront payment can be made somewhat big without any negative impact on honest nodes. If you're an honest intermediate node, only two cases are possible: * your downstream peer settled the HTLC quickly (before the grace period ends): in that case you refund him his upfront fee, and you have time to settle the HTLC upstream while still honoring the grace period, so it will be refunded to you as well (unless you delay the settlement upstream for whatever reason, in which case you deserve to pay the hold_fee) * your grace period has expired, so you can't get a refund upstream: if that happens, the grace period with your downstream node has also expired, so you're earning money downstream and paying money upstream, and you'll usually even take a small positive spread so everything's good The only node that can end up loosing money on the backwards upfront payment is the last node in the route. But that node should always settle the HTLC quickly (or decide to hodl it, but in that case it's normal that it pays the hold_fee). But what happens if the attacker is also on the other end of the > uncontrolled spam payment? Not holding the payment, but still collecting > the forward payments? That's what I call short-lived `controlled spam`. In that case the attacker pays the forward fee at the beginning of the route but has it refunded at the end of the route. If the attacker doesn't want to lose any money, he has to release the HTLC before the grace period ends (which is going to be short-lived - at least compared to block times). This gives an opportunity for legitimate payments to use the HTLC slots (but it's a race between the attacker and the legitimate users). It's not ideal, because the attacker isn't penalized...the only way I think we can penalize this kind of attack is if the forward fee decrements at each hop, but in that case it needs to be in the onion (to avoid probing) and the delta needs to be high enough to actually penalize the attacker. Time to bikeshed some numbers! C can trivially grief D here, making it look like D is delaying, by > delaying its own `commitment_signed` containing the *removal* of the HTLC. You're right to dive into these, there may be something here. But I think your example doesn't work, let me know if I'm mistaken. D is the one who decides whether he'll be refunded or not, because D is the first to send the `commit_sig` that removes the HTLC. I think we would extend `commit_sig` with a tlv field that indicates "I refunded myself for HTLC N" to help C compute the same commit tx and verify sigs. I agree with you that the details of how we'll implement the grace period may have griefing attacks depending on how we do it, it's worth exploring further. Cheers, Bastien Le ven. 23 oct. 2020 à 12:50, ZmnSCPxj <zmnsc...@protonmail.com> a écrit : > Good morning t-bast, > > > > > And in this case C earns. > > > > > Can C delay the refund to D to after the grace period even if D > settled the HTLC quickly? > > > > Yes C earns, but D has misbehaved. As a final recipient, D isn't > dependent on anyone downstream. > > An honest D should settle the HTLC before the `grace_period` ends. If D > chooses to hold the HTLC > > for a while, then it's fair that he pays C for this. > > > Okay, now let us consider the case where the supposedly-delaying party is > not the final destination. > > So, suppose D indicates to C that it should fail the HTLC. > In this case, C cannot immediately propagate the `update_fail_htlc` > upstream, since the latest commitment transaction for the C<->D channel > still contains the HTLC. > > In addition, our state machine is hand-over-hand, i.e. there is a small > window where there are two valid commitment transactions. > What happens is we sign the next commitment transaction and *then* revoke > the previous one. > > So I think C can only safely propagate its own upstream `update_fail_htlc` > once it receives the `revoke_and_ack` from D. > > So the time measured for the grace period between C and D should be from C > sending `update_add_htlc` to C receiving `revoke_and_ack` from D, in case > the HTLC fails. > This is the time period that D is allowed to consume, and if it exceeds > the grace period, it is penalized. > > (In this situation, it is immaterial if D is the destination: C cannot > know this fact.) > > So let us diagram this better: > > C D > |----update_add_htlc--->| --- > |---commitment_signed-->| ^ > |<----revoke_and_ack----| | > |<--commitment_signed---| | > |-----revoke_and_ack--->| | > | | grace period > |<--update_fail_htlc----| | > |<--commitment_signed---| | > |-----revoke_and_ack--->| | > |---commitment_signed-->| v <--- grief point! > |<----revoke_and_ack----| --- > > (somebody *else* better make sure my understanding of the state machine is > correct!) > > C can trivially grief D here, making it look like D is delaying, by > delaying its own `commitment_signed` containing the *removal* of the HTLC. > D cannot send its own `revoke_and_ack` until it receives the signature for > its own next commitment, as if it did so, it would lose the ability to > close the channel unilaterally; it has to wait for C to send the > `commitment_signed`. > > Thus, it seems to me that C can grief D here. > > The question is: does the above C-can-grief-D matter? > > I think D does have a defense against C griefing in the above case: > > * If the time between D->`update_fail_htlc`->C and the corresponding > C->`commitment_signed`->D becomes too long: > * D drops the channel onchain. > * The dropped commitment tx still contains the HTLC, since it is the > "previous" commitment that D happens to hold that has not yet had the > `update_fail_htlc` committed. > > If D performs the above, then C is forced to wait *even longer* (it has to > wait out the HTLC timelock) before it can safely propagate the > `update_fail_htlc`: D could be fooling with it and actually knows the > preimage and claim it onchain, so C for its own safety *must* wait out the > onchain timelock. > > Does that make sense? > Does it sensibly protect against this griefing? > Is it too much of a punishment and could potentially hurt D more than it > hurts C if C is a heavily-connected node that will not miss the channel > while D has fewer channels and opened the C<->D channel in the first place? > > -- > > For success case `update_fulfill_htlc`, I believe C can immediately > propagate this back to its upstream since it can now. > Thus, in that case, we can stop the timer at the `update_fulfill_htlc`. > > So at least for the *end point* of the grace period, I think the end point > should be: > > * If the HTLC failed: > * When both participants have sent `revoke_and_ack`. > * If the HTLC succeeded: > * When the downstream participant has sent `update_fulfill_htlc`. > > For the *start point*, it seems the C->`commitment_signed`->D containing > the HTLC would work as the start point. > In particular, it seems to me that C can also deliberately defer its own > C->`revoke_and_ack`->D: > > C D > |----update_add_htlc--->| > |---commitment_signed-->| --- > |<----revoke_and_ack----| ^ > |<--commitment_signed---| | > |-----revoke_and_ack--->| | <--- grief point! > | | grace period > |<--update_fail_htlc----| | > |<--commitment_signed---| | > |-----revoke_and_ack--->| | > |---commitment_signed-->| v > |<----revoke_and_ack----| --- > > (If D deliberately delays, then it is penalized, so we should consider the > case where C attempts to trigger the reverse case). > D cannot safely fulfill the HTLC until after the previous commitment > transactions of *both* sides have been revoked ("irrevocably committed" > state). > So D can use the same defense, I think: if C is taking too long to send > the `revoke_and_ack` pointed at above, it drops the channel onchain with > the HTLC instantiated (which is why the *start time* has to be the > C->`commitment_signed`->D that contains the new HTLC). > > Thus the D grace period has two smaller grace periods that D imposes on C, > using the threat of channel drop to protect against the C-side griefing. > > > > Sorry for dropping into details already but so far this is the only > griefing attack I can think of right now. > > > > Regards, > ZmnSCPxj >
_______________________________________________ Lightning-dev mailing list Lightning-dev@lists.linuxfoundation.org https://lists.linuxfoundation.org/mailman/listinfo/lightning-dev