网络编程.确定消息的结尾
Network programming. Determine end of message
linux缓冲区全部接收到套接字上的消息。但是在收到之前,此消息有一个开始和结束。Linux在缓冲区中依次写下此消息,因此丢失了消息结束的信息。
我知道在Linux中我可以使用CMSG_Header.ut Windows不提供send-/recvmsg()过程。如何确定缓冲平台Agnostic上的消息的结尾?
我不确定TCP/IP连接是否在交换界限良好的消息。路由器可以碎片包。(因此cmsg_header
可能是不可靠的)。
我知道的所有基于TCP/IP的协议(HTTP,SMTP,X11,RPCXDR)都在应用程序级别处理消息组织。您的应用程序库需要以某种方式知道"消息"启动或结束的时间。
只需以网络顺序发送消息长度的前4个字节即可。那么您将不会有这个问题。
我认为 sendmsg
, recvmsg
的winsock当量是 WSASendMsg
和 WSARecvMsg
。他们采用LPWSAMSG
参数,根据文档,基于MSGHDR结构的POSIX.1G规范的结构。
面向应用程序的网络通常具有清晰的运输/业务逻辑分离。
业务层仅操作整个消息。运输正在向上游业务层传递整个消息,从而可能从片段,重新切片并重新解释其作为一系列消息的连续流。
传输层通常使用形式的协议消息与远程传输层进行通信。其中[大小]是一个单个数字,其编组长度s在所有交流方中都知道。
传输层要做的第一件事是等待从下游接收s字节(无论是异步还是同步,无关紧要)。完成后,请收到数据并意识到要接收的有效载荷的长度l。
一旦有效载荷L的Lenght已知运输,就等待从下游接收l字节到临时缓冲区(可能必须结合多个读取),并且一旦完成,它就通知了应用程序层,将整个组装的消息传递到单个中缓冲区。
linux在缓冲区中依次写下此消息,因此丢失了消息结束的信息。
这是不正确的。在接收端,从来没有任何"有关消息结束的信息"。TCP是一个字节流协议。您的 send()
s或 write()
s在发件人处得到串联,,插入其套接字 send buffer,然后从那里传输了数据,但运输量已决定,但是运输决定了。这样做。
如果您想要通过TCP消息,则必须自己完全实现它们。通用技术:
- 在消息前发送一个长度单词
- 封装消息,例如在STX和ETX之间,如果出现在消息中,则适用于ETX(ESC ETX),因此在消息中出现在消息中的ESC本身(ESC)
- 使用自我描述的协议,例如xml。