TCP 协议

本贴最后更新于 2549 天前,其中的信息可能已经东海扬尘

TCP:可靠传输、按序到达。

一、TCP 报文段格式
源端口号(2byte)、目的端口号(2byte)
序列号(4byte)
ACKnum(4byte)
Offset(4bit)、Reserved(4bit)、TCP Flags(1byte)、Window(2byte)
Checksum(2byte)、...
...

二、三次握手

  1. 客户端向服务器发送连接建立请求报文段(Segement)(SYN=1,seq=x)(调用了 connect()方法),发送之后客户端进入 SYN_SEND 状态;
  2. 服务器收到客户端的请求报文段,向客户端发送一个 ACK 和连接建立请求结合在一起的报文段(ACK=1,ACKnum=x+1,SYN=1,seq=y),并从 LISTEN 状态(调用了 listen()方法)进入 SYN_RCVD 状态;
  3. 客户端收到 ACK 报文段后,向服务器发送一个 ACK 报文段(ACK=1,ACKnum=y+1),并进入 ESTABLISHED 状态;
  4. 服务器收到 ACK 报文段,也进入 ESTABLISHED 状态。
    至此,客户端和服务器的连接建立,之后就可以调用 read()和 write()方法进行读写操作了。

三、四次挥手

  1. 客户端向服务器发送连接关闭请求报文段(FIN=1,seq=x)(调用了 close()方法),发送之后客户端进入 FIN_WAIT_1 状态;
  2. 服务器收到客户端的请求报文段,向客户端发送 ACK 报文段(ACK=1,ACKnum=x+1),并进入 CLOSE_WAIT 状态;
  3. 客户端收到服务器的 ACK 报文段后进入 FIN_WAIT_2 状态;
  4. 服务器向客户端发送连接关闭请求报文段(FIN=1,seq=y)(调用了 close()方法),发送之后服务器进入 LAST_ACK 状态;
  5. 客户端收到服务器的请求报文段,向服务器发送 ACK 报文段(ACK=1,ACKnum=y+1),并进入 TIME_WAIT 状态;
  6. 服务器收到客户端的 ACK 报文段,进入 CLOSE 状态;
  7. 客户端等待 2MSL,期间没有收到服务端的连接关闭请求博爱文段,则进入 CLOSE 状态。
    至此,客户端与服务器的连接关闭。

MSL(Maxinum Segment Live)
TCP 报文在网络传输时最长生存时间。

客户端为什么要等待 2MSL
因为 ACK 报文段可能在网络传输的过程中丢失。如果发送了这种情况,那么服务器在等待 2MSL 时间后会重新一个连接关闭请求报文段,客户端在等待的这 2MSL 时间内正好可以收到这个请求报文段,于是重发 ACK 报文段,再等待 2MSL,重复这个过程直到在等待的 2MSL 时间内没有收到请求报文段,进入 CLOSE 状态。

SYN Flood 攻击
描述:给服务器发了一个 SYN 后,就下线了,于是服务器需要默认等 63s 才会断开连接,这样,攻击者就可以把服务器的 syn 连接的队列耗尽,让正常的连接请求不能处理。
解决方法:Linux 下给了一个叫 tcp_syncookies 的参数来应对这个事——当 SYN 队列满了后,TCP 会通过源地址端口、目标地址端口和时间戳打造出一个特别的 Sequence Number 发回去(又叫 cookie),如果是攻击者则不会有响应,如果是正常连接,则会把这个 SYN Cookie 发回来,然后服务端可以通过 cookie 建连接(即使你不在 SYN 队列中)。

三、确认机制
一种是确认收到的最大的连续收到的包。
一种是收到一个包去人一个包。

四、超时重传机制
一种是重传超时的包及其之后的包(因为接收端只确认了最大的连续收到的包),快,但浪费带宽。
一种是仅重传超时的包,慢,但节省带宽。

往返时间(RTT,Round Trip Time)
通过 RTT+ 算法(好几种)算出超时重传时间(RTO,Retransmission TimeOut)。

五、滑动窗口协议
window:还有多少缓冲区可以用。

发送端
LastByteAcked、LastByteSent、LastByteWriter
SendWindow、UsableWindow

接收器
LastByteRead、NextByteExpected、LastByteRcvd
...、ReceiveWindow
window=MaxRcvBuffer - LastByteRcvd – 1

六、拥塞控制
慢启动阈值(ssthresh,slow start threshold)

拥塞控制算法:
Tahoe:没有快速恢复阶段;
Reno:增加了快速恢复阶段。

1. 慢启动
拥塞窗口(cwnd,Congestion Window)。
①. 连接建立后初始化 cwnd=1;
②. 每当收到一个 ACK,cwnd++,呈线性上升;
③. 每过一个 RTT,cwnd*=2,呈指数上升;
④. 当 cwnd>=慢启动阈值时,将 cwnd 减半,进入拥塞避免算法;

2. 拥塞避免
①. 每收到一个 ACK,cwnd = cwnd + 1/cwnd;
②. 每过一个 RTT,cwnd += 1;

3. 快速重传
收到 3 个重复 ACK 就重传包,然后 cwnd = cwnd /2,ssthresh = cwnd, 进入快速恢复阶段。
(以前是等到超过超时重传时间 RTO 再重传包,然后 ssthresh = cwnd /2,cwnd 置为 1,重新进入慢启动。)

4. 快速恢复
快速恢复阶段认为,还有 3 个重复 ACK 说明网络并不那么糟糕,所以
①. cwnd = ssthresh + 3*MSS;
②. 重传重复 ACK 指定的包;
③. 如果再收到重复 ACK,直接 cwnd += 1;
④. 如果收到新的 ACK,那么 cwnd = ssthresh,然后进入拥塞避免算法。

这个快速恢复算法存在的问题就是它依赖于 3 个重复的 ACK。 注意,3 个重复的 ACK 并不代表只丢了一个数据包,很有可能是丢了好多包。但这个算法只会重传一个,而剩下的那些包只能等到 RTO 超时,于是,进入了恶 梦模式——超时一个窗口就减半一下,多个超时会超成 TCP 的传输速度呈级数下降,而且也不会触发快速恢复算法了。

相关帖子

回帖

欢迎来到这里!

我们正在构建一个小众社区,大家在这里相互信任,以平等 • 自由 • 奔放的价值观进行分享交流。最终,希望大家能够找到与自己志同道合的伙伴,共同成长。

注册 关于
请输入回帖内容 ...

推荐标签 标签

  • 大疆创新

    深圳市大疆创新科技有限公司(DJI-Innovations,简称 DJI),成立于 2006 年,是全球领先的无人飞行器控制系统及无人机解决方案的研发和生产商,客户遍布全球 100 多个国家。通过持续的创新,大疆致力于为无人机工业、行业用户以及专业航拍应用提供性能最强、体验最佳的革命性智能飞控产品和解决方案。

    2 引用 • 14 回帖
  • Netty

    Netty 是一个基于 NIO 的客户端-服务器编程框架,使用 Netty 可以让你快速、简单地开发出一个可维护、高性能的网络应用,例如实现了某种协议的客户、服务端应用。

    49 引用 • 33 回帖 • 22 关注
  • BookxNote

    BookxNote 是一款全新的电子书学习工具,助力您的学习与思考,让您的大脑更高效的记忆。

    笔记整理交给我,一心只读圣贤书。

    1 引用 • 1 回帖
  • 大数据

    大数据(big data)是指无法在一定时间范围内用常规软件工具进行捕捉、管理和处理的数据集合,是需要新处理模式才能具有更强的决策力、洞察发现力和流程优化能力的海量、高增长率和多样化的信息资产。

    93 引用 • 113 回帖
  • 小薇

    小薇是一个用 Java 写的 QQ 聊天机器人 Web 服务,可以用于社群互动。

    由于 Smart QQ 从 2019 年 1 月 1 日起停止服务,所以该项目也已经停止维护了!

    34 引用 • 467 回帖 • 742 关注
  • Java

    Java 是一种可以撰写跨平台应用软件的面向对象的程序设计语言,是由 Sun Microsystems 公司于 1995 年 5 月推出的。Java 技术具有卓越的通用性、高效性、平台移植性和安全性。

    3187 引用 • 8213 回帖
  • 外包

    有空闲时间是接外包好呢还是学习好呢?

    26 引用 • 232 回帖 • 2 关注
  • Redis

    Redis 是一个开源的使用 ANSI C 语言编写、支持网络、可基于内存亦可持久化的日志型、Key-Value 数据库,并提供多种语言的 API。从 2010 年 3 月 15 日起,Redis 的开发工作由 VMware 主持。从 2013 年 5 月开始,Redis 的开发由 Pivotal 赞助。

    286 引用 • 248 回帖 • 62 关注
  • 招聘

    哪里都缺人,哪里都不缺人。

    190 引用 • 1057 回帖
  • 安全

    安全永远都不是一个小问题。

    199 引用 • 816 回帖 • 1 关注
  • RESTful

    一种软件架构设计风格而不是标准,提供了一组设计原则和约束条件,主要用于客户端和服务器交互类的软件。基于这个风格设计的软件可以更简洁,更有层次,更易于实现缓存等机制。

    30 引用 • 114 回帖 • 1 关注
  • 电影

    这是一个不能说的秘密。

    120 引用 • 599 回帖
  • Love2D

    Love2D 是一个开源的, 跨平台的 2D 游戏引擎。使用纯 Lua 脚本来进行游戏开发。目前支持的平台有 Windows, Mac OS X, Linux, Android 和 iOS。

    14 引用 • 53 回帖 • 531 关注
  • DevOps

    DevOps(Development 和 Operations 的组合词)是一组过程、方法与系统的统称,用于促进开发(应用程序/软件工程)、技术运营和质量保障(QA)部门之间的沟通、协作与整合。

    47 引用 • 25 回帖 • 1 关注
  • 开源中国

    开源中国是目前中国最大的开源技术社区。传播开源的理念,推广开源项目,为 IT 开发者提供了一个发现、使用、并交流开源技术的平台。目前开源中国社区已收录超过两万款开源软件。

    7 引用 • 86 回帖
  • SpaceVim

    SpaceVim 是一个社区驱动的模块化 vim/neovim 配置集合,以模块的方式组织管理插件以
    及相关配置,为不同的语言开发量身定制了相关的开发模块,该模块提供代码自动补全,
    语法检查、格式化、调试、REPL 等特性。用户仅需载入相关语言的模块即可得到一个开箱
    即用的 Vim-IDE。

    3 引用 • 31 回帖 • 99 关注
  • RabbitMQ

    RabbitMQ 是一个开源的 AMQP 实现,服务器端用 Erlang 语言编写,支持多种语言客户端,如:Python、Ruby、.NET、Java、C、PHP、ActionScript 等。用于在分布式系统中存储转发消息,在易用性、扩展性、高可用性等方面表现不俗。

    49 引用 • 60 回帖 • 362 关注
  • HHKB

    HHKB 是富士通的 Happy Hacking 系列电容键盘。电容键盘即无接点静电电容式键盘(Capacitive Keyboard)。

    5 引用 • 74 回帖 • 471 关注
  • SOHO

    为成为自由职业者在家办公而努力吧!

    7 引用 • 55 回帖 • 18 关注
  • 持续集成

    持续集成(Continuous Integration)是一种软件开发实践,即团队开发成员经常集成他们的工作,通过每个成员每天至少集成一次,也就意味着每天可能会发生多次集成。每次集成都通过自动化的构建(包括编译,发布,自动化测试)来验证,从而尽早地发现集成错误。

    15 引用 • 7 回帖 • 1 关注
  • V2EX

    V2EX 是创意工作者们的社区。这里目前汇聚了超过 400,000 名主要来自互联网行业、游戏行业和媒体行业的创意工作者。V2EX 希望能够成为创意工作者们的生活和事业的一部分。

    17 引用 • 236 回帖 • 328 关注
  • 以太坊

    以太坊(Ethereum)并不是一个机构,而是一款能够在区块链上实现智能合约、开源的底层系统。以太坊是一个平台和一种编程语言 Solidity,使开发人员能够建立和发布下一代去中心化应用。 以太坊可以用来编程、分散、担保和交易任何事物:投票、域名、金融交易所、众筹、公司管理、合同和知识产权等等。

    34 引用 • 367 回帖
  • HTML

    HTML5 是 HTML 下一个的主要修订版本,现在仍处于发展阶段。广义论及 HTML5 时,实际指的是包括 HTML、CSS 和 JavaScript 在内的一套技术组合。

    107 引用 • 295 回帖
  • React

    React 是 Facebook 开源的一个用于构建 UI 的 JavaScript 库。

    192 引用 • 291 回帖 • 384 关注
  • Quicker

    Quicker 您的指尖工具箱!操作更少,收获更多!

    32 引用 • 130 回帖 • 2 关注
  • LaTeX

    LaTeX(音译“拉泰赫”)是一种基于 ΤΕΧ 的排版系统,由美国计算机学家莱斯利·兰伯特(Leslie Lamport)在 20 世纪 80 年代初期开发,利用这种格式,即使使用者没有排版和程序设计的知识也可以充分发挥由 TeX 所提供的强大功能,能在几天,甚至几小时内生成很多具有书籍质量的印刷品。对于生成复杂表格和数学公式,这一点表现得尤为突出。因此它非常适用于生成高印刷质量的科技和数学类文档。

    12 引用 • 54 回帖 • 63 关注
  • 一些有用的避坑指南。

    69 引用 • 93 回帖