Linux守护进程随机卡顿,栈信息显示卡在do_sys_poll如何排查?
问题解答
1. 是否意味着进程卡在do_sys_poll?
是的。从/proc/<pid>/stack的调用栈可以看到,进程当前的执行路径停留在do_sys_poll函数中;再结合strace -cp <pid>的统计结果(poll系统调用占比99.97%的CPU时间),说明进程在do_sys_poll中消耗了绝大多数运行时间,确实是卡在这个函数上了。
2. do_sys_poll的作用是什么?
do_sys_poll是Linux内核中处理用户空间poll()/ppoll()系统调用的核心实现函数,主要作用是:
- 监听多个文件描述符的I/O事件(包括可读、可写、异常等类型)
- 阻塞进程,直到至少一个被监听的文件描述符触发了目标事件,或者到达设置的超时时间后返回
- 给用户空间返回触发事件的文件描述符列表,让应用程序可以针对性处理I/O操作
简单说,它是实现多路I/O复用的内核层核心逻辑,很多网络服务、异步I/O程序都会依赖它来高效管理多个I/O通道。
3. 如何排查卡顿原因?
步骤1:确定poll监听的文件描述符
- 用
lsof -p <pid>列出进程打开的所有文件描述符,记录下类型(比如IPv4/IPv6对应网络套接字,FIFO对应管道,REG对应普通文件)和关联的资源信息 - 用
strace -T -p <pid>实时追踪系统调用,-T参数会显示每个poll调用的耗时,同时可以看到poll传入的文件描述符集合和超时时间参数
步骤2:检查目标文件描述符的状态
- 如果是网络套接字:用
ss -tunp | grep <pid>查看对应套接字的连接状态(比如ESTABLISHED/CLOSE_WAIT/TIME_WAIT),检查远端服务是否正常响应、网络链路是否通畅,或者是否存在半开连接未被处理 - 如果是管道/套接字对:检查管道另一端的进程是否正常运行(用
ps aux查找关联进程),是否出现挂起、崩溃导致数据无法传递 - 如果是磁盘文件:用
iostat -x查看磁盘IO负载,dmesg检查是否有磁盘读写错误,确认是否是磁盘IO阻塞导致poll等待
步骤3:验证poll的超时配置
通过strace -p <pid>观察poll调用的超时参数:
- 如果超时设置为无限(比如参数为
-1),那么在没有I/O事件触发时,进程会一直阻塞在do_sys_poll中 - 如果超时设置合理但仍长期阻塞,说明被监听的描述符始终没有触发预期的I/O事件
步骤4:排查系统级资源问题
- 用
vmstat查看系统内存、CPU、磁盘IO的整体状态,确认是否存在资源耗尽(比如内存不足导致swap频繁、CPU负载过高) - 用
cat /proc/<pid>/limits检查进程的资源限制(比如最大文件描述符数),确认是否因为资源不足导致I/O异常 - 查看
dmesg和系统日志(/var/log/messages或journalctl),排查是否有内核层面的错误或警告
步骤5:结合应用日志分析
查看应用自身的运行日志,定位是否存在业务逻辑层面的问题:比如某个请求发送后一直未收到响应、某个I/O操作未正确处理异常导致进程持续等待事件触发
内容的提问来源于stack exchange,提问作者Komal
相关产品推荐
相关产品推荐

