mirror of
https://github.com/ethereum/go-ethereum.git
synced 2026-07-20 11:46:44 +00:00
feat: add eth/62 handshake support for XDC
- Added StatusPacket62 without ForkID field - Added handshake62() function for eth/62, eth/63, XDPOS2 - Added readStatus62() for reading XDC status messages Note: Peer connection still fails due to XDC's custom discovery protocol using pingXDC (type 5) instead of standard ping (type 1). This requires modification to p2p/discover layer.
This commit is contained in:
parent
93bbb7c130
commit
fbc86ff61f
2 changed files with 62 additions and 0 deletions
|
|
@ -19,6 +19,7 @@ package eth
|
||||||
import (
|
import (
|
||||||
"errors"
|
"errors"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
"math/big"
|
||||||
"time"
|
"time"
|
||||||
|
|
||||||
"github.com/ethereum/go-ethereum/common"
|
"github.com/ethereum/go-ethereum/common"
|
||||||
|
|
@ -41,11 +42,59 @@ func (p *Peer) Handshake(networkID uint64, chain forkid.Blockchain, rangeMsg Blo
|
||||||
return p.handshake69(networkID, chain, rangeMsg)
|
return p.handshake69(networkID, chain, rangeMsg)
|
||||||
case ETH68:
|
case ETH68:
|
||||||
return p.handshake68(networkID, chain)
|
return p.handshake68(networkID, chain)
|
||||||
|
case ETH62, ETH63, XDPOS2:
|
||||||
|
// XDC uses eth/62, eth/63, and xdpos2 without ForkID
|
||||||
|
return p.handshake62(networkID, chain)
|
||||||
default:
|
default:
|
||||||
return errors.New("unsupported protocol version")
|
return errors.New("unsupported protocol version")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// handshake62 performs the eth/62 handshake without ForkID (used by XDC)
|
||||||
|
func (p *Peer) handshake62(networkID uint64, chain forkid.Blockchain) error {
|
||||||
|
var (
|
||||||
|
genesis = chain.Genesis()
|
||||||
|
latest = chain.CurrentHeader()
|
||||||
|
// XDC is pre-merge, so TD is relevant. Use a placeholder TD based on block number.
|
||||||
|
// In a proper implementation, this should come from the chain's state.
|
||||||
|
td = new(big.Int).SetUint64(latest.Number.Uint64())
|
||||||
|
)
|
||||||
|
errc := make(chan error, 2)
|
||||||
|
go func() {
|
||||||
|
pkt := &StatusPacket62{
|
||||||
|
ProtocolVersion: uint32(p.version),
|
||||||
|
NetworkID: networkID,
|
||||||
|
TD: td,
|
||||||
|
Head: latest.Hash(),
|
||||||
|
Genesis: genesis.Hash(),
|
||||||
|
}
|
||||||
|
errc <- p2p.Send(p.rw, StatusMsg, pkt)
|
||||||
|
}()
|
||||||
|
var status StatusPacket62 // safe to read after two values have been received from errc
|
||||||
|
go func() {
|
||||||
|
errc <- p.readStatus62(networkID, &status, genesis.Hash())
|
||||||
|
}()
|
||||||
|
|
||||||
|
return waitForHandshake(errc, p)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (p *Peer) readStatus62(networkID uint64, status *StatusPacket62, genesis common.Hash) error {
|
||||||
|
if err := p.readStatusMsg(status); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
if status.NetworkID != networkID {
|
||||||
|
return fmt.Errorf("%w: %d (!= %d)", errNetworkIDMismatch, status.NetworkID, networkID)
|
||||||
|
}
|
||||||
|
if uint(status.ProtocolVersion) != p.version {
|
||||||
|
return fmt.Errorf("%w: %d (!= %d)", errProtocolVersionMismatch, status.ProtocolVersion, p.version)
|
||||||
|
}
|
||||||
|
if status.Genesis != genesis {
|
||||||
|
return fmt.Errorf("%w: %x (!= %x)", errGenesisMismatch, status.Genesis, genesis)
|
||||||
|
}
|
||||||
|
// No ForkID check for eth/62
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
func (p *Peer) handshake68(networkID uint64, chain forkid.Blockchain) error {
|
func (p *Peer) handshake68(networkID uint64, chain forkid.Blockchain) error {
|
||||||
var (
|
var (
|
||||||
genesis = chain.Genesis()
|
genesis = chain.Genesis()
|
||||||
|
|
|
||||||
|
|
@ -111,6 +111,16 @@ type Packet interface {
|
||||||
Kind() byte // Kind returns the message type.
|
Kind() byte // Kind returns the message type.
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// StatusPacket62 is the network packet for the status message in eth/62 and eth/63.
|
||||||
|
// XDC uses this format without ForkID.
|
||||||
|
type StatusPacket62 struct {
|
||||||
|
ProtocolVersion uint32
|
||||||
|
NetworkID uint64
|
||||||
|
TD *big.Int
|
||||||
|
Head common.Hash
|
||||||
|
Genesis common.Hash
|
||||||
|
}
|
||||||
|
|
||||||
// StatusPacket is the network packet for the status message.
|
// StatusPacket is the network packet for the status message.
|
||||||
type StatusPacket68 struct {
|
type StatusPacket68 struct {
|
||||||
ProtocolVersion uint32
|
ProtocolVersion uint32
|
||||||
|
|
@ -361,6 +371,9 @@ type BlockRangeUpdatePacket struct {
|
||||||
LatestBlockHash common.Hash
|
LatestBlockHash common.Hash
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (*StatusPacket62) Name() string { return "Status" }
|
||||||
|
func (*StatusPacket62) Kind() byte { return StatusMsg }
|
||||||
|
|
||||||
func (*StatusPacket68) Name() string { return "Status" }
|
func (*StatusPacket68) Name() string { return "Status" }
|
||||||
func (*StatusPacket68) Kind() byte { return StatusMsg }
|
func (*StatusPacket68) Kind() byte { return StatusMsg }
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue