diff --git a/node/direct/sentry_client.go b/node/direct/sentry_client.go index 0380fb80bef..a3c077876a0 100644 --- a/node/direct/sentry_client.go +++ b/node/direct/sentry_client.go @@ -28,37 +28,25 @@ import ( "github.com/erigontech/erigon/node/gointerfaces/sentryproto" "github.com/erigontech/erigon/node/gointerfaces/typesproto" + "github.com/erigontech/erigon/p2p/protocols/eth" + "github.com/erigontech/erigon/p2p/protocols/wit" "github.com/erigontech/erigon/p2p/sentry/libsentry" ) const ( - ETH68 = 68 - ETH69 = 69 - ETH70 = 70 - ETH71 = 71 + ETH68 = eth.ETH68 + ETH69 = eth.ETH69 + ETH70 = eth.ETH70 + ETH71 = eth.ETH71 - WIT0 = 1 + WIT0 = wit.WIT1 ) var ( - ProtocolToUintMap = map[sentryproto.Protocol]uint{ - sentryproto.Protocol_ETH68: ETH68, - sentryproto.Protocol_ETH69: ETH69, - sentryproto.Protocol_ETH70: ETH70, - sentryproto.Protocol_ETH71: ETH71, - } - UintToProtocolMap = map[uint]sentryproto.Protocol{ - ETH68: sentryproto.Protocol_ETH68, - ETH69: sentryproto.Protocol_ETH69, - ETH70: sentryproto.Protocol_ETH70, - ETH71: sentryproto.Protocol_ETH71, - } - SupportedSideProtocols = map[sentryproto.Protocol]struct{}{ - sentryproto.Protocol_WIT0: {}, - } - UintToSideProtocolMap = map[uint]sentryproto.Protocol{ - WIT0: sentryproto.Protocol_WIT0, - } + ProtocolToUintMap = libsentry.ProtocolToUintMap + UintToProtocolMap = libsentry.UintToProtocolMap + SupportedSideProtocols = libsentry.SupportedSideProtocols + UintToSideProtocolMap = libsentry.UintToSideProtocolMap ) //go:generate mockgen -typed=true -destination=./sentry_client_mock.go -package=direct . SentryClient diff --git a/p2p/protocols/eth/handlers.go b/p2p/protocols/eth/handlers.go index 69bb976ff3e..c376229dd9f 100644 --- a/p2p/protocols/eth/handlers.go +++ b/p2p/protocols/eth/handlers.go @@ -283,7 +283,7 @@ const NoSizeLimit = math.MaxInt // ReceiptQueryOpts controls the behavior differences between eth protocol versions // when answering GetReceipts queries. type ReceiptQueryOpts struct { - // EthVersion is the protocol version (e.g. direct.ETH68, direct.ETH69, direct.ETH70). + // EthVersion is the protocol version (e.g. ETH68, ETH69, ETH70). // eth/69+ uses encoding without the Bloom field. EthVersion uint // FirstBlockReceiptIndex skips this many receipts from the first block (eth/70). diff --git a/p2p/protocols/eth/handlers_receipts_query_test.go b/p2p/protocols/eth/handlers_receipts_query_test.go index e494ec3d57a..a12182f34a4 100644 --- a/p2p/protocols/eth/handlers_receipts_query_test.go +++ b/p2p/protocols/eth/handlers_receipts_query_test.go @@ -31,7 +31,6 @@ import ( "github.com/erigontech/erigon/execution/chain" "github.com/erigontech/erigon/execution/rlp" "github.com/erigontech/erigon/execution/types" - "github.com/erigontech/erigon/node/direct" ) // Per the devp2p spec, a Receipts response carries one receipt list per requested @@ -97,7 +96,7 @@ func answerQuery(t *testing.T, f *receiptsQueryFixture) ([]rlp.RawValue, bool, e tx, err := db.BeginTemporalRo(context.Background()) require.NoError(t, err) defer tx.Rollback() - opts := ReceiptQueryOpts{EthVersion: direct.ETH68, SizeLimit: NoSizeLimit} + opts := ReceiptQueryOpts{EthVersion: ETH68, SizeLimit: NoSizeLimit} return AnswerGetReceiptsQuery(context.Background(), chain.TestChainBerlinConfig, f.getter, f.br, tx, f.query, nil, opts) } diff --git a/p2p/protocols/eth/protocol.go b/p2p/protocols/eth/protocol.go index 425ea1cba2b..fa334ad2288 100644 --- a/p2p/protocols/eth/protocol.go +++ b/p2p/protocols/eth/protocol.go @@ -22,6 +22,7 @@ package eth import ( "fmt" "io" + "maps" "math/big" "github.com/holiman/uint256" @@ -29,16 +30,22 @@ import ( "github.com/erigontech/erigon/common" "github.com/erigontech/erigon/execution/rlp" "github.com/erigontech/erigon/execution/types" - "github.com/erigontech/erigon/node/direct" "github.com/erigontech/erigon/node/gointerfaces/sentryproto" "github.com/erigontech/erigon/p2p/forkid" ) +const ( + ETH68 = 68 + ETH69 = 69 + ETH70 = 70 + ETH71 = 71 +) + var ProtocolToString = map[uint]string{ - direct.ETH68: "eth68", - direct.ETH69: "eth69", - direct.ETH70: "eth70", - direct.ETH71: "eth71", + ETH68: "eth68", + ETH69: "eth69", + ETH70: "eth70", + ETH71: "eth71", } // ProtocolName is the official short name of the `eth` protocol used during @@ -49,7 +56,7 @@ const ProtocolName = "eth" const maxMessageSize = 10 * 1024 * 1024 const ProtocolMaxMsgSize = maxMessageSize -var ProtocolLengths = map[uint]uint64{direct.ETH68: 17, direct.ETH69: 18, direct.ETH70: 18, direct.ETH71: 20} +var ProtocolLengths = map[uint]uint64{ETH68: 17, ETH69: 18, ETH70: 18, ETH71: 20} const ( // Protocol messages in eth/64 @@ -75,137 +82,70 @@ const ( BlockAccessListsMsg = 0x13 ) +var toProto68 = map[uint64]sentryproto.MessageId{ + GetBlockHeadersMsg: sentryproto.MessageId_GET_BLOCK_HEADERS_66, + BlockHeadersMsg: sentryproto.MessageId_BLOCK_HEADERS_66, + GetBlockBodiesMsg: sentryproto.MessageId_GET_BLOCK_BODIES_66, + BlockBodiesMsg: sentryproto.MessageId_BLOCK_BODIES_66, + GetReceiptsMsg: sentryproto.MessageId_GET_RECEIPTS_66, + ReceiptsMsg: sentryproto.MessageId_RECEIPTS_66, + NewBlockHashesMsg: sentryproto.MessageId_NEW_BLOCK_HASHES_66, + NewBlockMsg: sentryproto.MessageId_NEW_BLOCK_66, + TransactionsMsg: sentryproto.MessageId_TRANSACTIONS_66, + NewPooledTransactionHashesMsg: sentryproto.MessageId_NEW_POOLED_TRANSACTION_HASHES_68, + GetPooledTransactionsMsg: sentryproto.MessageId_GET_POOLED_TRANSACTIONS_66, + PooledTransactionsMsg: sentryproto.MessageId_POOLED_TRANSACTIONS_66, +} + +var toProto69 = withDelta(toProto68, map[uint64]sentryproto.MessageId{ + StatusMsg: sentryproto.MessageId_STATUS_69, + GetReceiptsMsg: sentryproto.MessageId_GET_RECEIPTS_69, + BlockRangeUpdateMsg: sentryproto.MessageId_BLOCK_RANGE_UPDATE_69, +}) + +var toProto70 = withDelta(toProto69, map[uint64]sentryproto.MessageId{ + GetReceiptsMsg: sentryproto.MessageId_GET_RECEIPTS_70, + ReceiptsMsg: sentryproto.MessageId_RECEIPTS_70, +}) + +var toProto71 = withDelta(toProto70, map[uint64]sentryproto.MessageId{ + GetBlockAccessListsMsg: sentryproto.MessageId_GET_BLOCK_ACCESS_LISTS_71, + BlockAccessListsMsg: sentryproto.MessageId_BLOCK_ACCESS_LISTS_71, +}) + var ToProto = map[uint]map[uint64]sentryproto.MessageId{ - direct.ETH68: { - GetBlockHeadersMsg: sentryproto.MessageId_GET_BLOCK_HEADERS_66, - BlockHeadersMsg: sentryproto.MessageId_BLOCK_HEADERS_66, - GetBlockBodiesMsg: sentryproto.MessageId_GET_BLOCK_BODIES_66, - BlockBodiesMsg: sentryproto.MessageId_BLOCK_BODIES_66, - GetReceiptsMsg: sentryproto.MessageId_GET_RECEIPTS_66, - ReceiptsMsg: sentryproto.MessageId_RECEIPTS_66, - NewBlockHashesMsg: sentryproto.MessageId_NEW_BLOCK_HASHES_66, - NewBlockMsg: sentryproto.MessageId_NEW_BLOCK_66, - TransactionsMsg: sentryproto.MessageId_TRANSACTIONS_66, - NewPooledTransactionHashesMsg: sentryproto.MessageId_NEW_POOLED_TRANSACTION_HASHES_68, // Modified in eth/68 - GetPooledTransactionsMsg: sentryproto.MessageId_GET_POOLED_TRANSACTIONS_66, - PooledTransactionsMsg: sentryproto.MessageId_POOLED_TRANSACTIONS_66, - }, - direct.ETH69: { - StatusMsg: sentryproto.MessageId_STATUS_69, - GetBlockHeadersMsg: sentryproto.MessageId_GET_BLOCK_HEADERS_66, - BlockHeadersMsg: sentryproto.MessageId_BLOCK_HEADERS_66, - GetBlockBodiesMsg: sentryproto.MessageId_GET_BLOCK_BODIES_66, - BlockBodiesMsg: sentryproto.MessageId_BLOCK_BODIES_66, - GetReceiptsMsg: sentryproto.MessageId_GET_RECEIPTS_69, // Modified in eth/69 - ReceiptsMsg: sentryproto.MessageId_RECEIPTS_66, - NewBlockHashesMsg: sentryproto.MessageId_NEW_BLOCK_HASHES_66, - NewBlockMsg: sentryproto.MessageId_NEW_BLOCK_66, - TransactionsMsg: sentryproto.MessageId_TRANSACTIONS_66, - NewPooledTransactionHashesMsg: sentryproto.MessageId_NEW_POOLED_TRANSACTION_HASHES_68, - GetPooledTransactionsMsg: sentryproto.MessageId_GET_POOLED_TRANSACTIONS_66, - PooledTransactionsMsg: sentryproto.MessageId_POOLED_TRANSACTIONS_66, - BlockRangeUpdateMsg: sentryproto.MessageId_BLOCK_RANGE_UPDATE_69, // Modified in eth/69 - }, - direct.ETH70: { - StatusMsg: sentryproto.MessageId_STATUS_69, - GetBlockHeadersMsg: sentryproto.MessageId_GET_BLOCK_HEADERS_66, - BlockHeadersMsg: sentryproto.MessageId_BLOCK_HEADERS_66, - GetBlockBodiesMsg: sentryproto.MessageId_GET_BLOCK_BODIES_66, - BlockBodiesMsg: sentryproto.MessageId_BLOCK_BODIES_66, - GetReceiptsMsg: sentryproto.MessageId_GET_RECEIPTS_70, // Modified in eth/70 - ReceiptsMsg: sentryproto.MessageId_RECEIPTS_70, // Modified in eth/70 - NewBlockHashesMsg: sentryproto.MessageId_NEW_BLOCK_HASHES_66, - NewBlockMsg: sentryproto.MessageId_NEW_BLOCK_66, - TransactionsMsg: sentryproto.MessageId_TRANSACTIONS_66, - NewPooledTransactionHashesMsg: sentryproto.MessageId_NEW_POOLED_TRANSACTION_HASHES_68, - GetPooledTransactionsMsg: sentryproto.MessageId_GET_POOLED_TRANSACTIONS_66, - PooledTransactionsMsg: sentryproto.MessageId_POOLED_TRANSACTIONS_66, - BlockRangeUpdateMsg: sentryproto.MessageId_BLOCK_RANGE_UPDATE_69, - }, - direct.ETH71: { - StatusMsg: sentryproto.MessageId_STATUS_69, - GetBlockHeadersMsg: sentryproto.MessageId_GET_BLOCK_HEADERS_66, - BlockHeadersMsg: sentryproto.MessageId_BLOCK_HEADERS_66, - GetBlockBodiesMsg: sentryproto.MessageId_GET_BLOCK_BODIES_66, - BlockBodiesMsg: sentryproto.MessageId_BLOCK_BODIES_66, - GetReceiptsMsg: sentryproto.MessageId_GET_RECEIPTS_70, - ReceiptsMsg: sentryproto.MessageId_RECEIPTS_70, - NewBlockHashesMsg: sentryproto.MessageId_NEW_BLOCK_HASHES_66, - NewBlockMsg: sentryproto.MessageId_NEW_BLOCK_66, - TransactionsMsg: sentryproto.MessageId_TRANSACTIONS_66, - NewPooledTransactionHashesMsg: sentryproto.MessageId_NEW_POOLED_TRANSACTION_HASHES_68, - GetPooledTransactionsMsg: sentryproto.MessageId_GET_POOLED_TRANSACTIONS_66, - PooledTransactionsMsg: sentryproto.MessageId_POOLED_TRANSACTIONS_66, - BlockRangeUpdateMsg: sentryproto.MessageId_BLOCK_RANGE_UPDATE_69, - // Added in eth/71 (EIP-8159 Block Access List Exchange) - GetBlockAccessListsMsg: sentryproto.MessageId_GET_BLOCK_ACCESS_LISTS_71, - BlockAccessListsMsg: sentryproto.MessageId_BLOCK_ACCESS_LISTS_71, - }, -} - -var FromProto = map[uint]map[sentryproto.MessageId]uint64{ - direct.ETH68: { - sentryproto.MessageId_GET_BLOCK_HEADERS_66: GetBlockHeadersMsg, - sentryproto.MessageId_BLOCK_HEADERS_66: BlockHeadersMsg, - sentryproto.MessageId_GET_BLOCK_BODIES_66: GetBlockBodiesMsg, - sentryproto.MessageId_BLOCK_BODIES_66: BlockBodiesMsg, - sentryproto.MessageId_GET_RECEIPTS_66: GetReceiptsMsg, - sentryproto.MessageId_RECEIPTS_66: ReceiptsMsg, - sentryproto.MessageId_NEW_BLOCK_HASHES_66: NewBlockHashesMsg, - sentryproto.MessageId_NEW_BLOCK_66: NewBlockMsg, - sentryproto.MessageId_TRANSACTIONS_66: TransactionsMsg, - sentryproto.MessageId_NEW_POOLED_TRANSACTION_HASHES_68: NewPooledTransactionHashesMsg, - sentryproto.MessageId_GET_POOLED_TRANSACTIONS_66: GetPooledTransactionsMsg, - sentryproto.MessageId_POOLED_TRANSACTIONS_66: PooledTransactionsMsg, - }, - direct.ETH69: { - sentryproto.MessageId_GET_BLOCK_HEADERS_66: GetBlockHeadersMsg, - sentryproto.MessageId_BLOCK_HEADERS_66: BlockHeadersMsg, - sentryproto.MessageId_GET_BLOCK_BODIES_66: GetBlockBodiesMsg, - sentryproto.MessageId_BLOCK_BODIES_66: BlockBodiesMsg, - sentryproto.MessageId_GET_RECEIPTS_69: GetReceiptsMsg, - sentryproto.MessageId_RECEIPTS_66: ReceiptsMsg, - sentryproto.MessageId_NEW_BLOCK_HASHES_66: NewBlockHashesMsg, - sentryproto.MessageId_NEW_BLOCK_66: NewBlockMsg, - sentryproto.MessageId_TRANSACTIONS_66: TransactionsMsg, - sentryproto.MessageId_NEW_POOLED_TRANSACTION_HASHES_68: NewPooledTransactionHashesMsg, - sentryproto.MessageId_GET_POOLED_TRANSACTIONS_66: GetPooledTransactionsMsg, - sentryproto.MessageId_POOLED_TRANSACTIONS_66: PooledTransactionsMsg, - sentryproto.MessageId_BLOCK_RANGE_UPDATE_69: BlockRangeUpdateMsg, - }, - direct.ETH70: { - sentryproto.MessageId_GET_BLOCK_HEADERS_66: GetBlockHeadersMsg, - sentryproto.MessageId_BLOCK_HEADERS_66: BlockHeadersMsg, - sentryproto.MessageId_GET_BLOCK_BODIES_66: GetBlockBodiesMsg, - sentryproto.MessageId_BLOCK_BODIES_66: BlockBodiesMsg, - sentryproto.MessageId_GET_RECEIPTS_70: GetReceiptsMsg, - sentryproto.MessageId_RECEIPTS_70: ReceiptsMsg, - sentryproto.MessageId_NEW_BLOCK_HASHES_66: NewBlockHashesMsg, - sentryproto.MessageId_NEW_BLOCK_66: NewBlockMsg, - sentryproto.MessageId_TRANSACTIONS_66: TransactionsMsg, - sentryproto.MessageId_NEW_POOLED_TRANSACTION_HASHES_68: NewPooledTransactionHashesMsg, - sentryproto.MessageId_GET_POOLED_TRANSACTIONS_66: GetPooledTransactionsMsg, - sentryproto.MessageId_POOLED_TRANSACTIONS_66: PooledTransactionsMsg, - sentryproto.MessageId_BLOCK_RANGE_UPDATE_69: BlockRangeUpdateMsg, - }, - direct.ETH71: { - sentryproto.MessageId_GET_BLOCK_HEADERS_66: GetBlockHeadersMsg, - sentryproto.MessageId_BLOCK_HEADERS_66: BlockHeadersMsg, - sentryproto.MessageId_GET_BLOCK_BODIES_66: GetBlockBodiesMsg, - sentryproto.MessageId_BLOCK_BODIES_66: BlockBodiesMsg, - sentryproto.MessageId_GET_RECEIPTS_70: GetReceiptsMsg, - sentryproto.MessageId_RECEIPTS_70: ReceiptsMsg, - sentryproto.MessageId_NEW_BLOCK_HASHES_66: NewBlockHashesMsg, - sentryproto.MessageId_NEW_BLOCK_66: NewBlockMsg, - sentryproto.MessageId_TRANSACTIONS_66: TransactionsMsg, - sentryproto.MessageId_NEW_POOLED_TRANSACTION_HASHES_68: NewPooledTransactionHashesMsg, - sentryproto.MessageId_GET_POOLED_TRANSACTIONS_66: GetPooledTransactionsMsg, - sentryproto.MessageId_POOLED_TRANSACTIONS_66: PooledTransactionsMsg, - sentryproto.MessageId_BLOCK_RANGE_UPDATE_69: BlockRangeUpdateMsg, - // Added in eth/71 (EIP-8159 Block Access List Exchange) - sentryproto.MessageId_GET_BLOCK_ACCESS_LISTS_71: GetBlockAccessListsMsg, - sentryproto.MessageId_BLOCK_ACCESS_LISTS_71: BlockAccessListsMsg, - }, + ETH68: toProto68, + ETH69: toProto69, + ETH70: toProto70, + ETH71: toProto71, +} + +var FromProto = inverseWithoutStatus(ToProto) + +func withDelta(prev, changes map[uint64]sentryproto.MessageId) map[uint64]sentryproto.MessageId { + next := maps.Clone(prev) + maps.Copy(next, changes) + return next +} + +// Status is handshake-only: FromProto omits it so that SendMessageById can +// never emit a status frame. +func inverseWithoutStatus(toProto map[uint]map[uint64]sentryproto.MessageId) map[uint]map[sentryproto.MessageId]uint64 { + fromProto := make(map[uint]map[sentryproto.MessageId]uint64, len(toProto)) + for version, codes := range toProto { + inv := make(map[sentryproto.MessageId]uint64, len(codes)) + for code, id := range codes { + if code == StatusMsg { + continue + } + if _, ok := inv[id]; ok { + panic(fmt.Sprintf("eth/%d: message id %s mapped from multiple message codes", version, id)) + } + inv[id] = code + } + fromProto[version] = inv + } + return fromProto } // Packet represents a p2p message in the `eth` protocol. diff --git a/p2p/protocols/eth/protocol_msgid_golden_test.go b/p2p/protocols/eth/protocol_msgid_golden_test.go new file mode 100644 index 00000000000..0be6c65990b --- /dev/null +++ b/p2p/protocols/eth/protocol_msgid_golden_test.go @@ -0,0 +1,191 @@ +// Copyright 2026 The Erigon Authors +// This file is part of Erigon. +// +// Erigon is free software: you can redistribute it and/or modify +// it under the terms of the GNU Lesser General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// Erigon is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU Lesser General Public License for more details. +// +// You should have received a copy of the GNU Lesser General Public License +// along with Erigon. If not, see . + +package eth_test + +import ( + "testing" + + "github.com/stretchr/testify/require" + + "github.com/erigontech/erigon/node/gointerfaces/sentryproto" + "github.com/erigontech/erigon/p2p/protocols/eth" +) + +var goldenToProto = map[uint]map[uint64]sentryproto.MessageId{ + 68: { + eth.GetBlockHeadersMsg: sentryproto.MessageId_GET_BLOCK_HEADERS_66, + eth.BlockHeadersMsg: sentryproto.MessageId_BLOCK_HEADERS_66, + eth.GetBlockBodiesMsg: sentryproto.MessageId_GET_BLOCK_BODIES_66, + eth.BlockBodiesMsg: sentryproto.MessageId_BLOCK_BODIES_66, + eth.GetReceiptsMsg: sentryproto.MessageId_GET_RECEIPTS_66, + eth.ReceiptsMsg: sentryproto.MessageId_RECEIPTS_66, + eth.NewBlockHashesMsg: sentryproto.MessageId_NEW_BLOCK_HASHES_66, + eth.NewBlockMsg: sentryproto.MessageId_NEW_BLOCK_66, + eth.TransactionsMsg: sentryproto.MessageId_TRANSACTIONS_66, + eth.NewPooledTransactionHashesMsg: sentryproto.MessageId_NEW_POOLED_TRANSACTION_HASHES_68, + eth.GetPooledTransactionsMsg: sentryproto.MessageId_GET_POOLED_TRANSACTIONS_66, + eth.PooledTransactionsMsg: sentryproto.MessageId_POOLED_TRANSACTIONS_66, + }, + 69: { + eth.StatusMsg: sentryproto.MessageId_STATUS_69, + eth.GetBlockHeadersMsg: sentryproto.MessageId_GET_BLOCK_HEADERS_66, + eth.BlockHeadersMsg: sentryproto.MessageId_BLOCK_HEADERS_66, + eth.GetBlockBodiesMsg: sentryproto.MessageId_GET_BLOCK_BODIES_66, + eth.BlockBodiesMsg: sentryproto.MessageId_BLOCK_BODIES_66, + eth.GetReceiptsMsg: sentryproto.MessageId_GET_RECEIPTS_69, + eth.ReceiptsMsg: sentryproto.MessageId_RECEIPTS_66, + eth.NewBlockHashesMsg: sentryproto.MessageId_NEW_BLOCK_HASHES_66, + eth.NewBlockMsg: sentryproto.MessageId_NEW_BLOCK_66, + eth.TransactionsMsg: sentryproto.MessageId_TRANSACTIONS_66, + eth.NewPooledTransactionHashesMsg: sentryproto.MessageId_NEW_POOLED_TRANSACTION_HASHES_68, + eth.GetPooledTransactionsMsg: sentryproto.MessageId_GET_POOLED_TRANSACTIONS_66, + eth.PooledTransactionsMsg: sentryproto.MessageId_POOLED_TRANSACTIONS_66, + eth.BlockRangeUpdateMsg: sentryproto.MessageId_BLOCK_RANGE_UPDATE_69, + }, + 70: { + eth.StatusMsg: sentryproto.MessageId_STATUS_69, + eth.GetBlockHeadersMsg: sentryproto.MessageId_GET_BLOCK_HEADERS_66, + eth.BlockHeadersMsg: sentryproto.MessageId_BLOCK_HEADERS_66, + eth.GetBlockBodiesMsg: sentryproto.MessageId_GET_BLOCK_BODIES_66, + eth.BlockBodiesMsg: sentryproto.MessageId_BLOCK_BODIES_66, + eth.GetReceiptsMsg: sentryproto.MessageId_GET_RECEIPTS_70, + eth.ReceiptsMsg: sentryproto.MessageId_RECEIPTS_70, + eth.NewBlockHashesMsg: sentryproto.MessageId_NEW_BLOCK_HASHES_66, + eth.NewBlockMsg: sentryproto.MessageId_NEW_BLOCK_66, + eth.TransactionsMsg: sentryproto.MessageId_TRANSACTIONS_66, + eth.NewPooledTransactionHashesMsg: sentryproto.MessageId_NEW_POOLED_TRANSACTION_HASHES_68, + eth.GetPooledTransactionsMsg: sentryproto.MessageId_GET_POOLED_TRANSACTIONS_66, + eth.PooledTransactionsMsg: sentryproto.MessageId_POOLED_TRANSACTIONS_66, + eth.BlockRangeUpdateMsg: sentryproto.MessageId_BLOCK_RANGE_UPDATE_69, + }, + 71: { + eth.StatusMsg: sentryproto.MessageId_STATUS_69, + eth.GetBlockHeadersMsg: sentryproto.MessageId_GET_BLOCK_HEADERS_66, + eth.BlockHeadersMsg: sentryproto.MessageId_BLOCK_HEADERS_66, + eth.GetBlockBodiesMsg: sentryproto.MessageId_GET_BLOCK_BODIES_66, + eth.BlockBodiesMsg: sentryproto.MessageId_BLOCK_BODIES_66, + eth.GetReceiptsMsg: sentryproto.MessageId_GET_RECEIPTS_70, + eth.ReceiptsMsg: sentryproto.MessageId_RECEIPTS_70, + eth.NewBlockHashesMsg: sentryproto.MessageId_NEW_BLOCK_HASHES_66, + eth.NewBlockMsg: sentryproto.MessageId_NEW_BLOCK_66, + eth.TransactionsMsg: sentryproto.MessageId_TRANSACTIONS_66, + eth.NewPooledTransactionHashesMsg: sentryproto.MessageId_NEW_POOLED_TRANSACTION_HASHES_68, + eth.GetPooledTransactionsMsg: sentryproto.MessageId_GET_POOLED_TRANSACTIONS_66, + eth.PooledTransactionsMsg: sentryproto.MessageId_POOLED_TRANSACTIONS_66, + eth.BlockRangeUpdateMsg: sentryproto.MessageId_BLOCK_RANGE_UPDATE_69, + eth.GetBlockAccessListsMsg: sentryproto.MessageId_GET_BLOCK_ACCESS_LISTS_71, + eth.BlockAccessListsMsg: sentryproto.MessageId_BLOCK_ACCESS_LISTS_71, + }, +} + +var goldenFromProto = map[uint]map[sentryproto.MessageId]uint64{ + 68: { + sentryproto.MessageId_GET_BLOCK_HEADERS_66: eth.GetBlockHeadersMsg, + sentryproto.MessageId_BLOCK_HEADERS_66: eth.BlockHeadersMsg, + sentryproto.MessageId_GET_BLOCK_BODIES_66: eth.GetBlockBodiesMsg, + sentryproto.MessageId_BLOCK_BODIES_66: eth.BlockBodiesMsg, + sentryproto.MessageId_GET_RECEIPTS_66: eth.GetReceiptsMsg, + sentryproto.MessageId_RECEIPTS_66: eth.ReceiptsMsg, + sentryproto.MessageId_NEW_BLOCK_HASHES_66: eth.NewBlockHashesMsg, + sentryproto.MessageId_NEW_BLOCK_66: eth.NewBlockMsg, + sentryproto.MessageId_TRANSACTIONS_66: eth.TransactionsMsg, + sentryproto.MessageId_NEW_POOLED_TRANSACTION_HASHES_68: eth.NewPooledTransactionHashesMsg, + sentryproto.MessageId_GET_POOLED_TRANSACTIONS_66: eth.GetPooledTransactionsMsg, + sentryproto.MessageId_POOLED_TRANSACTIONS_66: eth.PooledTransactionsMsg, + }, + 69: { + sentryproto.MessageId_GET_BLOCK_HEADERS_66: eth.GetBlockHeadersMsg, + sentryproto.MessageId_BLOCK_HEADERS_66: eth.BlockHeadersMsg, + sentryproto.MessageId_GET_BLOCK_BODIES_66: eth.GetBlockBodiesMsg, + sentryproto.MessageId_BLOCK_BODIES_66: eth.BlockBodiesMsg, + sentryproto.MessageId_GET_RECEIPTS_69: eth.GetReceiptsMsg, + sentryproto.MessageId_RECEIPTS_66: eth.ReceiptsMsg, + sentryproto.MessageId_NEW_BLOCK_HASHES_66: eth.NewBlockHashesMsg, + sentryproto.MessageId_NEW_BLOCK_66: eth.NewBlockMsg, + sentryproto.MessageId_TRANSACTIONS_66: eth.TransactionsMsg, + sentryproto.MessageId_NEW_POOLED_TRANSACTION_HASHES_68: eth.NewPooledTransactionHashesMsg, + sentryproto.MessageId_GET_POOLED_TRANSACTIONS_66: eth.GetPooledTransactionsMsg, + sentryproto.MessageId_POOLED_TRANSACTIONS_66: eth.PooledTransactionsMsg, + sentryproto.MessageId_BLOCK_RANGE_UPDATE_69: eth.BlockRangeUpdateMsg, + }, + 70: { + sentryproto.MessageId_GET_BLOCK_HEADERS_66: eth.GetBlockHeadersMsg, + sentryproto.MessageId_BLOCK_HEADERS_66: eth.BlockHeadersMsg, + sentryproto.MessageId_GET_BLOCK_BODIES_66: eth.GetBlockBodiesMsg, + sentryproto.MessageId_BLOCK_BODIES_66: eth.BlockBodiesMsg, + sentryproto.MessageId_GET_RECEIPTS_70: eth.GetReceiptsMsg, + sentryproto.MessageId_RECEIPTS_70: eth.ReceiptsMsg, + sentryproto.MessageId_NEW_BLOCK_HASHES_66: eth.NewBlockHashesMsg, + sentryproto.MessageId_NEW_BLOCK_66: eth.NewBlockMsg, + sentryproto.MessageId_TRANSACTIONS_66: eth.TransactionsMsg, + sentryproto.MessageId_NEW_POOLED_TRANSACTION_HASHES_68: eth.NewPooledTransactionHashesMsg, + sentryproto.MessageId_GET_POOLED_TRANSACTIONS_66: eth.GetPooledTransactionsMsg, + sentryproto.MessageId_POOLED_TRANSACTIONS_66: eth.PooledTransactionsMsg, + sentryproto.MessageId_BLOCK_RANGE_UPDATE_69: eth.BlockRangeUpdateMsg, + }, + 71: { + sentryproto.MessageId_GET_BLOCK_HEADERS_66: eth.GetBlockHeadersMsg, + sentryproto.MessageId_BLOCK_HEADERS_66: eth.BlockHeadersMsg, + sentryproto.MessageId_GET_BLOCK_BODIES_66: eth.GetBlockBodiesMsg, + sentryproto.MessageId_BLOCK_BODIES_66: eth.BlockBodiesMsg, + sentryproto.MessageId_GET_RECEIPTS_70: eth.GetReceiptsMsg, + sentryproto.MessageId_RECEIPTS_70: eth.ReceiptsMsg, + sentryproto.MessageId_NEW_BLOCK_HASHES_66: eth.NewBlockHashesMsg, + sentryproto.MessageId_NEW_BLOCK_66: eth.NewBlockMsg, + sentryproto.MessageId_TRANSACTIONS_66: eth.TransactionsMsg, + sentryproto.MessageId_NEW_POOLED_TRANSACTION_HASHES_68: eth.NewPooledTransactionHashesMsg, + sentryproto.MessageId_GET_POOLED_TRANSACTIONS_66: eth.GetPooledTransactionsMsg, + sentryproto.MessageId_POOLED_TRANSACTIONS_66: eth.PooledTransactionsMsg, + sentryproto.MessageId_BLOCK_RANGE_UPDATE_69: eth.BlockRangeUpdateMsg, + sentryproto.MessageId_GET_BLOCK_ACCESS_LISTS_71: eth.GetBlockAccessListsMsg, + sentryproto.MessageId_BLOCK_ACCESS_LISTS_71: eth.BlockAccessListsMsg, + }, +} + +func TestToProtoGolden(t *testing.T) { + require.Equal(t, goldenToProto, eth.ToProto) +} + +func TestFromProtoGolden(t *testing.T) { + require.Equal(t, goldenFromProto, eth.FromProto) +} + +// FromProto deliberately omits the status ids so that SendMessageById can +// never emit a status frame; status is exchanged only during the handshake. +func TestFromProtoOmitsStatus(t *testing.T) { + omitted := make(map[uint]map[sentryproto.MessageId]struct{}) + for version, toProto := range goldenToProto { + omitted[version] = make(map[sentryproto.MessageId]struct{}) + for _, id := range toProto { + if _, ok := goldenFromProto[version][id]; !ok { + omitted[version][id] = struct{}{} + } + } + } + + statusOnly := map[sentryproto.MessageId]struct{}{sentryproto.MessageId_STATUS_69: {}} + require.Equal(t, map[uint]map[sentryproto.MessageId]struct{}{ + 68: {}, + 69: statusOnly, + 70: statusOnly, + 71: statusOnly, + }, omitted) + + for _, version := range []uint{69, 70, 71} { + require.NotContains(t, eth.FromProto[version], sentryproto.MessageId_STATUS_69) + } +} diff --git a/p2p/protocols/eth/protocol_test.go b/p2p/protocols/eth/protocol_test.go index 9d462fa3512..3724b5c718f 100644 --- a/p2p/protocols/eth/protocol_test.go +++ b/p2p/protocols/eth/protocol_test.go @@ -28,7 +28,6 @@ import ( "github.com/erigontech/erigon/common" "github.com/erigontech/erigon/execution/rlp" "github.com/erigontech/erigon/execution/types" - "github.com/erigontech/erigon/node/direct" "github.com/erigontech/erigon/node/gointerfaces/sentryproto" ) @@ -330,14 +329,14 @@ func TestBlockAccessListsPacket66RoundTrip(t *testing.T) { // the protocol name/length tables and that the two new message codes route to // their sentry MessageId counterparts via ToProto/FromProto. func TestEth71ProtocolRegistration(t *testing.T) { - if name, ok := ProtocolToString[direct.ETH71]; !ok || name != "eth71" { + if name, ok := ProtocolToString[ETH71]; !ok || name != "eth71" { t.Fatalf("ProtocolToString[ETH71] = (%q, %v), want (eth71, true)", name, ok) } - if length, ok := ProtocolLengths[direct.ETH71]; !ok || length != 20 { + if length, ok := ProtocolLengths[ETH71]; !ok || length != 20 { t.Fatalf("ProtocolLengths[ETH71] = (%d, %v), want (20, true)", length, ok) } - fwd := ToProto[direct.ETH71] + fwd := ToProto[ETH71] if fwd == nil { t.Fatal("ToProto has no ETH71 entry") } @@ -348,7 +347,7 @@ func TestEth71ProtocolRegistration(t *testing.T) { t.Errorf("ToProto[ETH71][BlockAccessListsMsg] = %v, want BLOCK_ACCESS_LISTS_71", got) } - rev := FromProto[direct.ETH71] + rev := FromProto[ETH71] if rev == nil { t.Fatal("FromProto has no ETH71 entry") } diff --git a/p2p/protocols/wit/protocol.go b/p2p/protocols/wit/protocol.go index aa2e8745382..a59f6c0e91b 100644 --- a/p2p/protocols/wit/protocol.go +++ b/p2p/protocols/wit/protocol.go @@ -2,15 +2,15 @@ package wit import ( "errors" + "fmt" "github.com/erigontech/erigon/common" "github.com/erigontech/erigon/execution/types/stateless" - "github.com/erigontech/erigon/node/direct" "github.com/erigontech/erigon/node/gointerfaces/sentryproto" ) var ProtocolToString = map[uint]string{ - direct.WIT0: "wit0", + WIT1: "wit0", } // Constants to match up protocol versions and messages @@ -128,7 +128,7 @@ func (w *NewWitnessHashesPacket) Name() string { return "NewWitnessHashes" } func (w *NewWitnessHashesPacket) Kind() byte { return NewWitnessHashesMsg } var ToProto = map[uint]map[uint64]sentryproto.MessageId{ - direct.WIT0: { + WIT1: { NewWitnessMsg: sentryproto.MessageId_NEW_WITNESS_W0, NewWitnessHashesMsg: sentryproto.MessageId_NEW_WITNESS_HASHES_W0, GetWitnessMsg: sentryproto.MessageId_GET_BLOCK_WITNESS_W0, @@ -136,11 +136,19 @@ var ToProto = map[uint]map[uint64]sentryproto.MessageId{ }, } -var FromProto = map[uint]map[sentryproto.MessageId]uint64{ - direct.WIT0: { - sentryproto.MessageId_NEW_WITNESS_W0: NewWitnessMsg, - sentryproto.MessageId_NEW_WITNESS_HASHES_W0: NewWitnessHashesMsg, - sentryproto.MessageId_GET_BLOCK_WITNESS_W0: GetWitnessMsg, - sentryproto.MessageId_BLOCK_WITNESS_W0: WitnessMsg, - }, +var FromProto = inverse(ToProto) + +func inverse(toProto map[uint]map[uint64]sentryproto.MessageId) map[uint]map[sentryproto.MessageId]uint64 { + fromProto := make(map[uint]map[sentryproto.MessageId]uint64, len(toProto)) + for version, codes := range toProto { + inv := make(map[sentryproto.MessageId]uint64, len(codes)) + for code, id := range codes { + if _, ok := inv[id]; ok { + panic(fmt.Sprintf("wit/%d: message id %s mapped from multiple message codes", version, id)) + } + inv[id] = code + } + fromProto[version] = inv + } + return fromProto } diff --git a/p2p/protocols/wit/protocol_msgid_golden_test.go b/p2p/protocols/wit/protocol_msgid_golden_test.go new file mode 100644 index 00000000000..ccd3e5b035e --- /dev/null +++ b/p2p/protocols/wit/protocol_msgid_golden_test.go @@ -0,0 +1,36 @@ +package wit_test + +import ( + "testing" + + "github.com/stretchr/testify/require" + + "github.com/erigontech/erigon/node/gointerfaces/sentryproto" + "github.com/erigontech/erigon/p2p/protocols/wit" +) + +var goldenToProto = map[uint]map[uint64]sentryproto.MessageId{ + 1: { + wit.NewWitnessMsg: sentryproto.MessageId_NEW_WITNESS_W0, + wit.NewWitnessHashesMsg: sentryproto.MessageId_NEW_WITNESS_HASHES_W0, + wit.GetWitnessMsg: sentryproto.MessageId_GET_BLOCK_WITNESS_W0, + wit.WitnessMsg: sentryproto.MessageId_BLOCK_WITNESS_W0, + }, +} + +var goldenFromProto = map[uint]map[sentryproto.MessageId]uint64{ + 1: { + sentryproto.MessageId_NEW_WITNESS_W0: wit.NewWitnessMsg, + sentryproto.MessageId_NEW_WITNESS_HASHES_W0: wit.NewWitnessHashesMsg, + sentryproto.MessageId_GET_BLOCK_WITNESS_W0: wit.GetWitnessMsg, + sentryproto.MessageId_BLOCK_WITNESS_W0: wit.WitnessMsg, + }, +} + +func TestToProtoGolden(t *testing.T) { + require.Equal(t, goldenToProto, wit.ToProto) +} + +func TestFromProtoGolden(t *testing.T) { + require.Equal(t, goldenFromProto, wit.FromProto) +} diff --git a/p2p/sentry/libsentry/protocol.go b/p2p/sentry/libsentry/protocol.go index ef603b6565b..854f6a4af44 100644 --- a/p2p/sentry/libsentry/protocol.go +++ b/p2p/sentry/libsentry/protocol.go @@ -17,17 +17,53 @@ package libsentry import ( + "fmt" + "maps" + "slices" + "github.com/erigontech/erigon/node/gointerfaces/sentryproto" + "github.com/erigontech/erigon/p2p/protocols/eth" + "github.com/erigontech/erigon/p2p/protocols/wit" +) + +var ( + UintToProtocolMap = map[uint]sentryproto.Protocol{ + eth.ETH68: sentryproto.Protocol_ETH68, + eth.ETH69: sentryproto.Protocol_ETH69, + eth.ETH70: sentryproto.Protocol_ETH70, + eth.ETH71: sentryproto.Protocol_ETH71, + } + ProtocolToUintMap = inverseProtocolMap(UintToProtocolMap) + + UintToSideProtocolMap = map[uint]sentryproto.Protocol{ + wit.WIT1: sentryproto.Protocol_WIT0, + } + SupportedSideProtocols = map[sentryproto.Protocol]struct{}{ + sentryproto.Protocol_WIT0: {}, + } ) +func inverseProtocolMap(uintToProtocol map[uint]sentryproto.Protocol) map[sentryproto.Protocol]uint { + inv := make(map[sentryproto.Protocol]uint, len(uintToProtocol)) + for version, protocol := range uintToProtocol { + if _, ok := inv[protocol]; ok { + panic(fmt.Sprintf("protocol %s mapped from multiple versions", protocol)) + } + inv[protocol] = version + } + return inv +} + // ethProtocolsByVersion lists ETH protocols in ascending version order. // Used by MinProtocol to find the lowest version supporting a message. -var ethProtocolsByVersion = []sentryproto.Protocol{ - sentryproto.Protocol_ETH68, - sentryproto.Protocol_ETH69, - sentryproto.Protocol_ETH70, - sentryproto.Protocol_ETH71, -} +var ethProtocolsByVersion = func() []sentryproto.Protocol { + versions := slices.Sorted(maps.Keys(UintToProtocolMap)) + protocols := make([]sentryproto.Protocol, len(versions)) + for i, version := range versions { + protocols[i] = UintToProtocolMap[version] + } + return protocols +}() func MinProtocol(m sentryproto.MessageId) sentryproto.Protocol { for _, p := range ethProtocolsByVersion { @@ -41,73 +77,29 @@ func MinProtocol(m sentryproto.MessageId) sentryproto.Protocol { return -1 } -var ProtoIds = map[sentryproto.Protocol]map[sentryproto.MessageId]struct{}{ - sentryproto.Protocol_ETH68: { - sentryproto.MessageId_GET_BLOCK_HEADERS_66: struct{}{}, - sentryproto.MessageId_BLOCK_HEADERS_66: struct{}{}, - sentryproto.MessageId_GET_BLOCK_BODIES_66: struct{}{}, - sentryproto.MessageId_BLOCK_BODIES_66: struct{}{}, - sentryproto.MessageId_GET_RECEIPTS_66: struct{}{}, - sentryproto.MessageId_RECEIPTS_66: struct{}{}, - sentryproto.MessageId_NEW_BLOCK_HASHES_66: struct{}{}, - sentryproto.MessageId_NEW_BLOCK_66: struct{}{}, - sentryproto.MessageId_TRANSACTIONS_66: struct{}{}, - sentryproto.MessageId_NEW_POOLED_TRANSACTION_HASHES_68: struct{}{}, - sentryproto.MessageId_GET_POOLED_TRANSACTIONS_66: struct{}{}, - sentryproto.MessageId_POOLED_TRANSACTIONS_66: struct{}{}, - }, - sentryproto.Protocol_WIT0: { - sentryproto.MessageId_GET_BLOCK_WITNESS_W0: struct{}{}, - sentryproto.MessageId_BLOCK_WITNESS_W0: struct{}{}, - sentryproto.MessageId_NEW_WITNESS_W0: struct{}{}, - sentryproto.MessageId_NEW_WITNESS_HASHES_W0: struct{}{}, - }, - sentryproto.Protocol_ETH69: { - sentryproto.MessageId_GET_BLOCK_HEADERS_66: struct{}{}, - sentryproto.MessageId_BLOCK_HEADERS_66: struct{}{}, - sentryproto.MessageId_GET_BLOCK_BODIES_66: struct{}{}, - sentryproto.MessageId_BLOCK_BODIES_66: struct{}{}, - sentryproto.MessageId_GET_RECEIPTS_69: struct{}{}, - sentryproto.MessageId_RECEIPTS_66: struct{}{}, - sentryproto.MessageId_NEW_BLOCK_HASHES_66: struct{}{}, - sentryproto.MessageId_NEW_BLOCK_66: struct{}{}, - sentryproto.MessageId_TRANSACTIONS_66: struct{}{}, - sentryproto.MessageId_NEW_POOLED_TRANSACTION_HASHES_68: struct{}{}, - sentryproto.MessageId_GET_POOLED_TRANSACTIONS_66: struct{}{}, - sentryproto.MessageId_POOLED_TRANSACTIONS_66: struct{}{}, - sentryproto.MessageId_BLOCK_RANGE_UPDATE_69: struct{}{}, - }, - sentryproto.Protocol_ETH70: { - sentryproto.MessageId_GET_BLOCK_HEADERS_66: struct{}{}, - sentryproto.MessageId_BLOCK_HEADERS_66: struct{}{}, - sentryproto.MessageId_GET_BLOCK_BODIES_66: struct{}{}, - sentryproto.MessageId_BLOCK_BODIES_66: struct{}{}, - sentryproto.MessageId_GET_RECEIPTS_70: struct{}{}, - sentryproto.MessageId_RECEIPTS_70: struct{}{}, - sentryproto.MessageId_NEW_BLOCK_HASHES_66: struct{}{}, - sentryproto.MessageId_NEW_BLOCK_66: struct{}{}, - sentryproto.MessageId_TRANSACTIONS_66: struct{}{}, - sentryproto.MessageId_NEW_POOLED_TRANSACTION_HASHES_68: struct{}{}, - sentryproto.MessageId_GET_POOLED_TRANSACTIONS_66: struct{}{}, - sentryproto.MessageId_POOLED_TRANSACTIONS_66: struct{}{}, - sentryproto.MessageId_BLOCK_RANGE_UPDATE_69: struct{}{}, - }, - sentryproto.Protocol_ETH71: { - sentryproto.MessageId_GET_BLOCK_HEADERS_66: struct{}{}, - sentryproto.MessageId_BLOCK_HEADERS_66: struct{}{}, - sentryproto.MessageId_GET_BLOCK_BODIES_66: struct{}{}, - sentryproto.MessageId_BLOCK_BODIES_66: struct{}{}, - sentryproto.MessageId_GET_RECEIPTS_70: struct{}{}, - sentryproto.MessageId_RECEIPTS_70: struct{}{}, - sentryproto.MessageId_NEW_BLOCK_HASHES_66: struct{}{}, - sentryproto.MessageId_NEW_BLOCK_66: struct{}{}, - sentryproto.MessageId_TRANSACTIONS_66: struct{}{}, - sentryproto.MessageId_NEW_POOLED_TRANSACTION_HASHES_68: struct{}{}, - sentryproto.MessageId_GET_POOLED_TRANSACTIONS_66: struct{}{}, - sentryproto.MessageId_POOLED_TRANSACTIONS_66: struct{}{}, - sentryproto.MessageId_BLOCK_RANGE_UPDATE_69: struct{}{}, - // Added in eth/71 (EIP-8159 Block Access List Exchange) - sentryproto.MessageId_GET_BLOCK_ACCESS_LISTS_71: struct{}{}, - sentryproto.MessageId_BLOCK_ACCESS_LISTS_71: struct{}{}, - }, +var ProtoIds = func() map[sentryproto.Protocol]map[sentryproto.MessageId]struct{} { + ids := make(map[sentryproto.Protocol]map[sentryproto.MessageId]struct{}, len(eth.FromProto)+len(wit.FromProto)) + for version, fromProto := range eth.FromProto { + ids[protocolOf(UintToProtocolMap, version)] = messageIdSet(fromProto) + } + for version, fromProto := range wit.FromProto { + ids[protocolOf(UintToSideProtocolMap, version)] = messageIdSet(fromProto) + } + return ids +}() + +func protocolOf(uintToProtocol map[uint]sentryproto.Protocol, version uint) sentryproto.Protocol { + protocol, ok := uintToProtocol[version] + if !ok { + panic(fmt.Sprintf("no sentry protocol registered for version %d", version)) + } + return protocol +} + +func messageIdSet(fromProto map[sentryproto.MessageId]uint64) map[sentryproto.MessageId]struct{} { + set := make(map[sentryproto.MessageId]struct{}, len(fromProto)) + for id := range fromProto { + set[id] = struct{}{} + } + return set } diff --git a/p2p/sentry/libsentry/protocol_msgid_golden_test.go b/p2p/sentry/libsentry/protocol_msgid_golden_test.go new file mode 100644 index 00000000000..db6e1329bc4 --- /dev/null +++ b/p2p/sentry/libsentry/protocol_msgid_golden_test.go @@ -0,0 +1,100 @@ +// Copyright 2026 The Erigon Authors +// This file is part of Erigon. +// +// Erigon is free software: you can redistribute it and/or modify +// it under the terms of the GNU Lesser General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// Erigon is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU Lesser General Public License for more details. +// +// You should have received a copy of the GNU Lesser General Public License +// along with Erigon. If not, see . + +package libsentry_test + +import ( + "testing" + + "github.com/stretchr/testify/require" + + "github.com/erigontech/erigon/node/gointerfaces/sentryproto" + "github.com/erigontech/erigon/p2p/sentry/libsentry" +) + +var goldenProtoIds = map[sentryproto.Protocol]map[sentryproto.MessageId]struct{}{ + sentryproto.Protocol_ETH68: { + sentryproto.MessageId_GET_BLOCK_HEADERS_66: struct{}{}, + sentryproto.MessageId_BLOCK_HEADERS_66: struct{}{}, + sentryproto.MessageId_GET_BLOCK_BODIES_66: struct{}{}, + sentryproto.MessageId_BLOCK_BODIES_66: struct{}{}, + sentryproto.MessageId_GET_RECEIPTS_66: struct{}{}, + sentryproto.MessageId_RECEIPTS_66: struct{}{}, + sentryproto.MessageId_NEW_BLOCK_HASHES_66: struct{}{}, + sentryproto.MessageId_NEW_BLOCK_66: struct{}{}, + sentryproto.MessageId_TRANSACTIONS_66: struct{}{}, + sentryproto.MessageId_NEW_POOLED_TRANSACTION_HASHES_68: struct{}{}, + sentryproto.MessageId_GET_POOLED_TRANSACTIONS_66: struct{}{}, + sentryproto.MessageId_POOLED_TRANSACTIONS_66: struct{}{}, + }, + sentryproto.Protocol_WIT0: { + sentryproto.MessageId_GET_BLOCK_WITNESS_W0: struct{}{}, + sentryproto.MessageId_BLOCK_WITNESS_W0: struct{}{}, + sentryproto.MessageId_NEW_WITNESS_W0: struct{}{}, + sentryproto.MessageId_NEW_WITNESS_HASHES_W0: struct{}{}, + }, + sentryproto.Protocol_ETH69: { + sentryproto.MessageId_GET_BLOCK_HEADERS_66: struct{}{}, + sentryproto.MessageId_BLOCK_HEADERS_66: struct{}{}, + sentryproto.MessageId_GET_BLOCK_BODIES_66: struct{}{}, + sentryproto.MessageId_BLOCK_BODIES_66: struct{}{}, + sentryproto.MessageId_GET_RECEIPTS_69: struct{}{}, + sentryproto.MessageId_RECEIPTS_66: struct{}{}, + sentryproto.MessageId_NEW_BLOCK_HASHES_66: struct{}{}, + sentryproto.MessageId_NEW_BLOCK_66: struct{}{}, + sentryproto.MessageId_TRANSACTIONS_66: struct{}{}, + sentryproto.MessageId_NEW_POOLED_TRANSACTION_HASHES_68: struct{}{}, + sentryproto.MessageId_GET_POOLED_TRANSACTIONS_66: struct{}{}, + sentryproto.MessageId_POOLED_TRANSACTIONS_66: struct{}{}, + sentryproto.MessageId_BLOCK_RANGE_UPDATE_69: struct{}{}, + }, + sentryproto.Protocol_ETH70: { + sentryproto.MessageId_GET_BLOCK_HEADERS_66: struct{}{}, + sentryproto.MessageId_BLOCK_HEADERS_66: struct{}{}, + sentryproto.MessageId_GET_BLOCK_BODIES_66: struct{}{}, + sentryproto.MessageId_BLOCK_BODIES_66: struct{}{}, + sentryproto.MessageId_GET_RECEIPTS_70: struct{}{}, + sentryproto.MessageId_RECEIPTS_70: struct{}{}, + sentryproto.MessageId_NEW_BLOCK_HASHES_66: struct{}{}, + sentryproto.MessageId_NEW_BLOCK_66: struct{}{}, + sentryproto.MessageId_TRANSACTIONS_66: struct{}{}, + sentryproto.MessageId_NEW_POOLED_TRANSACTION_HASHES_68: struct{}{}, + sentryproto.MessageId_GET_POOLED_TRANSACTIONS_66: struct{}{}, + sentryproto.MessageId_POOLED_TRANSACTIONS_66: struct{}{}, + sentryproto.MessageId_BLOCK_RANGE_UPDATE_69: struct{}{}, + }, + sentryproto.Protocol_ETH71: { + sentryproto.MessageId_GET_BLOCK_HEADERS_66: struct{}{}, + sentryproto.MessageId_BLOCK_HEADERS_66: struct{}{}, + sentryproto.MessageId_GET_BLOCK_BODIES_66: struct{}{}, + sentryproto.MessageId_BLOCK_BODIES_66: struct{}{}, + sentryproto.MessageId_GET_RECEIPTS_70: struct{}{}, + sentryproto.MessageId_RECEIPTS_70: struct{}{}, + sentryproto.MessageId_NEW_BLOCK_HASHES_66: struct{}{}, + sentryproto.MessageId_NEW_BLOCK_66: struct{}{}, + sentryproto.MessageId_TRANSACTIONS_66: struct{}{}, + sentryproto.MessageId_NEW_POOLED_TRANSACTION_HASHES_68: struct{}{}, + sentryproto.MessageId_GET_POOLED_TRANSACTIONS_66: struct{}{}, + sentryproto.MessageId_POOLED_TRANSACTIONS_66: struct{}{}, + sentryproto.MessageId_BLOCK_RANGE_UPDATE_69: struct{}{}, + sentryproto.MessageId_GET_BLOCK_ACCESS_LISTS_71: struct{}{}, + sentryproto.MessageId_BLOCK_ACCESS_LISTS_71: struct{}{}, + }, +} + +func TestProtoIdsGolden(t *testing.T) { + require.Equal(t, goldenProtoIds, libsentry.ProtoIds) +}