核心思路是让无效或低质量连接尽早退出,通过 ssl_handshake_timeout 5s、client_header_timeout 8s、keepalive_timeout 25s、reset_timedout_connection on 实现快速超时断连;用 limit_conn_zone 限制单 IP 并发连接数;以 limit_req_zone 控制请求速率;关闭高开销 TLS 特性如 TLS 1.0/1.1 和 RSA 密钥交换。

核心思路是让无效或低质量连接尽早退出,不占用 CPU、内存、文件描述符等关键资源。Nginx 无法拦截原始 TCP 包,但能通过四层控制快速识别并切断异常行为。
收紧 TLS 握手与连接超时
SSL/TLS DoS 攻击常靠“卡住握手”耗尽 CPU,比如发一半 ClientHello 就停住。必须用精准超时逼它暴露:
- ssl_handshake_timeout 5s:仅 Nginx 1.19.0+ 支持,强制 TLS 握手必须在 5 秒内完成,超时直接断连
-
client_header_timeout 8s:HTTPS 连接建立后,客户端须在 8 秒内发完全部请求头(含
\r\n\r\n),防 Slow Headers - keepalive_timeout 25s:长连接保持时间不宜过长,25 秒可平衡复用效率与空闲连接积压风险
- reset_timedout_connection on:对超时连接发 RST 而非 FIN,更快释放内核连接状态,减少 TIME_WAIT
限制单 IP 并发连接数
攻击者常并发发起数千个 TLS 连接,哪怕每个只存活几秒,也能迅速占满 worker 进程的连接池:
- 在
http块定义限连区域:limit_conn_zone $binary_remote_addr zone=conn_per_ip:10m; - 在
server或location中启用:limit_conn conn_per_ip 15;(建议值 10–20,视业务而定) - 配合
limit_conn_log_level warn和limit_conn_status 429,便于监控和明确反馈
压制高频请求节奏
应用层洪水(如 HTTP Flood)会吃光后端处理能力,需用漏桶机制平滑入流:
- 定义请求速率区:
limit_req_zone $binary_remote_addr zone=req_rate:10m rate=30r/m;(即每分钟 30 次) - 在关键路径(如登录、搜索、API 入口)启用:
limit_req zone=req_rate burst=10 nodelay; - burst 值设为 10 可容忍短时脉冲,nodelay 避免排队延迟,超限立即返回 503
关闭高开销 TLS 特性
某些密码套件(如 RSA 密钥交换)或协议版本(TLS 1.0)在握手阶段 CPU 消耗极高,应主动禁用:
-
ssl_protocols TLSv1.2 TLSv1.3;(禁用 TLS 1.0/1.1) -
ssl_ciphers ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256;(优先 ECDSA/ECDHE,禁用 RSA 密钥交换) -
ssl_prefer_server_ciphers off;(让客户端选更优 cipher,而非服务端强制低效套件)


















