It is recommended to only support the latest version of the spec.
This document has been superseded by EIP-3076, available here: https://eips.ethereum.org/EIPS/eip-3076
v5 (2020-10-23):
interchange_format
fieldv4 (2020-09-17):
minimal
format by applying new semantics to the complete
formatv3 (2020-09-01):
last_signed_block_slot
and last_signed_attestation_{source,target}_epoch
to be null
in the minimal format, to represent the case where a validator has not yet signed a block or attestation (thanks Paul Harris).v2 (2020-08-31):
v1 (2020-08-18):
A complete record of all blocks and attestations signed by a set of validators
{
"metadata": {
"interchange_format_version": "5",
"genesis_validators_root": "0x04700007fabc8282644aed6d1c7c9e21d38a03a0c4ba193f3afe428824b3a673"
},
"data": [
{
"pubkey": "0xb845089a1457f811bfc000588fbb4e713669be8ce060ea6be3c6ece09afc3794106c91ca73acda5e5457122d58723bed",
"signed_blocks": [
{
"slot": "81952",
"signing_root": "0x4ff6f743a43f3b4f95350831aeaf0a122a1a392922c45d804280284a69eb850b"
},
{
"slot": "81951",
},
...
],
"signed_attestations": [
{
"source_epoch": "2290",
"target_epoch": "3007",
"signing_root": "0x587d6a4f59a58fe24f406e0502413e77fe1babddee641fda30034ed37ecc884d"
},
{
"source_epoch": "2290",
"target_epoch": "3008",
},
...
]
}
]
}
pubkey: BLSPubkey
is the BLS public key of the validator encoded as 0x-prefixed hex.signed_blocks
is a list of objects with fields:
slot: Slot
, the slot of the block that was signedsigning_root: Root
(optional) is compute_signing_root(block, domain)
, where:
block
is the block that was signed as type BeaconBlock
or equivalently BeaconBlockHeader
domain
is equal to compute_domain(DOMAIN_BEACON_PROPOSER, fork, metadata.genesis_validators_root)
, where:
metadata.genesis_validators_root
is the genesis_validators_root
from this interchange filefork: Version
is the fork that the block was signed againstsigned_attestations
is a list of objects with fields:
source_epoch: Epoch
, the attestation.data.source.epoch
of the signed attestationtarget_epoch: Epoch
, the attestation.data.target.epoch
of the signed attestationsigning_root: Root
(optional) is compute_signing_root(attestation, domain)
, where:
attestation
is the attestation that was signed as type AttestationData
domain
is equal to compute_domain(DOMAIN_BEACON_ATTESTER, fork, metadata.genesis_validators_root)
, where:
metadata.genesis_validators_root
is the genesis_validators_root
from this interchange filefork: Version
is the fork that the attestation was signed againstTo support the role that the minimal
format used to play, we impose some additional restrictions about signing messages less than the minimum block/attestation (points 2 and 4 below).
After importing an interchange file with data field data
, a signer MUST:
data.signed_blocks
. For details of what constitutes a slashable block, see process_proposer_slashing. If the signing_root
is absent from a block, a signer must assume that any new block with the same slot is slashable with respect to the imported block.slot <= min(b.slot for b in data.signed_blocks if b.pubkey == proposer_pubkey)
, except if it is a repeat signing as determined by the signing_root
.data.signed_attestations
. For details of what constitutes a slashable attestation, see is_slashable_attestation_data.source.epoch < min(att.source_epoch for att in data.signed_attestations if att.pubkey == attester_pubkey)
, ORtarget_epoch <= min(att.target_epoch for att in data.signed_attestations if att.pubkey == attester_pubkey)
The old minimal
format can be emulated by outputting 0-1 attestations and blocks for each validator (no signing root required). For example, this complete
interchange is now equivalent to the old minimal
example shown below:
{
"metadata": {
"interchange_format": "complete",
"interchange_format_version": "4",
"genesis_validators_root": "0x04700007fabc8282644aed6d1c7c9e21d38a03a0c4ba193f3afe428824b3a673"
},
"data": [
{
"pubkey": "0xb845089a1457f811bfc000588fbb4e713669be8ce060ea6be3c6ece09afc3794106c91ca73acda5e5457122d58723bed",
"signed_blocks": [ { "slot": "89765" } ],
"signed_attestations": [ { "source_epoch": "2990", "target_epoch": "3007" } ]
},
...
],
}
If a validator is yet to sign a block or attestation, the relevant list is simply left empty – no more null
!
NOT SUPPORTED AS OF v4 DRAFT OR LATER
Similar to Teku's native format, just 3 integers per validator:
{
"metadata": {
"interchange_format": "minimal",
"interchange_format_version": "3",
"genesis_validators_root": "0x04700007fabc8282644aed6d1c7c9e21d38a03a0c4ba193f3afe428824b3a673"
},
"data": [
{
"pubkey": "0xb845089a1457f811bfc000588fbb4e713669be8ce060ea6be3c6ece09afc3794106c91ca73acda5e5457122d58723bed",
"last_signed_block_slot": "89765",
"last_signed_attestation_source_epoch": "2990",
"last_signed_attestation_target_epoch": "3007",
},
...
],
}
pubkey
is the BLS public key of the validator encoded as 0x-prefixed hex.last_signed_block_slot: Slot
(optional) is the greatest slot of a block signed by pubkey
. Can be null
to indicate that no block has been signed.last_signed_attestation_source_epoch: Epoch
(optional) is the greatest attestation.data.source.epoch
of an attestation
signed by pubkey
. Can be null
or absent.last_signed_attestation_target_epoch: Epoch
(optional) is the greatest attestation.data.target.epoch
of an attestation
signed by pubkey
. Can be null
or absent.It is an error for one of last_signed_attestation_source_epoch
or last_signed_attestation_target_epoch
to be null
/absent, if the other is present.
https://github.com/eth2-clients/slashing-protection-interchange-tests
Some breaking changes that could be worth pursuing with client consensus
last_signed_
fields to greatest_signed_
or highest_signed_
to clarify that it should not be the most recently signed message, but the highest slot/epoch one.