neoneo-go/pkg/network/tcp.go

72 lines
1.6 KiB
Go
Raw Normal View History

2018-01-26 18:04:13 +00:00
package network
import (
"io"
"net"
)
func listenTCP(s *Server, port string) error {
ln, err := net.Listen("tcp", port)
if err != nil {
return err
}
for {
conn, err := ln.Accept()
if err != nil {
return err
}
go handleConnection(s, conn, true)
2018-01-26 18:04:13 +00:00
}
}
2018-01-28 13:59:32 +00:00
func connectToRemoteNode(s *Server, address string) {
conn, err := net.Dial("tcp", address)
if err != nil {
2018-01-28 17:42:22 +00:00
s.logger.Printf("failed to connect to remote node %s", address)
2018-01-28 13:59:32 +00:00
if conn != nil {
conn.Close()
}
return
}
s.logger.Printf("connected to %s", conn.RemoteAddr())
go handleConnection(s, conn, false)
}
2018-01-26 18:04:13 +00:00
func connectToSeeds(s *Server, addrs []string) {
for _, addr := range addrs {
2018-01-28 13:59:32 +00:00
go connectToRemoteNode(s, addr)
2018-01-26 18:04:13 +00:00
}
}
func handleConnection(s *Server, conn net.Conn, initiated bool) {
peer := NewPeer(conn, initiated)
2018-01-26 18:04:13 +00:00
s.register <- peer
// remove the peer from connected peers and cleanup the connection.
defer func() {
2018-01-28 17:42:22 +00:00
// all cleanup will happen in the server's loop when unregister is received.
2018-01-26 18:04:13 +00:00
s.unregister <- peer
}()
// Start a goroutine that will handle all writes to the registered peer.
go peer.writeLoop()
// Read from the connection and decode it into an RPCMessage and
// tell the server there is message available for proccesing.
for {
2018-01-28 10:20:42 +00:00
msg := &Message{}
2018-01-26 18:04:13 +00:00
if err := msg.decode(conn); err != nil {
// remote connection probably closed.
if err == io.EOF {
s.logger.Printf("conn read error: %s", err)
break
}
// remove this node on any decode errors.
s.logger.Printf("RPC :: decode error %s", err)
break
}
s.message <- messageTuple{peer, msg}
}
}