celestiaorg / go-header

Go library with all the services needed to request, sync and store blockchain headers.
Apache License 2.0
17 stars 16 forks source link

Attacks possible if we always accept non-adjacent headers #79

Closed Wondertan closed 10 months ago

Wondertan commented 11 months ago

We were talking about Rollkit implications with @nashqueue and found a few attacks with the current solution:

liamsi commented 11 months ago

We accept all non-adjacent headers as valid, and everyone gossips them.

Can we not wait to gossip them until verified via adjacent verification (or if that does not check out, they won't be gossiped at all)?

We don't have any top limit on height for accepted non-adjacent headers, so attackers can fill up the whole network through message amplification until OOM

Couldn't that be fixed by estimating a time/height for the time that has past from genesis?

Wondertan commented 11 months ago

Can we not wait to gossip them until verified via adjacent verification (or if that does not check out, they won't be gossiped at all)?

This is the simplest thing we can do. When we discussed this with @renaynay, we had a concern that the headers won't gossip because no one will regossip them, but in fact, all well-connected nodes will be synced up to the tip and will do adjacent verification to submit it further. Only nodes who didn't catch up to the tip won't reshare them, which I think is not bad and even intuitively feels right.

Couldn't that be fixed by estimating a time/height for the time that has past from genesis?

I think so, but I remember @musalbas had some concerns about block time assumptions not being realistic/precise. It might be that we don't need perfect precision in this case, and would like to hear your thoughts.

renaynay commented 11 months ago

TODO (outcomes from meeting on 12.7.23)

Wondertan commented 11 months ago

The default trusting period in celestia-core https://github.com/celestiaorg/celestia-core/blob/v0.34.x-celestia/cmd/cometbft/commands/light.go#L90.

liamsi commented 11 months ago
  1. currently, if nodes start following a fork (outside of the unbonding period), they will discard the subjective head (which was given by a subjectively chosen trusted peer or the default baked in trusted peer in node). This is an issue that can easily be fixed by:

    • either by backwards-sync (which would be very time consuming), or

    • a simpler fix: once your fork passed the time or the height of the subjective header (inside of the unbonding period), you realize you are actually on a fork and you (store the fork as evidence and) halt; it’s important that the fork headers aren’t gossiped. Recovering from this requires you to restart the node, ideally blacklisting the peers that fooled you

  2. The concern about timing assumption are a non-issue as you would always reject headers that are subjective header + too far in the future (outside of the unbonding period but forward looking); no precision around block times is necessary here.