网络阻塞问题分析二

明白,你希望我给出一个 100%详细、可执行、覆盖 CPU/内核/TCP/应用的排查流程,可以判断 HTTP 响应慢的原因(机器负载、网络不稳、业务阻塞),并且每一项都明确列出 观测指标、方法、命令、判断依据,特别强调对 业务进程延迟和网络延迟的影响。下面我整理成系统化指南。


HTTP 响应慢排查指南(CPU / TCP / 网络 / 应用)


1️⃣ 采集 TCP 栈函数耗时(内核态耗时分析)

目的:量化 TCP/IP 内核处理耗时,判断 CPU 对网络延迟影响

方法 A:ftrace function_graph(内核自带)

# 1. 开启 function_graph tracer
echo function_graph > /sys/kernel/debug/tracing/current_tracer

# 2. 设置 TCP 栈关键函数过滤
echo tcp_v4_do_rcv > /sys/kernel/debug/tracing/set_ftrace_filter
echo tcp_rcv_established >> /sys/kernel/debug/tracing/set_ftrace_filter
echo tcp_sendmsg >> /sys/kernel/debug/tracing/set_ftrace_filter
echo tcp_cleanup_rbuf >> /sys/kernel/debug/tracing/set_ftrace_filter
echo tcp_ack >> /sys/kernel/debug/tracing/set_ftrace_filter

# 3. 开启 tracing
echo 1 > /sys/kernel/debug/tracing/tracing_on

# 4. 发起 HTTP 请求进行采样
curl -s http://yourserver/endpoint

# 5. 查看 trace 输出
cat /sys/kernel/debug/tracing/trace_pipe

观察指标及判断

指标观测方法判断依据对延迟影响
TCP 栈函数耗时 trace_pipe 或 trace 文件中每个函数耗时 函数耗时占 CPU 总时间 > 50% 内核 TCP 处理慢 → Send-Q / Recv-Q 堆积 → 网络延迟增加
函数调用堆栈深 trace 文件 call graph 函数多层调用且耗时长 CPU 处理 HTTP 请求前的 TCP 数据积压

方法 B:perf record / perf report(采样分析)

# 采样系统内核态 CPU
perf record -e cycles:k -a -g sleep 10
perf report
  • 检查 tcp_sendmsg, tcp_cleanup_rbuf, tcp_v4_do_rcv 等函数耗时

  • 判断依据

    • 内核函数占比高 → CPU 内核成为瓶颈 → HTTP 响应慢由机器负载导致

    • 函数耗时低 → TCP 内核处理正常 → 延迟可能由网络或业务逻辑导致


2️⃣ 采集 CPU 各核使用率

目的:判断 CPU 是否成为网络延迟或业务延迟瓶颈

方法

# 每秒采集各核使用率
mpstat -P ALL 1

# 关键字段:
# %usr  -> 用户态占用,应用逻辑处理占 CPU 时间
# %sys  -> 内核态占用,内核 TCP/IP 处理耗时
# %soft -> 软中断占用,网络处理相关
# %iowait -> I/O 等待,磁盘/网络 I/O 阻塞
# %idle -> 空闲

判断 TCP 网络延迟影响

CPU 指标观察方法影响判断
%sys 高 mpstat 内核态 CPU 占用高 → TCP 栈处理慢 → Send-Q/Recv-Q 堆积 → 网络延迟增加
%soft 高 mpstat + /proc/softirqs NET_RX / NET_TX 高 → 网络软中断 CPU 成瓶颈 → HTTP 数据包处理慢
单核 %sys/%soft 高 mpstat 分核 CPU 不均衡 → 某核成为瓶颈 → 队列堆积、HTTP OK 延迟增加

判断业务延迟影响

CPU 指标观察方法影响判断
%usr 高 mpstat 用户态占用高 → 应用处理慢 → HTTP handler 延迟增加
%iowait 高 mpstat I/O 阻塞 → HTTP 响应慢
%idle 低 mpstat CPU 饱和 → 业务处理受限

3️⃣ 采集 TCP 队列、RTT、cwnd、重传

目的:量化网络状况对 HTTP 响应延迟的影响

方法

# 每秒采集
ss -ti

关键字段说明:

字段含义判断依据
Recv-Q 接收队列长度 队列堆积 → 应用未及时读 → 业务延迟
Send-Q 发送队列长度 队列持续堆积 → 内核或应用阻塞 → 网络延迟
rtt 平均 RTT RTT 高 → 网络不稳
cwnd 拥塞窗口 cwnd 缩小 → 网络拥塞
retrans 重传段 retrans 多 → 网络丢包 → HTTP 延迟增加

分析逻辑

  1. 队列堆积 + %sys/%soft 高 → CPU/内核瓶颈 → 网络延迟

  2. RTT 高 + retrans 多 + CPU 不高 → 网络不稳 → 网络延迟

  3. Send-Q 高 + %usr 高 → 应用处理慢 → 业务延迟


4️⃣ 采集应用 handler latency / 线程状态

目的:判断业务逻辑是否导致 HTTP 响应慢

方法 A:Web 服务器慢日志

  • Nginx:

log_format latency '$remote_addr $request_time $upstream_response_time';
access_log /var/log/nginx/access.log latency;
  • Go HTTP:

start := time.Now()
// handle request
elapsed := time.Since(start)
log.Printf("handler latency: %v", elapsed)

方法 B:线程阻塞状态

语言/工具命令观察指标判断依据
Linux strace -p -tt -T -e trace=write,read,send,recv syscall 耗时 syscall 阻塞 → 应用延迟
Go go tool pprof http://localhost:6060/debug/pprof/goroutine RUNNABLE / IO_WAIT goroutine 阻塞 → handler 延迟
Java jstack RUNNABLE / WAITING 线程阻塞 → handler 延迟

5️⃣ 软/硬中断影响观察(网络延迟)

# 软中断统计
cat /proc/softirqs | grep NET_RX
cat /proc/softirqs | grep NET_TX

# NIC 中断
cat /proc/interrupts

判断依据

  • NET_RX / NET_TX 占用高 → CPU 内核成为网络处理瓶颈 → HTTP 响应延迟

  • 中断在单核集中 → 处理能力受限 → 网络延迟增加


6️⃣ 综合判断逻辑

HTTP 响应慢
    |
    |-- TCP 栈函数耗时占内核CPU高 + TCP 队列堆积 → 机器负载瓶颈
    |-- RTT 高 / retrans 多 + CPU 不高 → 网络不稳
    |-- Send-Q 堆积 + 用户态 handler latency 高 → 业务逻辑阻塞
场景核心指标判断依据延迟类型
机器负载瓶颈 %sys/%soft 高 + TCP 栈耗时高 + 队列堆积 内核处理 TCP 数据慢 网络延迟
网络不稳 RTT 高 + retrans 多 + 队列正常 TCP 拥塞/丢包 网络延迟
业务阻塞 %usr 高 + Send-Q 堆积 + handler latency 高 应用处理慢 / 阻塞 业务延迟

7️⃣ 建议观测流程

  1. 每秒采集 CPU 各核 (mpstat -P ALL 1)

  2. 每秒采集 TCP 队列/RTT/cwnd/retrans (ss -ti)

  3. Trace TCP 栈函数耗时 (ftraceperf)

  4. 采集应用 handler latency / 线程阻塞 (strace / pprof / jstack)

  5. 观察软/硬中断 NET_RX/NET_TX (/proc/softirqs / /proc/interrupts)

  6. 结合表格判断延迟来源


💡 总结

  • 网络延迟来源:内核 TCP 栈处理慢(机器负载) 或 网络拥塞/丢包(RTT/retrans)

  • 业务延迟来源:应用处理慢 / 阻塞 (%usr 高 + handler latency 高 + Send-Q 堆积)

  • CPU 使用率与延迟关系

    • %sys/%soft 高 → 网络延迟

    • %usr 高 → 业务延迟

    • %iowait 高 → I/O 阻塞延迟


如果你需要,我可以帮你写一个 完整自动化采集脚本

  • 每秒采集:

    • TCP 栈函数耗时

    • CPU 各核 us/sy/soft/iowait

    • TCP 队列 / RTT / cwnd / retrans

    • 应用 handler latency

  • 输出 CSV

  • 自动标记延迟来源(机器负载 / 网络 / 业务阻塞)


我可以直接写这个脚本,你想让我写吗?

posted on 2025-12-26 14:07  吃草的青蛙  阅读(1)  评论(0)    收藏  举报

导航