握手包下载 循序渐进搞懂 TCP 三次握手核心

在线wifi跑包 金刚包跑包 cap跑包 hccapx ewsa在线 就来 握手包跑包

各位好 又见面了 我是曹操 今天给大家带来一篇新的教程

希望各位细心学习 低调用网

握手包下载

引言:本文的目的是通过生动的例子和实际操作,将抽象的、虚拟的网络转化为具体的、可视化的形式。通过逐步掌握TCP三次握手的核心知识点,为深入学习TCP协议打下基础。

通俗版:如下图所示,小明(客户端)给小美(服务端)打电话,在经过互相询问和应答,确认通信畅通后,才开始愉快地聊天。(请注意,这个例子并不一定是完美的,主要是为了理解概念)

握手包下载握手包下载

细节版:一个TCP报文段分为首部和数据两部分,TCP的所有功能都体现在首部的各个字段中。

序列号:本报文段所发送数据的第一个字节的序号,在建立连接时会随机生成初始序列号ISN(Inital Sequence Number)。

确认号:下一次应该收到的数据的序列号,若确认号为N,则代表到序列号N-1为止的数据都已经正确收到。

控制位:

func main() {
  // 监听端口
  l, err := net.Listen("tcp", "0.0.0.0:8080")
  if err != nil {
    panic(err)
  }
  defer l.Close()
  for {
    // 接受连接
    conn, err := l.Accept()
    if err != nil {
      log.Printf("accept err: %sn", err)
      continue
    }
    go hello(conn)
  }
}
func hello(conn net.Conn) {
  defer conn.Close()
  buf := make([]byte, 1024)
  // 读数据
  if _, err := conn.Read(buf); err != nil {
    log.Printf("conn read err: %sn", err)
    return
  }
  log.Printf("%sn", string(buf))
  // 写数据
  if _, err := conn.Write([]byte("hello, xiao ming.n")); err != nil {
    log.Printf("conn write err: %sn", err)
    return
  }
}
echo -n "hello, xiao mei." | nc 81.68.197.93 8080

由于上述报文都未携带数据,即len=0,所以响应的ack等于请求的seq+1。

实战版:为了捕获比较纯净的数据包,我们实现了一个简单的TCP服务器,用于接收客户端的请求并进行回复。

客户端请求:

握手包下载握手包下载

使用Wireshark进行分析(统计-流量图),可以清楚地看到三次握手的过程。同时也可以看到序列号(seq)和确认号(ack)之间的关系。在握手成功后,发送了len=16的数据包,然后ack=17表示序列号在16之前的数据都已经正确接收。

注意:ISN是一个随机数,并不为0。为了显示更友好,Wireshark使用了相对序号。取消相对序号显示后,可以看到真正的序列号,例如Seq=3503481500。

握手包下载

# 使用 netstat 命令查看当前系统的 TCP 连接状态
$ netstat -t
Active Internet connections (w/o servers)
Proto Recv-Q Send-Q Local Address           Foreign Address         State
tcp        0      0 ubuntu:58824            39.156.66.18:http       TIME_WAIT
tcp        0      0 localhost:20172         localhost:37276         ESTABLISHED

握手包源文件下载地址

状态机:TCP所谓的面向连接本质上是客户端和服务端各自维护的一个”连接状态”。在三次握手期间,状态的变化如下:

LISTEN:服务端主动监听一个端口,等待客户端的连接请求

SYN-SENT:发送SYN包后的状态

SYN-RECEIVED:收到SYN包,并发送了SYN+ACK包后的状态

ESTABLISHED:连接建立成功

赞(0)