douzhanrun0497 2016-03-03 03:47
浏览 48
已采纳

仅在连接关闭时在端口上侦听TCP数据包才能读取数据

I am creating a TCP server end in GO, which receives TCP packets and sends responses accordingly. I am able to listen to connections, but when the client-end sends TCP packets to the server, the server only receives them when the connection is reset (TCP RST).

This means that when the client sends a packet, the server waits for the next packet to do something with the first. This is the code affecting this part of the problem:

listener, err := net.Listen("tcp", ":25565")

if err != nil {
  fmt.Println(err)
}

for {
  conn, err := listener.Accept()

  if err != nil {
    fmt.Println(err)
  }

  message, _ := ioutil.ReadAll(conn) // Get the bytes from the TCP packet
  fmt.Println("Received connection " + conn.RemoteAddr().String())
  HandlePacket(conn, message) // Do stuff with the data
  conn.Close() // End the connection
}

HandlePacket(...) parses the bytes received in the packet. The thing is, it receives nothing when the client sends the first packet, and then prints the first packet's data when the second is sent.

  • 写回答

1条回答 默认 最新

  • dsh84723 2016-03-03 04:10
    关注

    The big hint is right there in your call to read from the socket:

    message, _ := ioutil.ReadAll(conn) // Get the bytes from the TCP packet
    

    ReadAll() won't just return the available data in the socket's buffer. ReadAll() is going to read until there's never going to be any more data to read - until the stream is closed. The stream is closed only when the connection is closed, as you've seen.

    You have to ask the TCP socket to read some finite amount of data. Since TCP does not preserve message boundaries, you have to use your own framing scheme to know how much data to read.

    One such simple scheme is to make it so that your packets are always some fixed size. This might be useful, for instance, if you're sending streaming updates for, say, a game's netcode; just make each packet 256 bytes and stuff in as many position updates as will fit in 256 bytes; if there's more, just send more packets.

    If using a fixed-sized frame doesn't work for you, consider using a packet with a little header. Perhaps the first 4 bytes are an integer telling you how long the message is, followed by the message. Then, every time you want to read a packet, you perform a hard read of 4 bytes to find out the size, and then read that many bytes from the socket.

    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论

报告相同问题?

悬赏问题

  • ¥15 c语言怎么用printf(“\b \b”)与getch()实现黑框里写入与删除?
  • ¥20 怎么用dlib库的算法识别小麦病虫害
  • ¥15 华为ensp模拟器中S5700交换机在配置过程中老是反复重启
  • ¥15 java写代码遇到问题,求帮助
  • ¥15 uniapp uview http 如何实现统一的请求异常信息提示?
  • ¥15 有了解d3和topogram.js库的吗?有偿请教
  • ¥100 任意维数的K均值聚类
  • ¥15 stamps做sbas-insar,时序沉降图怎么画
  • ¥15 买了个传感器,根据商家发的代码和步骤使用但是代码报错了不会改,有没有人可以看看
  • ¥15 关于#Java#的问题,如何解决?