Linux 网络编程详解八
TCP/IP协议三次握手机制
TCP/IP是全双工通道,两端都可以读写,三次握手机制就是验证TCP/IP是否是全双工通道
1.客户端调用connect()函数,阻塞客户端进程,客户端向服务器发送数据包SYN,包SYN的值是a,客户端状态置为SYN_SENT,表示向服务器发送验证
2.服务器在调用listen()函数后,将socket套接字变成被动套接字,然后服务器端在accept()函数处阻塞(因为此时listen队列中没有已连接的文件描述符),
此时服务器端状态是SYN_RCVD,表示等待客户端发送SYN包。当服务器接收到客户端的SYN的数据包之后(管道的一端可写),服务器端向客户端发送两个包SYN包和ACK包,
SYN存放值b,ACK包中存放值a+
3.客户端接收到服务器的SYN包和ACK包(管道的另一端可写),校验ACK的值a+,
判断服务器可以接收客户端发送的数据(管道的另一端可以读),既然服务器端可读可写,
客户端状态置为ESABLISHED,表明客户端连接服务器成功,并且将服务器发送的SYN包的值b,加上1,生成ACK包发送给服务器,connect()返回
4.服务器接收到客户端的ACK包,校验ACK包的值,确定客户端可以接收到服务器的数据(管道一端可读),
说明管道两端都可读可写,服务器状态置为ESTABLISHED,accept()函数返回,服务器端和客户端连接成功。
TCP/IP协议四次断开机制
TCP/IP协议规定执行主动关闭那一端,进入TIME_WAIT状态。客户端,服务器都可以主动关闭连接
1.假设客户端主动调用close()函数(进程退出也会调用close函数),客户端连接状态置为FIN_WAIT_1,向服务器发送两个数据包FIN(值为x)和ACK(值为y)
2.服务器端TCP/IP协议接收到数据包FIN和ACK之后,服务器连接状态置为CLOSE_WAIT,服务器立刻向客户端发送数据包ACK(值为x+)
注意:不是执行read()函数才能接收到数据包FIN和ACK,这两个数据包是TCP/IP协议内部接收的,并且接收之后将read()函数的返回值置0。
3.客户端接收到ACK数据包,客户端状态置为FIN_WAIT_2
4.服务器如果没有调用close()函数,服务器就会一直处于CLOSE_WAIT状态,调用close()函数后,
服务器向客户端发送两个数据包FIN(值为y)和ACK(值为y+),此时服务器连接的状态是LAST_ACK
5.客户端接收到FIN数据包和ACK数据包,那么客户端就会置为TIME_WAIT状态
TIME_WAIT可以存在一定的时间,原因是数据包(ACK y+)发送失败了可以重新发送,这也是服务器有时候需要设置setsockopt()函数的原因。
6.服务器接收数据包(ACK y+),将服务器端连接置为CLOSED状态
为什么客户端关闭了服务器不会立刻处于CLOSED状态?
客户端的读写虽然都关闭了,但是socket有缓存区,write()函数仍然可以向缓存区写数据,
此时如果服务器端没有调用close()函数,服务器一直可以写,直到socket缓存数据被写满。所以服务器可以暂时处于CLOSE_WAIT状态。
TCP/IP协议的第十一种状态
当TCP/IP协议的两端同时调用close(),这时候两端将一同置为CLOSING状态,最后双方都进入TIME_WAIT状态
注意:netstat -na | grep 8080命令下,TCP/IP的CLOSED状态不会显示出来。
Linux 网络编程详解八的更多相关文章
- TCP/UDP Linux网络编程详解
本文主要记录TCP/UDP网络编程的基础知识,采用TCP/UDP实现宿主机和目标机之间的网络通信. 内容目录 1. 目标2.Linux网络编程基础2.1 嵌套字2.2 端口2.3 网络地址2.3.1 ...
- Linux 网络编程详解九
TCP/IP协议中SIGPIPE信号产生原因 .假设客户端socket套接字close(),会给服务器发送字节段FIN: .服务器接收到FIN,但是没有调用close(),因为socket有缓存区,所 ...
- Linux 网络编程详解二(socket创建流程、多进程版)
netstat -na | grep " --查看TCP/IP协议连接状态 //socket编程提高版--服务器 #include <stdio.h> #include < ...
- Linux 网络编程详解一(IP套接字结构体、网络字节序,地址转换函数)
IPv4套接字地址结构 struct sockaddr_in { uint8_t sinlen;(4个字节) sa_family_t sin_family;(4个字节) in_port_t sin_p ...
- Linux 网络编程详解十一
/** * read_timeout - 读超时检测函数,不含读操作 * @fd:文件描述符 * @wait_seconds:等待超时秒数,如果为0表示不检测超时 * 成功返回0,失败返回-1,超时返 ...
- Linux 网络编程详解十
select int select(int nfds, fd_set *readfds, fd_set *writefds,fd_set *exceptfds, struct timeval *tim ...
- Linux 网络编程详解五(TCP/IP协议粘包解决方案二)
ssize_t recv(int s, void *buf, size_t len, int flags); --与read相比,只能用于网络套接字文件描述符 --当flags参数的值设置为MSG_P ...
- Linux 网络编程详解四(流协议与粘包)
TCP/IP协议是一种流协议,流协议是字节流,只有开始和结束,包与包之间没有边界,所以容易产生粘包,但是不会丢包. UDP/IP协议是数据报,有边界,不存在粘包,但是可能丢包. 产生粘包问题的原因 . ...
- Linux 网络编程详解十二
UDP的特点 --无连接 --基于消息的数据传输服务 --不可靠 --UDP更加高效 UDP注意点 --UDP报文可能会丢失,重复 --UDP报文可能会乱序 --UDP缺乏流量控制(UDP缓冲区写满之 ...
随机推荐
- Android IPC机制之ContentProvider
ContentProvider:即内容提供者,用来管理数据,并对外暴露一个uri,外部可以通过uri和数据建立联系并获取或操作数据: 服务端:1.首先创建一个数据库类,并创建一个表:2.创建一个Con ...
- 自动化部署与统一安装升级 - 类ansible工具 udeploy0.3版本发布 (更新时间2014-12-24)
下载地址: unifyDeploy0.1版本 unifyDeploy0.2版本 unifyDeploy0.3版本 (更新时间2014-07-25) 自动化部署与统一安装升级,适用于多资 ...
- 算法导论( FFT & 自动机 & 最优二叉搜索树 !!!)
原图链接:(!!!)
- 开篇:IT软件人员学习的书籍 - IT软件人员书籍系列文章
读书是一件快乐的事情. 读书能够增长知识,了解社会,了解人类的思想,继而转换成智慧.无论是什么人,都需要读书,多读书,读好书,同时也要把书中的精髓记录下来,一个是当做读后感,一个是为以后如果忘记了回头 ...
- 【译】Java中的枚举
前言 译文链接:http://www.programcreek.com/2014/01/java-enum-examples/ Java中的枚举跟其它普通类很像,在其内部包含了一堆预先定义好的对象集合 ...
- Jenkins用户配置(安装好jenkins后,怎么配置用户管理、权限管理)
直奔主题 安装完成后,先开启用户配置 1. 系统管理-->配置权限 2. 启用安全,并选中"安全矩阵" 如上,搞定: 可以按用户去设置各项目的操作权限了: 轻松实现,jen ...
- JavaScript Patterns 5.7 Object Constants
Principle Make variables shouldn't be changed stand out using all caps. Add constants as static prop ...
- php中文乱码问题
HTML中文乱码问题的解决方法. 比如有个index.html的页面(这里是指真正的静态页面,修改服务器的……伪静态的请看方案B) 1.在head标签里面加入这句 <head> <m ...
- mvc razor中renderPartial,RenderAction,Partial,Action的使用选择
RenderPartial: 通常被用来显示一个功能相对独立的“块”,比如说显示菜单或者导航条. RenderPartial输出的结果被作为调用的View的一部分显示. 这个方法会直接将结果写入到当前 ...
- 必须知道的八大种排序算法【java实现】(二) 选择排序,插入排序,希尔算法【详解】
一.选择排序 1.基本思想:在要排序的一组数中,选出最小的一个数与第一个位置的数交换:然后在剩下的数当中再找最小的与第二个位置的数交换,如此循环到倒数第二个数和最后一个数比较为止. 2.实例 3.算法 ...