forked from TrueCloudLab/neoneo-go
wip
This commit is contained in:
parent
98a6831d6a
commit
d76b86febd
2 changed files with 33 additions and 13 deletions
|
@ -98,6 +98,8 @@ func (m *Message) commandType() commandType {
|
||||||
return cmdVersion
|
return cmdVersion
|
||||||
case "verack":
|
case "verack":
|
||||||
return cmdVerack
|
return cmdVerack
|
||||||
|
case "getaddr":
|
||||||
|
return cmdGetAddr
|
||||||
case "addr":
|
case "addr":
|
||||||
return cmdAddr
|
return cmdAddr
|
||||||
case "getheaders":
|
case "getheaders":
|
||||||
|
@ -211,7 +213,7 @@ func newVersionPayload(p uint16, ua string, h uint32, r bool) *Version {
|
||||||
Services: 1,
|
Services: 1,
|
||||||
Timestamp: 12345,
|
Timestamp: 12345,
|
||||||
Port: p,
|
Port: p,
|
||||||
Nonce: 1911099534,
|
Nonce: 19110,
|
||||||
UserAgent: []byte(ua),
|
UserAgent: []byte(ua),
|
||||||
StartHeight: 0,
|
StartHeight: 0,
|
||||||
Relay: r,
|
Relay: r,
|
||||||
|
|
|
@ -68,7 +68,9 @@ func NewServer(net NetMode) *Server {
|
||||||
}
|
}
|
||||||
|
|
||||||
s := &Server{
|
s := &Server{
|
||||||
userAgent: fmt.Sprintf("/NEO:%s/", version),
|
// It is important to have this user agent correct. Otherwise we will get
|
||||||
|
// disconnected.
|
||||||
|
userAgent: fmt.Sprintf("\v/NEO:%s/", version),
|
||||||
logger: logger,
|
logger: logger,
|
||||||
peers: make(map[*Peer]bool),
|
peers: make(map[*Peer]bool),
|
||||||
register: make(chan *Peer),
|
register: make(chan *Peer),
|
||||||
|
@ -118,6 +120,12 @@ func (s *Server) shutdown() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (s *Server) disconnect(p *Peer) {
|
||||||
|
p.conn.Close()
|
||||||
|
close(p.send)
|
||||||
|
s.unregister <- p
|
||||||
|
}
|
||||||
|
|
||||||
func (s *Server) loop() {
|
func (s *Server) loop() {
|
||||||
for {
|
for {
|
||||||
select {
|
select {
|
||||||
|
@ -133,7 +141,10 @@ func (s *Server) loop() {
|
||||||
peer.send <- resp
|
peer.send <- resp
|
||||||
}
|
}
|
||||||
case peer := <-s.unregister:
|
case peer := <-s.unregister:
|
||||||
s.logger.Printf("peer %s disconnected", peer.conn.RemoteAddr())
|
if _, ok := s.peers[peer]; ok {
|
||||||
|
delete(s.peers, peer)
|
||||||
|
s.logger.Printf("peer %s disconnected", peer.conn.RemoteAddr())
|
||||||
|
}
|
||||||
case tuple := <-s.message:
|
case tuple := <-s.message:
|
||||||
if err := s.processMessage(tuple.msg, tuple.peer); err != nil {
|
if err := s.processMessage(tuple.msg, tuple.peer); err != nil {
|
||||||
s.logger.Fatalf("failed to process message: %s", err)
|
s.logger.Fatalf("failed to process message: %s", err)
|
||||||
|
@ -147,16 +158,15 @@ func (s *Server) loop() {
|
||||||
// TODO: unregister peers on error.
|
// TODO: unregister peers on error.
|
||||||
// processMessage processes the received message from a remote node.
|
// processMessage processes the received message from a remote node.
|
||||||
func (s *Server) processMessage(msg *Message, peer *Peer) error {
|
func (s *Server) processMessage(msg *Message, peer *Peer) error {
|
||||||
rpcLogger.Printf("IN :: %+v", msg)
|
rpcLogger.Printf("IN :: %+v", string(msg.Command))
|
||||||
|
|
||||||
switch msg.commandType() {
|
switch msg.commandType() {
|
||||||
case cmdVersion:
|
case cmdVersion:
|
||||||
v, _ := msg.decodePayload()
|
v, err := msg.decodePayload()
|
||||||
resp, err := s.handleVersionCmd(v.(*Version))
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
peer.send <- resp
|
s.handleVersionCmd(v.(*Version), peer)
|
||||||
case cmdVerack:
|
case cmdVerack:
|
||||||
case cmdGetAddr:
|
case cmdGetAddr:
|
||||||
case cmdAddr:
|
case cmdAddr:
|
||||||
|
@ -187,14 +197,22 @@ func (s *Server) handlePeerConnected() (*Message, error) {
|
||||||
return msg, nil
|
return msg, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// Version declares the server's version when a new connection is been made.
|
// Version declares the server's version.
|
||||||
// We respond with a instant "verack" message.
|
func (s *Server) handleVersionCmd(v *Version, peer *Peer) {
|
||||||
func (s *Server) handleVersionCmd(v *Version) (*Message, error) {
|
|
||||||
// TODO: check version and verify to trust that node.
|
// TODO: check version and verify to trust that node.
|
||||||
|
|
||||||
// Empty payload for the verack message.
|
payload := newVersionPayload(s.port, s.userAgent, 0, s.relay)
|
||||||
msg := newMessage(s.net, cmdVerack, nil)
|
b, err := payload.encode()
|
||||||
return msg, nil
|
if err != nil {
|
||||||
|
s.disconnect(peer)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
versionMsg := newMessage(s.net, cmdVersion, b)
|
||||||
|
peer.send <- versionMsg
|
||||||
|
|
||||||
|
peer.verack = true
|
||||||
|
verackMsg := newMessage(s.net, cmdVerack, nil)
|
||||||
|
peer.send <- verackMsg
|
||||||
}
|
}
|
||||||
|
|
||||||
func logo() string {
|
func logo() string {
|
||||||
|
|
Loading…
Add table
Reference in a new issue