插座清洁

时间:2013-04-26 19:36:56

标签: c linux sockets ipc

我对unix套接字(TCP local)感到有点困惑

我有一个服务器和一个客户端

  • 客户端通过套接字向服务器发送一些信息(使用send) 很多次
  • 服务器打印此数据(服务器调用recv以接收该数据)。

问题是服务器不仅会打印客户端发送的最新信息,还会显示一些旧信息(有时已损坏)这个客户端也是如此,所以我认为套接字累积客户端所写的所有先前数据

服务器如何仅接收来自客户端的最新数据?我应该以某种方式清理插座,或者我应该一直关闭它并创建新的(非常糟糕的解决方案)?

3 个答案:

答案 0 :(得分:3)

TCP套接字是流套接字 这意味着您发送的所有数据不会被视为一系列消息,而是一系列字节。字节按顺序接收,没有添加或省略,但不一定在相同的块中。

例如,如果您的客户端调用send 3次,每次调用1000个字节,则无法确定recv将返回数据的次数。它可以返回3次,每次1000字节,或者只返回3000字节一次,或理论上甚至3000次,每次1字节。

答案 1 :(得分:1)

图像发送/接收的字节放在队列(内部缓冲区)中。如果你两次调用send(),每次发送10个字节,缓冲区中将有20个字节。当另一方调用recv()时,它会从该队列中取出一些字节并将它们放入传递的数组中。多少字节?最多可用(20)或更少。

例如,如果你打电话

   nb =  recv(socket, arr, 15,...);

然后只消耗15个字节(可能你的数组arr有这个长度),它们将被复制到arrnb将是15,并且在内部缓冲区中我们剩下5个字节。

如果我们打电话

   nb =  recv(socket, arr, 100,...);

然后将20个字节复制到arrnb将为20,内部缓冲区将为空。

这告诉你:

  • send() / recv()来电与

  • 您必须始终检查recv返回(nb)以了解已读取的字节数

  • 您无法知道每个send()来电中发送了哪些字节。 “消息”的划分取决于您

  • 您不是在阅读消息,也不是字符串(以空值终止的字符数组),您只是在读取字节。然后,您不能只是调用printf("%s",arr)来查看收到的字节

答案 2 :(得分:1)

  1. tcp是流协议;

  2. 检查send和recv的返回值,确保错误处理得当;

  3. 检查您打印的是您发送的内容,检查二进制内容和长度的发送和recv缓冲区。

  4. 确保您在发送方发送的内容是您在接收方获得的内容。

    一段代码非常值得进一步分析。