2. 端口概念回顾:TCP/UDP端口号、端口范围划分、端口与进程关系、端口状态详解
聊QUIC排查之前,咱们得先把端口这件事儿掰扯清楚。我见过太多人一上来就抓包、看日志,折腾半天发现连端口号是干嘛的都没搞明白。说白了,端口就是操作系统给网络进程分配的门牌号。
你想想看,一台服务器上跑着几十个服务,数据包到了网卡之后,系统怎么知道该交给谁?靠的就是端口号。IP地址找到机器,端口号找到进程,就这么简单。
2.1 端口号的范围划分
端口号是个16位的数字,范围从0到65535。这个范围被分成了三段,每段的用途不一样。我刚开始做运维那会儿,经常搞混这些段,后来踩了几次坑才记住。
| 范围 | 分类 | 说明 | 典型例子 |
|---|---|---|---|
| 0 - 1023 | 系统端口(Well-Known Ports) | 需要root权限才能绑定,留给标准服务 | HTTP(80)、HTTPS(443)、DNS(53) |
| 1024 - 49151 | 注册端口(Registered Ports) | 用户进程可用,IANA登记过的服务 | MySQL(3306)、Redis(6379) |
| 49152 - 65535 | 动态/私有端口(Dynamic/Private Ports) | 临时使用,客户端随机分配 | 浏览器发请求时的临时端口 |
2.2 TCP与UDP端口的核心差异
很多人以为端口就是端口,TCP和UDP没区别。其实不是。TCP和UDP的端口空间是独立的。什么意思?就是TCP 443和UDP 443是两个不同的门,可以绑定不同的服务。
QUIC用的是UDP,这一点特别重要。我遇到过好几次,有人把QUIC的端口占用问题当成TCP端口冲突去查,方向完全错了。
| 特性 | TCP端口 | UDP端口 |
|---|---|---|
| 连接状态 | 有状态(ESTABLISHED、LISTEN等) | 无状态(只有绑定和未绑定) |
| 端口复用 | SO_REUSEADDR需要谨慎使用 | SO_REUSEPORT常见于多进程模型 |
| 端口扫描 | 三次握手可探测 | 无握手,探测难度大 |
| 典型应用 | HTTP、SSH、数据库连接 | DNS、QUIC、视频流 |
2.3 端口与进程的关系
端口本身不干活,干活的是进程。端口只是进程和网络之间的一个绑定关系。你可以把进程想象成一个公司,端口就是公司的前台电话。数据包打进来,前台(端口)转给对应的部门(进程)。
在Linux上,查看端口和进程的关系,最常用的命令就是ss和lsof。我个人习惯用ss,因为它更快,而且输出更清晰。
# 查看所有UDP监听端口及其对应的进程
ss -ulnp
# 查看特定端口(比如443)的占用情况
ss -ulnp sport = :443
# 查看进程ID对应的端口
ss -ulnp | grep 'pid=1234'
输出示例:
State Recv-Q Send-Q Local Address:Port Peer Address:Port Process
UNCONN 0 0 0.0.0.0:443 0.0.0.0:* users:(("quic-server",pid=1234,fd=7))
这里要注意,UDP的State列显示的是UNCONN,表示未连接状态。TCP的监听状态是LISTEN,这是两者在端口状态上的一个明显区别。
2.4 端口状态详解
端口状态这个概念,TCP和UDP差别很大。TCP有完整的状态机,UDP就简单得多。咱们先看TCP的,再看UDP的。
2.4.1 TCP端口状态
TCP端口的状态其实反映的是连接的状态。一个端口可以同时处于多个连接中,每个连接都有自己的状态。但端口本身也有一个监听状态。
| 状态 | 含义 | 常见场景 |
|---|---|---|
| LISTEN | 端口正在监听,等待连接 | 服务端启动后,等待客户端连接 |
| ESTABLISHED | 连接已建立,正在通信 | 客户端与服务器正常通信 |
| TIME_WAIT | 主动关闭方等待2MSL | 大量短连接场景,端口被占用 |
| CLOSE_WAIT | 被动关闭方等待应用关闭 | 程序bug,忘记关闭连接 |
| FIN_WAIT1/2 | 主动关闭方等待确认 | 正常关闭过程中的中间状态 |
ss -ulnp先确认端口是否在监听,然后用QUIC自带的连接管理命令查看内部连接状态。
2.4.2 UDP端口状态
UDP端口的状态就简单多了。它只有两种:
- UNCONN:端口已绑定,等待接收数据。这是UDP监听端口的正常状态。
- 未绑定:端口没有被任何进程使用。
UDP没有连接状态,因为UDP本身是无连接的。数据来了就收,收完就完事。但QUIC在UDP之上实现了自己的连接状态机,所以排查QUIC问题时,你需要同时关注UDP端口层和QUIC连接层。
2.5 端口占用的本质
端口占用,说白了就是某个进程已经绑定了这个端口,其他进程不能再绑定同一个端口(除非设置了端口复用选项)。
我遇到过最典型的场景:重启QUIC服务时,旧进程还没完全退出,新进程启动时发现端口被占用,直接报错退出。这时候用ss -ulnp | grep :443一看,发现旧进程还在,等几秒再试就好了。
2.6 本章知识体系
下面这张图把端口相关的核心概念串起来了,方便你快速回顾。
端口概念是排查QUIC问题的地基。地基不稳,后面所有排查手段都是空中楼阁。记住三点:UDP端口独立于TCP、端口绑定的是进程不是服务、UDP端口状态只有UNCONN。把这三点刻在脑子里,后面章节的排查思路才能用得上。