p2p: add network simulation framework (#14982)
This commit introduces a network simulation framework which can be used to run simulated networks of devp2p nodes. The intention is to use this for testing protocols, performing benchmarks and visualising emergent network behaviour.
This commit is contained in:
committed by
Felix Lange
parent
673007d7ae
commit
9feec51e2d
42
p2p/peer.go
42
p2p/peer.go
@ -25,6 +25,7 @@ import (
|
||||
"time"
|
||||
|
||||
"github.com/ethereum/go-ethereum/common/mclock"
|
||||
"github.com/ethereum/go-ethereum/event"
|
||||
"github.com/ethereum/go-ethereum/log"
|
||||
"github.com/ethereum/go-ethereum/p2p/discover"
|
||||
"github.com/ethereum/go-ethereum/rlp"
|
||||
@ -60,6 +61,38 @@ type protoHandshake struct {
|
||||
Rest []rlp.RawValue `rlp:"tail"`
|
||||
}
|
||||
|
||||
// PeerEventType is the type of peer events emitted by a p2p.Server
|
||||
type PeerEventType string
|
||||
|
||||
const (
|
||||
// PeerEventTypeAdd is the type of event emitted when a peer is added
|
||||
// to a p2p.Server
|
||||
PeerEventTypeAdd PeerEventType = "add"
|
||||
|
||||
// PeerEventTypeDrop is the type of event emitted when a peer is
|
||||
// dropped from a p2p.Server
|
||||
PeerEventTypeDrop PeerEventType = "drop"
|
||||
|
||||
// PeerEventTypeMsgSend is the type of event emitted when a
|
||||
// message is successfully sent to a peer
|
||||
PeerEventTypeMsgSend PeerEventType = "msgsend"
|
||||
|
||||
// PeerEventTypeMsgRecv is the type of event emitted when a
|
||||
// message is received from a peer
|
||||
PeerEventTypeMsgRecv PeerEventType = "msgrecv"
|
||||
)
|
||||
|
||||
// PeerEvent is an event emitted when peers are either added or dropped from
|
||||
// a p2p.Server or when a message is sent or received on a peer connection
|
||||
type PeerEvent struct {
|
||||
Type PeerEventType `json:"type"`
|
||||
Peer discover.NodeID `json:"peer"`
|
||||
Error string `json:"error,omitempty"`
|
||||
Protocol string `json:"protocol,omitempty"`
|
||||
MsgCode *uint64 `json:"msg_code,omitempty"`
|
||||
MsgSize *uint32 `json:"msg_size,omitempty"`
|
||||
}
|
||||
|
||||
// Peer represents a connected remote node.
|
||||
type Peer struct {
|
||||
rw *conn
|
||||
@ -71,6 +104,9 @@ type Peer struct {
|
||||
protoErr chan error
|
||||
closed chan struct{}
|
||||
disc chan DiscReason
|
||||
|
||||
// events receives message send / receive events if set
|
||||
events *event.Feed
|
||||
}
|
||||
|
||||
// NewPeer returns a peer for testing purposes.
|
||||
@ -297,9 +333,13 @@ func (p *Peer) startProtocols(writeStart <-chan struct{}, writeErr chan<- error)
|
||||
proto.closed = p.closed
|
||||
proto.wstart = writeStart
|
||||
proto.werr = writeErr
|
||||
var rw MsgReadWriter = proto
|
||||
if p.events != nil {
|
||||
rw = newMsgEventer(rw, p.events, p.ID(), proto.Name)
|
||||
}
|
||||
p.log.Trace(fmt.Sprintf("Starting protocol %s/%d", proto.Name, proto.Version))
|
||||
go func() {
|
||||
err := proto.Run(p, proto)
|
||||
err := proto.Run(p, rw)
|
||||
if err == nil {
|
||||
p.log.Trace(fmt.Sprintf("Protocol %s/%d returned", proto.Name, proto.Version))
|
||||
err = errProtocolReturned
|
||||
|
Reference in New Issue
Block a user