Ethereum nodes communicate among themselves using a simple wire protocol forming a virtual or overlay well-formed network. To achieve this goal, this protocol called ÐΞVp2p, uses technologies and standards such as RLP.
In order to provide confidentiality and protect against network disruption, ÐΞVp2p nodes use RLPx messages, an encrypted and authenticated transport protocol. RLPx utilizes a routing algorithm similar to Kademlia, which is a distributed hash table (DHT) for decentralized peer-to-peer computer networks.
RLPx, as an underlying transport protocol, allows among other, "Node Discovery and Network Formation". Another remarkable feature of RLPx is the support of multiple protocols over a single connection.
When ÐΞVp2p nodes communicate via Internet (as they usually do), they use TCP, which provides a connection-oriented medium, but actually ÐΞVp2p nodes communicate in terms of packets, using the so-called facilities (or messages) provided by the underlying transport protocol RLPx, allowing them to communicate sending and receiving packets.
Packets are dynamically framed, prefixed with an RLP encoded header, encrypted and authenticated. Multiplexing is achieved via the frame header which specifies the destination protocol of a packet.
Connections are established via a handshake and, once established, packets are encrypted and encapsulated as frames.
This handshake will be carried out in two phases, the first phase involves the keys exchange and the second phase will perform authentication, and as a part of DEVp2p, will also exchange the capabilities of each node.
All cryptographic operations are based on secp256k1 and each node is expected to maintain a static private key which is saved and restored between sessions.
Until encryption is implemented, packets have a timestamp property to reduce the window of time for carrying out replay attacks. It is recommended that the receiver only accepts packets created within the last 3 seconds.
Packets are signed. Verification is performed by recovering the public key from the signature and checking that it matches an expected value.
With RLP we can encode different types of payloads, whose types are determined by the integer value used in the first entry of the RLP. In this way, ÐΞVp2p, the basic wire protocol, support arbitrary sub-protocols.
Message IDs between 0x00-0x10
are reserved for ÐΞVp2p messages. Therefore, the message IDs of sub-protocols are assumed to be from 0x10
onwards.
Sub-protocols that are not shared between peers are ignored. If multiple versions of the same (equal name) sub-protocol are shared, the numerically highest wins.
As a very basic example, when two peers initiate their communication, each one greets the other with a special ÐΞVp2p message called "Hello", which is identified by the 0x00
message ID.
Through this particular ÐΞVp2p "Hello" message, each node will disclose to its peer relevant data that will allow the communication to begin at a very basic level.
In this step, each peer will know the following information about his peer.
-
The implemented version of the P2P protocol. Now must be
1
. -
The client software identity, as a human-readable string (e.g.
Ethereum(++)/1.0.0
). -
Peer capability name as an ASCII string of length 3. Currently supported capability names are
eth
andshh
. -
Peer capability version as a positive integer. Currently supported versions are
34
foreth
, and1
forshh
. -
The port that the client is listening on. If
0
it indicates the client is not listening. -
The Unique Identity of the node specified as a 512-bit hash.
To carry out an ordered disconnection, the node that wants to disconnect, will send a ÐΞVp2p message called "Disconnect", which is identified by the "0x01" message id. Furthermore, the node specifies the reason for the disconnection using the parameter "reason".
The "reason" parameter can take values from 0x00
to 0x10
, e.g. 0x00
represents the reason "Disconnect requested" and 0x04
represents "Too many peers".
This sub-protocol is identified by the +0x00
message-id.
This message should be sent after the initial handshake and prior to any Ethereum related messages and inform of its current state.
To do this, the node disclose to its peer the following data;
-
The Protocol version.
-
The Network Id.
-
The Total Difficulty of the best chain.
-
The Hash of the best known block.
-
The Hash of the Genesis block.
About networks ids here is a list of those currently known;
-
0: Olympic; Ethereum public pre-release testnet
-
1: Frontier; Homestead, Metropolis, the Ethereum public main network
-
1: Classic; The (un)forked public Ethereum Classic main network, chain ID 61
-
1: Expanse; An alternative Ethereum implementation, chain ID 2
-
2: Morden; The public Ethereum testnet, now Ethereum Classic testnet
-
3: Ropsten; The public cross-client Ethereum testnet
-
4: Rinkeby: The public Geth Ethereum testnet
-
42: Kovan; The public Parity Ethereum testnet
-
77: Sokol; The public POA testnet
-
99: POA; The public Proof of Authority Ethereum network
-
7762959: Musicoin; The music blockchain
This sub-protocol is identified by the +0x05
message-id.
With this message the node requests its peer the specified blocks each by its own hash.
The way to request the nodes is through a list with all the hashes of them, taking the message the following form;
[+0x05: P, hash_0: B_32, hash_1: B_32, ...]
The requesting node must not have a response message containing all the requested blocks, in which case it must request again those that have not been sent by its peer.