xiaohanliang
Network
Network
  • hi
  • LOWER
    • 0. arp决定下一跳
    • 1. dns决定终点
    • 2. [WIP]dns是不是真的有这些层级
  • MIDDLE
    • 0. 如何理解tcp握手的设计
    • 1. 诡异的tcp拆包现象
    • 2. tcp是一种高效的协议吗
    • 3. 为什么说没有人可以裸用tcp
    • 4. 尝试理解tcp的设计
    • 5. 连接建立@tcp调优
    • 6. 连接断开@tcp调优
    • 7. [WIP]拥塞控制@tcp调优
    • 8. 不需要这些花里胡哨的东西
    • 9. 怎么又是socket又是tcp
  • UPPER
    • 0. 为什么大家都用http
    • 1. [WIP]为什么http也keep-alive
    • 2. 如何保证pipeline的顺序到达
    • 3. 如何保证http的安全性
    • 4. 只不过https基于tls连接
    • 5. 怎么理解get/post
    • 6. http2为什么更快
    • 7. [WIP]内置加速的http3
    • 8. 怎样制造出实时效果-ws
    • 9. kcp是如何榨干你的带宽的
  • DEVICES
    • [302] 跳转到Linux网络设备
  • KUBERNETES NETWORK
    • [302] 跳转到容器网络
Powered by GitBook
On this page
  • 三次握手
  • 潜在的攻击点 - synrcvd
  • 四次挥手

Was this helpful?

  1. MIDDLE

0. 如何理解tcp握手的设计

Previous2. [WIP]dns是不是真的有这些层级Next1. 诡异的tcp拆包现象

Last updated 4 years ago

Was this helpful?

三次握手

(长话短说)为什么三次握手呢? 四次不说了, 因为你总是可以用更多的通话次数交流等量的信息. 而两次会是什么情况? 因为TCP报文里没有一个表示时间的字段:

  1. 这种设计导致我无从得知这个包是什么时候发出的, 你拿到这个syn包的时候只能选择接受与不接受.

  2. 如果对方发完syn包人就撤了, 或者这个包出于某种原因游荡太久才抵达, 对方看你没响应人撤了, 总之这个会话端口就是关了. 而你选择接受并进入established就绪状态, 最后就变成你在这里空等着的场面了. 利用这种特点我就可以让你开一大堆没用的session, 浪费你的资源.

  3. 但如果我们有第三次确认, 我等不到你人还在的确认, 默认60秒之后断开连接

潜在的攻击点 - synrcvd

但这种方式并不是万能的, 至少我能耗你60秒对吗? 这就够了具备这种特点我可以找一大堆肉鸡, 或者一台机器开无数端口让你maintain一大堆 syn-recv 的连接, 然后你的服务器基本就处于无法提供服务的状态 (瘫痪了就是), 假设现在东西卖的很便宜, 我想买但是我不让你买, 那我就令服务器上的链接除了我以外都是肉鸡, 60秒够了

我们可以通过netstat的方式看看现在挂了多少个连接, 分别处于什么状态, 如果能发现一大堆sync-recv基本就可以断言了, 因为正常情况下这种状态很快就会被就绪态覆盖掉了, 想要处理掉这种情况, 你可以把时间改短一点, 或者增长rcvd队列

四次挥手

两段: TCP是双向聊天的(双工的), 终结一个session需要双方都完事, 每一段都是(FIN,ACK)的pair . 每一个wait节点都标注了自己在等待 (想要得到) 什么

一个常见的问题是为什么需要TIMEWAIT以及为什么时长是2MSL:

  • 如果没有TIMEWAIT: 那么客户端也立刻终止这个端口, 稍后这个端口被拿来重新使用重新连接服务器, 如果这个时候一个服务器的包现在才到, 那么上一个session的包就进入了这次session

  • 如果没有TIMEWAIT: 那么你发完就关闭了, 而这个ACK包服务器却没收到, 那么服务器就卡在最后一个环节了, 等一会如果服务器没有收到最后一个ACK包, 它会重发FIN包的

  • 如果TIMEWAIT不是2MSL: 还是刚刚那个场景, 一个包在网络上飘荡的时间最长是2MSL, 如果你的TIMEWAIT小于2MSL那么同样可能接到这个包