• 【解决】Select网络模型问题——奇怪的发送接收问题


    2010-04-07 00:16:34|  分类: 网络开发 |  标签: |字号 订阅

    考虑到以后可能要用到服务器程序,如果没有现成的、稳定的代码,到时候可能会遇到麻烦。所以,最近一有空,就写服务器的框架代码。

    问题一:select模型如何得知连接中断?

    select模型只有三种套接字集合:发送、接收、异常。那么,怎么知道远程客户端中断了网络连接呢?跟踪调试发现,当远程客户端主动中断连接时,服务器接收到长度为0的数据包。

    这一点很好理解。因为TCP连接中断时,客户端和服务器会相互发送通知数据包。这个数据包没有内容,只有TCP/IP报头。所以,内容长度为0,这是可以理解的。

    于是,在接收到长度为0的数据包时,可以认为,这是远程客户端中断了连接。——但是,在网络上找到的代码,里面都没有对远程客户端主动中断连接进行处理,所以,我无法验证自己的看法是否正确。

    另外,对于TCP连接,还有一种数据包的长度为0,即“心跳数据包”。和UDP不同,TCP是基于连接的。这种基于连接的协议,它的实现其实并不复杂。TCP会定时发送“心跳数据包”,通过这个数据包来保持两台主机之间的连接性。

    假设,客户端发送了多次“心跳数据包”,服务器始终没有响应,那么,说明连接可能中断了;反之,表示连接仍然保持着。这就是“面向连接”。

    可以猜想,这种心跳数据包应该也是长度为0的吧,那它不是和连接关闭的数据包相互混淆了?那到底该怎么判断客户端主动关闭了连接?

     

    问题二:select模型为什么无缘无故地要求发送数据?

    客户端连接服务器之后,什么事情都没做,但是select的结果是发送数据包!不向服务器发送数据包还不行!可能是哪句代码弄错了?

    我想,可能在TCP连接成功建立之后,客户端是应该马上发送数据包给服务器的。但是,我之所以这么做,是因为曾经截获过HTTPS协议的数据包。如果我没有记错的话,HTTPS在TCP连接建立之后,服务器会向客户端发送一个数据包,也就是SSL的加密密钥。

    这么说来,连接建立之后,客户端是可以不发送数据的吧?那为什么select模型总是提示客户端应该发送数据包?

     
    20110916注:
    问题一的答案:
    在TCP连接中断时的四次挥手中,会触发上层应用程序接收数据,此时收到的是0字节的数据包,据此可以判断连接中断。

    问题二的答案:
    select模型,在连接建立后,触发事件并提示可以发送数据包,此时,表示网卡空闲,可以发送数据包。我们此时可以发送,也可以不发送。这里的“要求发送”只是一种通知,等同于说,这里有空座位,你可以去坐,也可以不坐。

  • 相关阅读:
    js触摸屏案例
    Docker
    Docker 镜像加速
    Docker 命令大全
    linux gpasswd
    Docker基础教程
    PHP输出毫秒时间戳
    PHP Variable handling 函数
    Partition Array by Odd and Even
    Median
  • 原文地址:https://www.cnblogs.com/lancidie/p/2286408.html
Copyright © 2020-2023  润新知