github.com/cranelv/ethereum_mpc@v0.0.0-20191031014521-23aeb1415092/mpcService/peer.go (about) 1 package mpcService 2 3 import ( 4 "fmt" 5 "github.com/ethereum/go-ethereum/p2p" 6 "github.com/ethereum/go-ethereum/p2p/discover" 7 "github.com/ethereum/go-ethereum/rlp" 8 "gopkg.in/fatih/set.v0" 9 "github.com/ethereum/go-ethereum/mpcService/protocol" 10 "github.com/ethereum/go-ethereum/log" 11 ) 12 13 // peer represents a whisper protocol peer connection. 14 type Peer struct { 15 // host *Storeman 16 *p2p.Peer 17 ws p2p.MsgReadWriter 18 trusted bool 19 20 known *set.Set // Messages already known by the peer to avoid wasting bandwidth 21 22 } 23 24 // newPeer creates a new whisper peer object, but does not run the handshake itself. 25 func newPeer( remote *p2p.Peer, rw p2p.MsgReadWriter) *Peer { 26 return &Peer{ 27 Peer: remote, 28 ws: rw, 29 trusted: false, 30 known: set.New(), 31 } 32 } 33 34 35 // handshake sends the protocol initiation status message to the remote peer and 36 // verifies the remote status too. 37 func (p *Peer) handshake() error { 38 // Send the handshake status message asynchronously 39 errc := make(chan error, 1) 40 go func() { 41 errc <- p2p.Send(p.ws, protocol.StatusCode, protocol.ProtocolVersion) 42 }() 43 // Fetch the remote status packet and verify protocol match 44 packet, err := p.ws.ReadMsg() 45 if err != nil { 46 log.Error("storeman peer read msg fail.", "peer",p.ID(), "error" ,err) 47 return err 48 } 49 defer packet.Discard() 50 51 log.Info("storeman received handshake. ", "peer",p.ID(), "packet code" ,packet.Code) 52 if packet.Code != protocol.StatusCode { 53 log.Error("storeman peer sent packet before status packet", "peer",p.ID(), "packet code" ,packet.Code) 54 return fmt.Errorf("storman peer [%s] sent packet %x before status packet", p.ID().String(), packet.Code) 55 } 56 s := rlp.NewStream(packet.Payload, uint64(packet.Size)) 57 peerVersion, err := s.Uint() 58 if err != nil { 59 log.Error("storman peer sent bad status message:","peer",p.ID(), "error" ,err) 60 return fmt.Errorf("storman peer [%s] sent bad status message: %v", p.ID().String(), err) 61 } 62 if peerVersion != protocol.ProtocolVersion { 63 log.Error("storman peer : protocol version mismatch ", "peer",p.ID(), peerVersion, protocol.ProtocolVersion) 64 return fmt.Errorf("storman peer [%s]: protocol version mismatch %d != %d", p.ID().String(), peerVersion, protocol.ProtocolVersion) 65 } 66 // Wait until out own status is consumed too 67 if err := <-errc; err != nil { 68 log.Error("storman peer failed to send status packet:", "peer",p.ID(), "error" ,err) 69 return fmt.Errorf("storman peer [%s] failed to send status packet: %v", p.ID().String(), err) 70 } 71 return nil 72 } 73 74 func (p *Peer) ID() discover.NodeID { 75 id := p.Peer.ID() 76 return id 77 }