天天看点

TCP/IP协议简介及三次握手

OSI简介

OSI是一个定义良好的协议规范集,并有许多可选部分完成类似的任务。它定义了开放系统的层次结构、层次之间的相互关系以及各层所包括的可能的任务,作为一个框架来协调和组织各层所提供的服务。

OSI参考模型并没有提供一个可以实现的方法,而是描述了一些概念,用来协调进程间通信标准的制定。即OSI参考模型并不是一个标准,而是一个在制定标准时所使用的概念性框架。

而TCP/IP协议正是参考OSI模型进行设计的落地实现,划分为四层。

TCP/IP协议简介及三次握手

传输流程

TCP/IP协议简介及三次握手

TCP(传输控制协议)

传输控制协议(英语:Transmission Control Protocol,缩写:TCP)是一种面向连接的、可靠的、基于字节流的传输层通信协议,由IETF的RFC 793定义。在简化的计算机网络OSI模型中,它完成第四层传输层所指定的功能。用户数据报协议(UDP)是同一层内另一个重要的传输协议。

在因特网协议族(Internet protocol suite)中,TCP层是位于IP层之上,应用层之下的中间层。不同主机的应用层之间经常需要可靠的、像管道一样的连接,但是IP层不提供这样的流机制,而是提供不可靠的包交换。

应用层向TCP层发送用于网间传输的、用8位字节表示的数据流,然后TCP把数据流分割成适当长度的报文段(通常受该计算机连接的网络的数据链路层的最大传输单元(MTU)的限制)。之后TCP把结果包传给IP层,由它来通过网络将包传送给接收端实体的TCP层。TCP为了保证不发生丢包,就给每个包一个序号,同时序号也保证了传送到接收端实体的包的按序接收。然后接收端实体对已成功收到的包发回一个相应的确认信息(ACK);如果发送端实体在合理的往返时延(RTT)内未收到确认,那么对应的数据包就被假设为已丢失并进行重传。TCP用一个校验和函数来检验数据是否有错误,在发送和接收时都要计算校验和。

TCP协议的运行可划分为三个阶段:连接创建(connection establishment)、数据传送(data transfer)和连接终止(connection termination)。

其中连接创建和链接终止分别是三次握手和四次挥手

三次握手

1.客户端通过向服务器端发送一个SYN来创建一个主动打开,
  作为三次握手的一部分。客户端把这段连的序号设定为随机数A。

2.服务器端应当为一个合法的SYN回送一个SYN/ACK。ACK的确认码应为A+1,
  SYN/ACK包本身又有一个随机产生的序号B。

3.最后,客户端再发送一个ACK。此时包的序号被设定为A+1,而ACK的确认码则为B+1。
  当服务端收到这个ACK的时候,就完成了三次握手,并进入了连接创建状态。
           
TCP/IP协议简介及三次握手

如果服务器端接到了客户端发的SYN后回了SYN-ACK后客户端掉线了,服务器端没有收到客户端回来的ACK,那么,这个连接处于一个中间状态,即没成功,也没失败。于是,服务器端如果在一定时间内没有收到的TCP会重发SYN-ACK。在Linux下,默认重试次数为5次,重试的间隔时间从1s开始每次都翻倍,5次的重试时间间隔为1s, 2s, 4s, 8s, 16s,总共31s,第5次发出后还要等32s才知道第5次也超时了,所以,总共需要 1s + 2s + 4s+ 8s+ 16s + 32s = 63s,TCP才会断开这个连接。使用三个TCP参数来调整行为:tcp_synack_retries 减少重试次数;tcp_max_syn_backlog,增大SYN连接数;tcp_abort_on_overflow决定超出能力时的行为。

SYN_Flood攻击

根据建立连接的原理,攻击者可以通过发送SYN给服务端,然后下线,让服务器等63秒再断开连接。如此攻击者可以把SYN队列耗尽,正常的连接就无法处理。

在LINUX系统中,当SYN队列满时,通过tcp_syncookies参数回发SYN Cookie(源地址端口+目标地址端口+时间戳)。

正常的连接会回发SYN Cookie,直接建立连接

保活机制

当客户端和服务端建立连接后,非活动状态的时间超过keepalive_time,就会向对方发送保活探测报文,如果未收到响应则按照keepalive_intvl继续发送,发送次数为 keepalive_probes

tcp_keepalive_time:在TCP保活打开的情况下,最后一次数据交换到TCP发送第一个保活探测包的间隔,即允许的持续空闲时长,或者说每次正常发送心跳的周期,默认值为7200s(2h)。

tcp_keepalive_probes :在tcp_keepalive_time之后,没有接收到对方确认,继续发送保活探测包次数,默认值为9(次)

tcp_keepalive_intvl:在tcp_keepalive_time之后,没有接收到对方确认,继续发送保活探测包的发送频率,默认值为75s。

继续阅读