-
Notifications
You must be signed in to change notification settings - Fork 300
Integrate payload attestations into validator duties #7783
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
base: unstable
Are you sure you want to change the base?
Conversation
Tomi-3-0
commented
Dec 8, 2025
- Fix: Sign PayloadAttestationData instead of full message per spec
- Integrate payload attestations into validator duty cycle
|
|
||
| for i in 0..<commitments.len: | ||
| var blob: BlobSidecar | ||
| if not node.dag.db.getBlobSidecar(beacon_block_root, BlobIndex(i), blob): |
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.
It would be better to just check for the existence of the key, less database I/O and less memory usage, similar to how
nimbus-eth2/beacon_chain/beacon_chain_db.nim
Lines 1277 to 1323 in b186c99
| proc containsBlock*(db: BeaconChainDBV0, key: Eth2Digest): bool = | |
| db.backend.contains(subkey(phase0.SignedBeaconBlock, key)).expectDb() | |
| proc containsBlock*[X: ForkyTrustedSignedBeaconBlock]( | |
| db: BeaconChainDB, key: Eth2Digest, T: typedesc[X]): bool = | |
| const consensusFork = T.kind | |
| var res = | |
| db.blocks[consensusFork] != nil and | |
| db.blocks[consensusFork].contains(key.data).expectDb() | |
| when consensusFork < ConsensusFork.Altair: | |
| # During initial releases phase0, we stored states in a different table | |
| res = res or db.v0.containsBlock(key) | |
| res | |
| proc containsBlock*(db: BeaconChainDB, key: Eth2Digest, fork: ConsensusFork): bool = | |
| case fork | |
| of ConsensusFork.Phase0: | |
| containsBlock(db, key, phase0.TrustedSignedBeaconBlock) | |
| else: | |
| db.blocks[fork] != nil and | |
| db.blocks[fork].contains(key.data).expectDb() | |
| proc containsBlock*(db: BeaconChainDB, key: Eth2Digest): bool = | |
| for fork in countdown(ConsensusFork.high, ConsensusFork.low): | |
| if db.containsBlock(key, fork): return true | |
| false | |
| proc containsState*(db: BeaconChainDBV0, key: Eth2Digest): bool = | |
| let sk = subkey(Phase0BeaconStateNoImmutableValidators, key) | |
| db.stateStore.contains(sk).expectDb() or | |
| db.backend.contains(sk).expectDb() or | |
| db.backend.contains(subkey(phase0.BeaconState, key)).expectDb() | |
| proc containsState*(db: BeaconChainDB, fork: ConsensusFork, key: Eth2Digest, | |
| legacy: bool = true): bool = | |
| if db.statesNoVal[fork] == nil: return false | |
| if db.statesNoVal[fork].contains(key.data).expectDb(): return true | |
| (legacy and fork == ConsensusFork.Phase0 and db.v0.containsState(key)) | |
| proc containsState*(db: BeaconChainDB, key: Eth2Digest, legacy: bool = true): bool = | |
| for fork in countdown(ConsensusFork.high, ConsensusFork.low): | |
| if db.statesNoVal[fork] != nil and | |
| db.statesNoVal[fork].contains(key.data).expectDb(): return true | |
| (legacy and db.v0.containsState(key)) |
work, i.e. a
contains function in the database layer.
These also end up being conveniently testable insofar as there are tests for put/get/del.
That said, I'm not sure checking for blobs in the database at all is the right approach. For example, blobs can't in general be reconstructed unless one has at least half the columns, but nodes which have fewer than half the columns are also expected to provide payload attestations, because neither https://github.com/ethereum/consensus-specs/blob/v1.6.1/specs/gloas/validator.md#payload-timeliness-committee nor https://github.com/ethereum/consensus-specs/blob/v1.6.1/specs/gloas/validator.md#constructing-a-payload-attestation specifies anything about the PTC needing to be made entirely of supernodes or light supernodes.
So I don't know if checkBlobDataAvailable is the right function to have, here.
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.
Exactly. I agree
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.
7779b07 changes it to custody columns, not blobs, consistent with current spec interpretation.
|
| withBlck(blckData): | ||
| when consensusFork >= ConsensusFork.Gloas: | ||
| var envelope: TrustedSignedExecutionPayloadEnvelope | ||
| if not node.dag.db.getExecutionPayloadEnvelope( |
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.
The actual envelope here isn't used, so retrieving it from the database, allocating and copying it around, and returning it is pointless. Better to have a containsExecutionPayloadEnvelope function in beacon_chain_db and query that.
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.
I've removed the envelope check entirely and just check custody columns directly.
eliminating the envelope deserialization completely. The trade-off is checking custody columns even when there are no blobs, but since those are just fast SQL key lookups versus the expensive deserialisation
| # check that our custody columns are available | ||
| for columnIdx in node.dataColumnQuarantine.custodyColumns: | ||
| var column: gloas.DataColumnSidecar | ||
| if not node.dag.db.getDataColumnSidecar( |
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.
The column here isn't used, so retrieving it from the database, allocating and copying it around, and returning it is pointless. Better to have a containsDataColumnSidecar function in beacon_chain_db and query that.