-
Notifications
You must be signed in to change notification settings - Fork 447
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
simulators/ethereum/engine: Re-org to Chain with Missing Invalid Payload #526
Conversation
IMO, the following order of message should better reflect a real CL flow:
In this case if Inducing this scenario requires We may also skip |
Thanks for the feedback @mkalinin , I think I can do some experiments on how many blocks do we need to advance on the canonical chain before I also like the idea of the client having to pull I will start working on this update. |
Hi @mkalinin, I ran the experiment of doing a long canonical chain to attempt to induce a state prune of the
Geth response to Let me know what you think about this scenario, I think the original test case is still valuable even without state pruning (latestValidHash verification was valuable to find an issue in geth). |
I think that there need to be a contract deployment in |
I checked with @MariusVanDerWijden and it seems like state pruning only occurs after 90,000 blocks, at least for Geth, which I think would make this test take extremely long for a regression test. Would sending |
e02e8fc
to
c04a549
Compare
Hi @mkalinin, @MariusVanDerWijden, @djrtwo, I've added the Invalid Payload Sync test cases that have the Geth error. The test case is structured as follows:
At the moment none of the clients passes these tests because either:
I have added a test case per each possible header field that can be manipulated in order to produce an invalid payload, with a total of 14 test cases. If this is too exhaustive please let me know and we can reduce the test cases to the most significant ones. |
I always think the more variants of the test the better. Especially, if they run on CI. If tests consume a lot of time and this becomes an issue then we should think about the way to reduce this number, unless that I'd say run as many as we can. |
@marioevz Does the geth bug happen with a particular test or on all of them? |
I've only found one combination where the issue reproduces (Modified StateRoot + No Tx) out of all the combinations. |
This PR should be ready for review/merge. One consideration to take into account is that the new tests are currently failing for all clients due to the reasons explained in a previous comment. |
Hi @mkalinin, I've added the check on the fcU LVH on the invalid ancestor chain. |
That's not quite the case. State pruning occurs after 128 blocks -- that's when we start removing the trie roots. |
Ah I see, the original idea for the test was that at some point the I think the test scenario is correctly achieved by the sync test case, but it's open for discussion if there could be a way we could trigger the |
I have updated the test cases to be more in line with the implementation description here: The test cases now invalidate the second to last payload on the side chain, therefore, The test is still failing for all clients. LMK if this change looks ok @mkalinin @MariusVanDerWijden |
|
||
const ( | ||
InvalidParentHash InvalidPayloadField = "ParentHash" | ||
InvalidStateRoot = "StateRoot" |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
BTW, the constants here will not have the type you expect. While InvalidParentHash
has type InvalidPayloadField
, the other constants are of type 'untyped string'. See https://go.dev/play/p/tyAGBY8nkuS for an example. The code compiles anyway because a value of type 'untyped string' can be assigned to a variables of type InvalidPayloadField
(since the underlying type is string).
You can fix this by listing the type in every line. We usually do it like this:
const (
InvalidParentHash = InvalidPayloadField("ParentHash")
...
)
This PR implements test case where the CL attempts to re-org into a side chain with unknown payloads to the EL.
The test first generates a side chain with N payloads, which at some point contains an invalid payload, but the side chain remains unknown to the EL:
After Pn, the CL performs an
fcU(Pn')
to the head of the side chain.Then the CL proceeds to reveal the remaining payloads in the following order:
Currently two scenarios are implemented:
P1'
is invalid, and sinceCommonAncestor
is known to the EL, the response tonewPayload(P1')
should beINVALID
withlatestValidHash==CommonAncestor.Hash
.P3'
is invalid and the response tonewPayload(P3')
should beACCEPTED
withlatestValidHash==nil
because when the payload is received there is not enough information to invalidate the payload.Current outcome:
INVALID
on the first scenario, but returns an incorrect LVH withlatestValidHash==Pn.Hash
The PR is open for discussion and suggestions.
cc @mkalinin, @MarekM25, @MariusVanDerWijden