服务器与大带宽专家 · 持牌IDC/CDN/ISP服务商
简米科技官网JIANMI TECH
资讯 2026-10-23 简米科技 4,603 字 11 分钟阅读

服务器被占用怎么办?,服务器进程占用资源怎么快速排查释放?

导读服务器被占用,本质上就是某个进程霸占了端口、CPU、内存或磁盘资源,解决办法是先通过命令锁定进程PID,再根据情况kill或优化配置;下面按最常见的几种占用场景逐一拆解,服务器端口被占用怎么解决?先锁定进程再释放端口遇到端口被占用,很多人第一反应是重启应用,结果提示端口已在使用,其实端口本身不会“被占用”,是某……

服务器被占用,本质上就是某个进程霸占了端口、CPU、内存或磁盘资源,解决办法是先通过命令锁定进程PID,再根据情况kill或优化配置;下面按最常见的几种占用场景逐一拆解。

服务器端口被占用怎么解决?先锁定进程再释放端口

遇到端口被占用,很多人第一反应是重启应用,结果提示端口已在使用,其实端口本身不会“被占用”,是某个进程在监听,你需要做的是找到这个进程。

用lsof命令快速揪出端口的主人

lsof是Linux下定位端口占用的首选工具,假设你启动Nginx时发现80端口被占用:

lsof -i:80

输出里会显示COMMAND、PID、USER等字段,重点看PID那一列,比如得到PID为2345,接着用:

ps -p 2345 -f

就能看到具体是什么程序,路径和启动参数一目了然,确认是无关进程后,直接结束它:

kill -9 2345

如果lsof没装,可以用替代方案,很多精简系统默认不带lsof,这时用netstat更稳妥。

netstat的备用方案:一条命令看清监听状态

netstat -tunlp | grep 80

参数含义:-t显示TCP,-u显示UDP,-n直接显示IP和端口,-l列出监听状态,-p显示PID和程序名,输出最后一列就是PID/Program name,比如2345/nginx。

实战中经常遇到一个情况:端口明明没进程监听,启动时却报“Address already in use”,这往往是TCP连接处于TIME_WAIT状态,旧连接还没完全释放,对于高并发服务,TIME_WAIT本身是正常现象,但如果数量过大,可以用系统调优加快回收,而不是盲目kill,行业共识认为,调整net.ipv4.tcp_fin_timeout和tcp_tw_reuse需要谨慎,线上环境不建议直接开启tcp_tw_recycle,因为NAT环境下会导致连接异常。

端口被占用时,如何判断能不能直接杀掉

不是所有占用端口的进程都能随手kill,比如杀掉sshd会让远程连接断开,杀掉数据库进程会导致数据损坏风险,判断思路是:先看进程属性和父进程,再决定操作,用:

ps -ef | grep 2345

如果进程是别人正在跑的任务,最好先确认,如果确认是残留的僵尸进程或旧服务实例,再执行kill。

服务器CPU占用率高怎么排查?从top到系统调用

CPU被占满时,服务器明显卡顿,网站响应变慢,排查思路是:先看全局,再锁定线程,最后深入进程内部。

top命令的正确打开方式:先按CPU排序

运行top,进入交互界面后,按大写的P键,进程列表会立刻按CPU使用率从高到低排列,第一屏顶部几行是整体负载,下面就是吃CPU的进程。

需要注意的是,top里的CPU占用是瞬时值,有的短时进程一闪而过,如果你看到top里没有异常进程,但服务器负载(load average)很高,这就麻烦了。

用ps辅助找出那些“快闪”进程

负载高但top花屏,多数是短生命周期进程太多,用ps抓一个时间点:

ps aux --sort=-%cpu | head -20

这条命令按CPU占用率排序,显示前20个进程,执行两次,间隔几秒,对比看哪些进程出现次数最多,如果频繁出现php-fpm或java进程,说明它们在被频繁调用。

另一个常用技巧是用top -b -n 5批量采样,把结果重定向到文件分析,避免交互界面刷屏,对于命名的进程,如果能看到CPU超过100%,说明它使用了多核,不一定是坏事,要看服务是否健康。

CPU被某个进程占满时,怎么进一步定位问题

假如一个Python脚本CPU占用率高达200%,需要知道它在执行什么操作,用strace跟踪系统调用:

strace -p PID -o output.txt

观察一段时间后,如果大量出现write、read、epoll_wait,说明它在频繁读写IO;如果出现密集的clock_gettime,可能是忙等,业内专家指出,线上生产环境使用strace要格外小心,它会拖慢被跟踪进程,适合在低峰期临时使用。

如果是Java应用,单靠top不够,因为线程可能共享进程,需要用:

top -H -p PID

显示所有线程再排序,或者用jstack PID抓线程栈,查找状态为RUNNABLE且CPU耗时最高的线程ID,转成十六进制后去jstack里匹配,这套组合拳是Java服务CPU排查的标准动作。

服务器内存占用过高解决方法:free与ps组合定位

内存和CPU不同,它只增不减,如果进程有内存泄漏,你会看到free里的available数值一路下滑,最终触发OOM Killer。

先用free -m读取真实内存状态

执行:

free -m

输出里的total是总内存,used是已用,free是空闲,buff/cache是缓存,很多人一看used高就紧张,其实Linux把用不完的内存用作缓存,available才是应用程序实际可用的内存,判断内存是否真的紧张,重点看available是否接近0,以及swap使用率是否持续上升。

ps锁定内存大户:按%MEM排序

ps aux --sort=-%mem | head -15

这个命令和CPU排序类似,不过关键词换成--sort=-%mem,对于长期占用高内存的进程,先记录PID,再观察几天内的趋势,比如一个Node.js应用昨天占用2GB,今天变4GB,连续走高,基本可以判定内存泄漏。

swap占用异常时怎么办

如果swap使用率一直很高,说明物理内存确实不够,此时有两种选择:快速腾出内存,或者增加内存,快速腾出内存的办法是重启占用最多的服务,但这会导致短暂不可用,更好的做法是设置服务的内存限制,比如JVM的-Xmx参数,或者PHP-FPM的pm.max_children,控制单个进程的内存天花板,据统计,很多线上故障都是因为没设置内存上限,导致进程无限吃内存,最终整机宕机。

磁盘空间和IO占用排查:资源释放的最后一块拼图

服务器不只被CPU和内存牵制,磁盘满了照样让服务异常,尤其日志文件、临时文件、数据库binlog,都可能在不知不觉中写满磁盘。

df与du配合使用,找出占空间的元凶

先看整体磁盘情况:

df -h

发现某个分区使用率接近100%,就得定位具体目录,进入该分区的根目录,执行:

du -sh  | sort -rh | head -10

按大小排序,一步一层往下找,常见大头是/var/log下的日志、/tmp下的临时文件、/home下的用户数据,删除前确认文件是否还在被占用,尤其是正在写入的大日志文件。

文件被删除但空间不释放的典型处理

你有没有遇到这种情况:du显示删除了一个大日志,但df依然显示磁盘满,原因是文件被某进程打开了,删除只是解除了目录项,但进程还持有文件句柄,用:

lsof | grep deleted

找到持有已删除文件的进程PID,然后重启或kill该进程,如果是nginx这类长期运行的进程,直接kill会导致服务中断,可以先让nginx重新打开日志,再把旧句柄释放,比如执行kill -USR1 $(cat /var/run/nginx.pid)让nginx重开日志文件,这是一种平滑处理方式。

磁盘IO占用排查

当应用响应慢,但CPU和内存都正常,很可能是磁盘IO卡死了,用iostat -x 1观察%util,如果接近100%,磁盘已经在满负荷工作,更直观的是iotop,实时显示哪个进程读写磁盘最多,和top一样,iotop也支持按列排序,按p键按进程名显示,找到IO大户后,检查它的读写频率是否合理。

释放服务器资源的常用指令与日常预防

排查是手段,释放是目的,但释放资源不是只有kill三板斧,合理的管理方式能帮你避免下次再被占用。

kill的等级:从温和到强制

  • kill PID:发SIGTERM信号,让进程自己退出,允许清理资源。
  • kill -9 PID:发SIGKILL信号,强制杀死,不给清理机会。
  • pkill -f 进程名:按名称匹配杀死一组进程,比如pkill -f "php artisan queue"。

一般情况下,先尝试普通kill,等几秒看进程是否消失,如果它不响应,再使用kill -9,对批量重启服务的场景,可以用killall,但要谨慎,它会杀掉所有同名进程。

设置资源限制,防止单个进程失控

Linux提供了ulimit,可以限制进程使用的文件数、CPU时间和内存大小,比如限制单个用户可最大打开文件数:

ulimit -n 65535

但更重要的是在启动服务时使用systemd或cgroup限制资源,例如在systemd服务文件里添加:

MemoryLimit=2G
CPUQuota=80%

这样即使程序内部有Bug,也不会让整个服务器的CPU和内存被占满,行业共识认为,容器化部署(Docker)是天然的隔离方案,通过docker run -m 2g --cpus=2直接给容器设资源上限,比事后kill更靠谱。

日常监控:提前发现占用苗头

靠手动命令排查永远是被动的,建议部署基础监控,至少覆盖CPU、内存、磁盘四项核心指标,用cron定期执行ps和free,把结果输出到日志,或者用现成的监控工具(比如Prometheus+Grafana、Zabbix),设置告警阈值,当指标异常时第一时间收到告警,而不是等用户投诉后才登录服务器。

服务器被占用怎么办?三个高频问题解答

问题1:端口被占用但kill不掉,怎么办?

如果提示kill -9也无法结束,进程可能处于不可中断的睡眠状态(D state),多发生在等待磁盘IO时,这时候先检查磁盘是否故障,或者重启服务器,对于普通的僵死进程,用ps -ef | grep defunct找到,然后杀掉其父进程就能被系统回收。

问题2:服务器负载高,但top里看不到明显的CPU进程,是怎么回事?

负载(load average)不只是CPU算出来的,它还包含不可中断的IO等待(D state进程),如果负载很高但CPU使用率低,问题多半出在磁盘IO或网络等待上,用vmstat 1观察b列(阻塞的进程数),如果持续大于0,说明IO瓶颈,排查方向转向磁盘读写。

问题3:Java服务经常占用大量内存,如何避免?

给JVM设置合理的堆内存上限,比如-Xms2g -Xmx2g,让最大堆和初始堆一致,减少动态扩容带来的波动,同时配置-XX:+HeapDumpOnOutOfMemoryError,在OOM发生时自动导出堆转储文件,方便事后分析,对非核心服务,可以考虑限制容器内存额度,让OOM提前触发而不是拖垮整个机器。

服务器被占用并不可怕,可怕的是毫无章法地乱杀进程,先看端口再看CPU/内存,最后查磁盘IO,用命令一步步定位PID,你就有了一张清晰的战场地图,学会这些排查方法,下次再遇到“服务器被占用怎么办”的问题,就能稳稳拿出解决方案了。

分享本文
本文为 简米科技官网 原创,已由运维技术专家审核。转载请注明来源:原文链接
售前咨询 服务热线 售后 邮箱