关于Socket通讯中的Close_wait状态

文/转 编辑

编者按:使用Socket通讯,有时我们查看端口状态的时候,经常会发现Socket处于close_wait状态,从而影响系统性能,此文或许会给你一些答案。

最近遇到的一个关于socket.close的问题,在某个应用服务器出现的状况(执行netstat -np | grep tcp):

tcp        0    
 0 10.224.122.16:50158         10.224.112.58:8788
         CLOSE_WAIT

tcp        0    
 0 10.224.122.16:37655         10.224.112.58:8788
         CLOSE_WAIT

tcp        1    
 0 127.0.0.1:32713            
127.0.0.1:8080              CLOSE_WAIT

tcp       38      0
10.224.122.16:34538         10.224.125.42:443    
      CLOSE_WAIT

tcp       38      0
10.224.122.16:33394         10.224.125.42:443    
      CLOSE_WAIT

tcp        1    
 0 10.224.122.16:18882         10.224.125.10:80  
         CLOSE_WAIT

tcp        1    
 0 10.224.122.16:18637         10.224.125.10:80  
         CLOSE_WAIT

tcp        1    
 0 10.224.122.16:19655         10.224.125.12:80  
         CLOSE_WAIT

........................................

总共出现了200个CLOSE_WAIT的socket.而且这些socket长时间得不到释放.下面我们来看看为什么会出现这种大量socket的CLOSE_WAIT情况

首先我们要搞清楚的是,这个socket是谁发起的,我们可以看到122.16这台机器开了很多端口,而且端口号都很大,125.12
或者125.10上的端口都是很常见服务器端口,所以122.16上这么多CLOSE_WAIT

的socket是由122.16开启的,换句话说这台机器是传统的客户端,它会主动的请求其他机器的服务端口.

要搞清楚为什么会出现CLOSE_WAIT,那么首先我们必须要清楚CLOSE_WAIT的机制和原理.

假设我们有一个client,
一个server.

当client主动发起一个socket.close()这个时候对应TCP来说,会发生什么事情呢?如下图所示.

client首先发送一个FIN信号给server, 这个时候client变成了FIN_WAIT_1的状态, server端收到FIN之后,返回ACK,然后server端的状态变成了CLOSE_WAIT.

接着server端需要发送一个FIN给client,然后server端的状态变成了LAST_ACK,接着client返回一个ACK,然后server端的socket就被成功的关闭了.

从这里可以看到,如果由客户端主动关闭一链接,那么客户端是不会出现CLOSE_WAIT状态的.客户端主动关闭链接,那么Server端将会出现CLOSE_WAIT的状态.

而我们的服务器上,是客户端socket出现了CLOSE_WAIT,由此可见这个是由于server主动关闭了server上的socket.

那么当server主动发起一个socket.close(),这个时候又发生了一些什么事情呢.

从图中我们可以看到,如果是server主动关闭链接,那么Client则有可能进入CLOSE_WAIT,如果Client不发送FIN包,那么client就一直会处在CLOSE_WAIT状态(后面我们可以看到有参数可以调整这个时间).

那么现在我们要搞清楚的是,在第二中场景中,为什么Client不发送FIN包给server.要搞清楚这个问题,我们首先要搞清楚server是怎么发FIN包给client的,其实server就是调用了

socket.close方法而已,也就是说如果要client发送FIN包,那么client就必须调用socket.close,否则就client就一直会处在CLOSE_WAIT。

关于Socket通讯中的Close_wait状态的更多相关文章

  1. c# Socket通讯中关于粘包,半包的处理,加分割符

    using System; using System.Collections.Generic; using System.Text; using System.Net.Sockets; using S ...

  2. .Net中的Socket通讯

    .NetFrameWork为Socket通讯提供了System.Net.Socket命名空间,在这个命名空间里面有以下几个常用的重要类分别是: ·Socket类 这个低层的类用于管理连接,WebReq ...

  3. close_wait状态和time_wait状态(TCP连接)

    1.CLOSE_WAIT的简单解决方案 不久前,我的Socket Client程序遇到了一个非常尴尬的错误.它本来应该在一个socket长连接上持续不断地向服务器发送数据,如果socket连接断开,那 ...

  4. CLOSE_WAIT状态的原因与解决方法(转载留自己看)

    这个问题之前没有怎么留意过,是最近在面试过程中遇到的一个问题,面了两家公司,两家公司竟然都面到到了这个问题,不得不使我开始关注这个问题.说起CLOSE_WAIT状态,如果不知道的话,还是先瞧一下TCP ...

  5. close_wait状态的产生原因及解决(转)

    最近测试环境server由于需要与大量的后台server交互,今天突然发现有大量的close_wait产生,于是仔细研究了一下: 如果我们的服务器程序处于CLOSE_WAIT状态的话,说明套接字是被动 ...

  6. CLOSE_WAIT状态的原因与解决方法 --转

    转自:http://blog.chinaunix.net/uid-20357359-id-1963662.html 这个问题之前没有怎么留意过,是最近在面试过程中遇到的一个问题,面了两家公司,两家公司 ...

  7. socket编程中客户端常用函数

    1 常用函数 1.1   connect() int connect(int sockfd, const struct sockaddr *servaddr, socklen_taddrlen); 客 ...

  8. 基于Socket通讯(C#)和WebSocket协议(net)编写的两种聊天功能(文末附源码下载地址)

    今天我们来盘一盘Socket通讯和WebSocket协议在即时通讯的小应用——聊天. 理论大家估计都知道得差不多了,小编也通过查阅各种资料对理论知识进行了充电,发现好多demo似懂非懂,拷贝回来又运行 ...

  9. TCP建立与断开连接、socket通讯模板

    在传输层,有一个重点是TCP传输时建立连接的三次"握手"和四次"挥手",因为socket工作于应用层和传输层之间,故而涉及到建立连接和关闭连接的过程,以下笔记可 ...

随机推荐

  1. Elasticsearch前沿:ES 5.x改进详解与ES6展望

    转:http://www.dataguru.cn/article-11094-1.html 曾勇(Medcl),Elastic 工程师与布道师,2015 年加入 Elastic 公司.加入 Elast ...

  2. ServiceStack.Redis泛型存储后getById问题

    关于ServiceStack.Redis实体存储常用的有一下几个方法 StoreAsHash<T>(T entity)  //将对象按照Hash存储 Redis.As<T>() ...

  3. leetcode - 3、Longest Substring Without Repeating Characters

    题目链接:https://leetcode.com/problems/longest-substring-without-repeating-characters/description/ 题目要求: ...

  4. code1052 地鼠游戏

    贪心算法,从后往前 来自codevs的题解: 我的纠结思考过程:如果每一秒都没有重复的地鼠出现 那么肯定是一个一个挨着打如果有重复的地鼠 那么要考虑打那个更优 当然是选分值最大的 单纯这样想很合理 但 ...

  5. easyui combogrid 多选加载,保存,显示代码

    1.调用代码 UTIL.SetDict($("#txt_ExcludeIndustry_"), "SECTOR_TYPE", true, true, funct ...

  6. 查看并解除Oracle锁

    当某个数据库用户在数据库中插入.更新.删除一个表的数据,或者增加一个表的主键时或者表的索引时, 常常会出现ora-00054:resource busy and acquire with nowait ...

  7. jQuary总结9:html()的常见用法

    1html() 不传参数 用于获取内容 //html <div> <p></p> <span></span> 文本 </div> ...

  8. java IO类简单介绍

    一.流的概念 流是字节序列的抽象概念.流和文件的差别:文件是数据的静态存储形式,而流是指数据传输时的形态.文件只是流的操作对象之一.流按其操作的对象不同可以分为文件流.网络流.内存流.磁带流等.Jav ...

  9. 编写高质量代码改善C#程序的157个建议——建议87:区分WPF和WinForm的线程模型

    建议87:区分WPF和WinForm的线程模型 WPF和WinForm窗体应用程序都有一个要求,那就是UI元素(如Button.TextBox等)必须由创建它的那个线程进行更新.WinForm在这方面 ...

  10. 【LeetCode C++】Two Sum

    题目: Given an array of integers, return indices of the two numbers such that they add up to a specifi ...