Nginx 不直接记录“缓冲区溢出”,但通过“client intended to send too large body”“request header or cookie too large”“upstream sent too big header”三类错误精准指示请求体、请求头、响应头缓冲区超限,并需结合access.log时间戳、状态码及系统资源交叉验证。

Linux Nginx 本身不会直接记录“缓冲区溢出”字样,但会在 error.log 中留下明确的行为线索——这些不是漏洞报警,而是缓冲机制触发保护性拒绝后的日志痕迹。关键在于识别三类典型警告,并结合上下文判断溢出发生的位置(请求头、请求体、响应头、响应体或日志写入链路)。
看 error.log 里这三类高频错误提示
打开 /var/log/nginx/error.log,用 grep 快速筛查:
-
“client intended to send too large body”:说明客户端 POST/PUT 数据超过
client_max_body_size限制,Nginx 在读取阶段主动拒绝,属于请求体缓冲区防护触发; -
“request header or cookie too large”:表示请求头(含 Host、Cookie、Authorization 等)超出
large_client_header_buffers总容量,是请求头解析层的缓冲拦截; -
“upstream sent too big header”:后端返回的响应头(如 Set-Cookie 过长、自定义 Header 过多)超出了
proxy_buffer_size,代理层拒绝接收完整响应头,属响应头缓冲不足。
区分是真实溢出还是配置误配
单条报错不等于系统异常,需确认是否集中爆发、是否关联特定接口或用户行为:
Linux 安全审计工具,检查 SSH 配置、开放/监听端口、防火墙规则(ufw/iptables/nftables)、失败登录尝试、sudoers 权限...
- 若只在上传大文件接口(如 /api/upload)反复出现 “client intended…” 错误,大概率是
client_max_body_size设得太小,而非内存泄漏; - 若所有请求都报 “request header too large”,检查是否客户端(如前端 SDK)错误拼接了重复 Cookie 或带了调试用的超长 X-Trace-ID;
- 若仅某几个 upstream 出现 “upstream sent too big header”,应查后端服务是否返回了异常大的响应头(比如未压缩的 JWT、嵌套多层的调试头),而不是盲目调大
proxy_buffer_size。
配合 access.log 和时间戳交叉验证
找到 error.log 中某条警告的时间点(如 [error] 12345#0: *6789 client intended to send too large body),再查同一秒附近的 access.log:
- 对应请求是否确实是大 Body?看
$body_bytes_sent和$request_length字段,后者包含请求头+体长度,若远超配置值(如设了 10M 却显示 15M),就是真实超限; - 是否伴随 413 状态码?这是 Nginx 主动拒绝的 HTTP 状态,与上述错误严格对应;
- 是否同一 worker 进程 PID(日志中
*6789前的数字)在前后几分钟内还报过accept() failed (24: Too many open files)或worker process X exited on signal 9?若有,说明该 worker 已内存紧张,缓冲行为可能已失稳,需进一步查 dmesg 和内存使用。
注意日志自身缓冲导致的“假静默”
如果发现高并发下部分请求完全没进 access.log,但 error.log 也没报错,可能是日志写入缓冲区未 flush 就被进程终止(如 OOM kill):
- 检查
access_log指令是否用了buffer=64k flush=3s,没加 buffer 的默认 8k 容易积压; - 搜索 error.log 中是否有
reopen log或reopening logs记录,若出现在 reload 后而非 logrotate USR1 之后,说明日志句柄切换时缓冲丢失; - 用
lsof -p $(cat /var/run/nginx.pid) | grep log查当前 worker 打开的日志文件 inode,对比磁盘上实际文件 inode,不一致即存在轮转错位风险。

















