Linux端口进程查找与终止教程

Linux端口进程查找与终止教程

文章目录

概述

本文档记录了在Linux系统中如何查找并终止占用特定端口(如5501)的进程的完整流程。适用于需要释放被占用的端口、终止无响应服务或清理异常进程等场景。

问题场景

需要终止占用5501端口的进程,但系统中常用的网络命令(如netstatlsofss等)不可用。

环境信息

  • 操作系统:Linux (Debian)
  • 可用命令pscatgreppython3等基础命令
  • 目标端口:5501

完整操作流程

第一步:确认端口被占用

使用Python脚本检测端口是否被占用:

bash 复制代码
python3 -c "
import socket

sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
result = sock.connect_ex(('127.0.0.1', 5501))
if result == 0:
    print('Port 5501 is in use')
else:
    print('Port 5501 is not in use')
sock.close()
"

输出结果

复制代码
Port 5501 is in use

第二步:查找端口对应的Socket Inode

端口号在/proc/net/tcp文件中以十六进制格式存储。5501的十六进制为157D

bash 复制代码
cat /proc/net/tcp | grep -i 157D

输出结果

复制代码
   4: 00000000:157D 00000000:0000 0A 00000000:00000000 00:00000000 00000000     0        0 1990512643 1 0000000000000000 100 0 0 10 0                
  25: 0100007F:8562 0100007F:157D 06 00000000:00000000 03:0000085A 00000000     0        0 0 3 0000000000000000

字段解析

字段位置 字段名称 示例值 说明
第1个 local_address 00000000:157D 本地地址(IP:端口),157D = 5501
第2个 rem_address 00000000:0000 远程地址
第3个 st 0A 连接状态(0A=Listening)
第10个 inode 1990512643 Socket Inode(关键字段)

十六进制端口对照表

十进制 十六进制
5501 157D
22 0016
80 0050
443 01BB
8080 1F90

第三步:查找Inode对应的进程PID

遍历所有进程的fd目录,找到对应socket inode的进程:

bash 复制代码
for pid in $(ls /proc | grep -E '^[0-9]+$'); do
  if [ -d "/proc/$pid/fd" ]; then
    for fd in /proc/$pid/fd/*; do
      if [ -L "$fd" ]; then
        link=$(readlink "$fd" 2>/dev/null)
        if [[ "$link" == *"socket:[1990512643]"* ]]; then
          echo "Found PID: $pid"
          kill -9 $pid 2>/dev/null && echo "Killed process $pid"
        fi
      fi
    done
  fi
done

输出结果

复制代码
Found PID: 246253
Killed process 246253

第四步:验证端口已释放

bash 复制代码
python3 -c "
import socket

sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
result = sock.connect_ex(('127.0.0.1', 5501))
if result == 0:
    print('Port 5501 is still in use')
else:
    print('Port 5501 is now FREE')
sock.close()
"

输出结果

复制代码
Port 5501 is now FREE

原理说明

/proc/net/tcp 文件结构

Linux系统通过 /proc/net/tcp 文件提供TCP连接信息:

复制代码
sl  local_address rem_address   st tx_queue rx_queue tr tm->when retrnsmt   uid  timeout inode
  • local_address:本地IP地址和端口
  • inode:Socket inode号,是查找进程的关键
  • st:连接状态(06=TIME_WAIT, 0A=LISTEN, 01=ESTABLISHED)

进程与Socket的关联

Linux中所有进程信息都在/proc/目录下:

  • /proc/[PID]/fd/:进程打开的文件描述符
  • 每个fd是一个指向实际文件或socket的符号链接
  • socket链接格式:socket:[inode_number]

查找流程图

确认端口被占用
读取/proc/net/tcp获取inode
遍历/proc/*/fd/查找对应inode
找到对应PID
使用kill -9终止进程
验证端口已释放

常用替代方法

方法1:使用 lsof(如果可用)

bash 复制代码
lsof -i :5501
kill -9 $(lsof -t -i :5501)

方法2:使用 netstat(如果可用)

bash 复制代码
netstat -tlnp | grep 5501
kill -9 <PID>

方法3:使用 ss(如果可用)

bash 复制代码
ss -tlnp | grep 5501
kill -9 <PID>

方法4:使用 fuser(如果可用)

bash 复制代码
fuser -k 5501/tcp

方法5:使用泊坞窗(如果可用)

bash 复制代码
docker ps --format "{{.Ports}}" | grep 5501
docker stop <CONTAINER_ID>

完整Python脚本

以下是一个完整的Python脚本,可以直接使用:

python 复制代码
#!/usr/bin/env python3
"""
根据端口号查找并终止对应进程
用法: python3 kill_port.py <端口号>
"""

import subprocess
import sys
import re

def port_to_hex(port):
    """将端口号转换为十六进制"""
    return format(int(port), 'X').zfill(4).upper()

def find_inode(port):
    """查找端口对应的inode"""
    hex_port = port_to_hex(port)
    try:
        with open('/proc/net/tcp', 'r') as f:
            lines = f.readlines()
            for line in lines[1:]:  # 跳过标题行
                parts = line.split()
                if len(parts) > 9:
                    local_addr = parts[1]
                    if f':{hex_port}' in local_addr:
                        return parts[9]
    except Exception as e:
        print(f"Error reading /proc/net/tcp: {e}")
    return None

def find_pid_by_inode(inode):
    """根据inode查找进程PID"""
    try:
        # 遍历所有进程的fd目录
        result = subprocess.run(['ls', '/proc'], capture_output=True, text=True)
        pids = re.findall(r'\d+', result.stdout)
        
        for pid in pids:
            fd_dir = f'/proc/{pid}/fd'
            try:
                result = subprocess.run(['ls', '-l', fd_dir], capture_output=True, text=True)
                if f'socket:[{inode}]' in result.stdout:
                    return pid
            except:
                continue
    except Exception as e:
        print(f"Error finding PID: {e}")
    return None

def kill_process(pid):
    """终止进程"""
    try:
        subprocess.run(['kill', '-9', pid])
        return True
    except Exception as e:
        print(f"Error killing process: {e}")
        return False

def check_port(port):
    """检查端口是否被占用"""
    import socket
    sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
    result = sock.connect_ex(('127.0.0.1', int(port)))
    sock.close()
    return result == 0

def main():
    if len(sys.argv) != 2:
        print(f"用法: {sys.argv[0]} <端口号>")
        sys.exit(1)
    
    port = sys.argv[1]
    
    print(f"正在查找占用端口 {port} 的进程...")
    
    # 检查端口是否被占用
    if not check_port(port):
        print(f"端口 {port} 未被占用")
        sys.exit(0)
    
    # 查找inode
    inode = find_inode(port)
    if not inode:
        print(f"无法找到端口 {port} 对应的inode")
        sys.exit(1)
    
    print(f"找到 inode: {inode}")
    
    # 查找PID
    pid = find_pid_by_inode(inode)
    if not pid:
        print(f"无法找到占用端口 {port} 的进程")
        sys.exit(1)
    
    print(f"找到进程 PID: {pid}")
    
    # 终止进程
    if kill_process(pid):
        print(f"成功终止进程 {pid}")
        
        # 验证端口已释放
        if not check_port(port):
            print(f"端口 {port} 已成功释放")
        else:
            print(f"警告: 端口 {port} 仍被占用")
    else:
        print(f"终止进程失败")

if __name__ == '__main__':
    main()

使用方法

bash 复制代码
chmod +x kill_port.py
python3 kill_port.py 5501

注意事项

  1. 权限问题 :终止进程可能需要root权限,使用sudo或以root用户运行
  2. 进程依赖:终止进程可能影响依赖该服务的其他功能
  3. 数据保存:确保已保存重要数据,避免强制终止导致数据丢失
  4. 系统进程:不要终止系统关键进程(如sshd、supervisord等)

常见问题

Q: 为什么lsof、netstat、ss等命令不可用?

A: 在某些精简的Linux系统中,这些命令默认未安装。可以使用Python脚本作为替代方案。

Q: 如何查看进程信息?

bash 复制代码
ps aux | grep <PID>
cat /proc/<PID>/cmdline

Q: 如何查看端口对应的服务?

bash 复制代码
cat /proc/<PID>/comm
cat /proc/<PID>/status

参考资料

更新日志

日期 版本 描述
2026-04-19 1.0 初始版本,记录5501端口进程终止流程
相关推荐
busy dog~乌鸦~2 小时前
【THM-题目答案】:Web Fundamentals-How The Web Works-DNS in Detail: Domain Hierarchy
运维·web安全·网络安全·系统安全
奇妙之二进制3 小时前
zmq源码分析之own_t
服务器·网络
北山有鸟3 小时前
【学习笔记】MIPI CSI-2 协议全解析:从底层封包到像素解析
linux·驱动开发·笔记·学习·相机
mounter6253 小时前
深度解析:Linux 内核为何要移除“直接映射” (Direct Map)?
linux·运维·服务器·security·linux kernel·direct mem map
AC赳赳老秦4 小时前
HR必备:OpenClaw批量筛选简历、发送面试通知,优化招聘流程
运维·人工智能·python·eclipse·github·deepseek·openclaw
NineData4 小时前
NineData亮相香港国际创科展InnoEX 2026,以AI加速布局全球市场
运维·后端
another heaven4 小时前
【Docker/虚拟机 深度对比Docker与虚拟机:原理、区别与最佳使用场景】
运维·docker·容器
带娃的IT创业者4 小时前
零停机迁移:如何将服务器成本从 $1432 降至 $233
运维·服务器·网络·成本优化·服务器迁移·零停机·hetzner
bugu___4 小时前
Linux系统、网络知识点回顾1
linux·网络