TCP/IP 协议栈

一、OSI 七层 vs TCP/IP 四层

OSI 七层                TCP/IP 四层            协议
─────────────────────────────────────────────────
应用层                ─┐
表示层                 ├─ 应用层           HTTP/SSH/DNS/MQTT
会话层                ─┘
传输层                   传输层           TCP/UDP
网络层                   网络层           IP/ICMP/ARP
数据链路层             ─┐
物理层                  ├─ 网络接口层       Ethernet/Wi-Fi
                      ─┘

二、Linux 网络栈结构

应用 socket
  ↓
BSD Socket 层
  ↓
INET Socket(TCP/UDP)
  ↓
TCP / UDP
  ↓
IP
  ↓
邻居子系统(ARP / ND)
  ↓
Netdev 子系统
  ↓
网络设备驱动
  ↓
网卡硬件

三、关键协议

1. ARP(地址解析)

2. IP(Internet Protocol)

3. ICMP(Internet Control Message Protocol)

4. UDP(User Datagram Protocol)

5. TCP(Transmission Control Protocol)

四、TCP 三次握手 / 四次挥手

三次握手

Client                    Server
   |  --- SYN(seq=x) -->   |
   |  <-- SYN+ACK(seq=y, ack=x+1) |
   |  --- ACK(ack=y+1) ->   |
   |                        |
连接建立

四次挥手

Client                    Server
   |  --- FIN -->          |
   |  <-- ACK ---          |
   |  <-- FIN ---          |
   |  --- ACK -->          |
   |                        |
连接关闭

五、TCP 状态机

LISTEN → SYN_RCVD → ESTABLISHED → FIN_WAIT_1 → FIN_WAIT_2 → TIME_WAIT → CLOSED
                          ↑                ↓
                       SYN_SENT     CLOSE_WAIT

TIME_WAIT 持续 2 × MSL(60s~240s),防止最后 ACK 丢失。

六、TCP 关键参数

/proc/sys/net/ipv4/tcp_*
tcp_keepalive_time           默认 7200s
tcp_keepalive_intvl          默认 75s
tcp_keepalive_probes         默认 9 次
tcp_max_syn_backlog          SYN 队列长度
tcp_fin_timeout               FIN 超时
tcp_tw_reuse                  TIME_WAIT 复用(客户端)
tcp_tw_recycle                已废弃
tcp_max_tw_buckets            TIME_WAIT 数量上限
tcp_slow_start_after_idle     空闲后慢启动
tcp_window_scaling            窗口缩放
tcp_timestamps                时间戳

七、内核网络配置

# 查看 TCP 状态
netstat -ant | awk '{print $6}' | sort | uniq -c
ss -s

# IP 配置
ip addr add 192.168.1.100/24 dev eth0
ip link set eth0 up
ip route add default via 192.168.1.1

# DNS
echo "nameserver 8.8.8.8" > /etc/resolv.conf

# 接口信息
ethtool eth0
mii-tool eth0

八、内核结构

// 主要结构
struct sock {
    // ...
    struct sk_buff_head sk_receive_queue;
    struct sk_buff_head sk_write_queue;
    // ...
};

struct inet_sock {
    struct sock sk;
    __be32 inet_saddr;       // 源 IP
    __be32 inet_daddr;       // 目的 IP
    __be16 inet_sport;       // 源端口
    __be16 inet_dport;       // 目的端口
    // ...
};

struct tcp_sock {
    struct inet_sock inet;
    // 滑动窗口、拥塞控制、序列号等
    u32 snd_una;             // 未确认
    u32 snd_nxt;             // 下一个发送
    u32 rcv_nxt;             // 下一个期望
    // ...
};

九、TCP 连接数

理论上限:
- 客户端:受 fd 限制
- 服务端:受 fd、内存、端口限制(65535)

实际:
- 服务端 ~10k 连接(默认配置)
- 调优后 ~100k(需要大内存)

十、嵌入式 TCP/IP 栈

适用场景:
- 没有 MMU 的 MCU
- 不跑 Linux 的小芯片
- 资源极有限

十一、调试

tcpdump -i eth0 -nn
tcpdump -i eth0 port 80
tcpdump -i eth0 host 192.168.1.100 and tcp
tshark -i eth0 -Y 'tcp.port == 80'
ss -ant
ss -tinp

十二、内核 netstat

# /proc/net/tcp
# /proc/net/udp
# /proc/net/unix (Unix domain)
# /proc/net/arp
# /proc/net/route