4

我通常使用fuser命令来检查打开某个 tcp 端口的 pid,如下所示

fuser 22/tcp //To get pid opening the 22 tcp port

我有一个运行嵌入式 linux 的参考板。它已经为 ssh 连接打开了 22 个 tcp 端口。但是 fuser 不显示任何关于 22 端口的输出。所以我尝试了另一个 ssh 守护进程来打开 322 端口,然后尝试使用 fuser 检查 pid,它工作正常。

root@imx6qsabreauto:~# netstat -nlt | grep 22
tcp        0      0 0.0.0.0:4224            0.0.0.0:*               LISTEN
tcp        0      0 0.0.0.0:322             0.0.0.0:*               LISTEN
tcp        0      0 :::322                  :::*                    LISTEN
tcp        0      0 :::22                   :::*                    LISTEN

root@imx6qsabreauto:~# fuser 322/tcp
351

root@imx6qsabreauto:~# ps -ef | grep 351
root       351     1  0 01:46 ?        00:00:00 /usr/sbin/dropbear -r /etc/dropbear/dropbear_rsa_host_key -p 322 -B

root       379   315  0 02:11 ttymxc3  00:00:00 grep 351


root@imx6qsabreauto:~# fuser 22/tcp
==> This output nothing !!

如何确定哪个进程正在打开 tcp 22 端口。(在板上,lsof 命令不可用,并且.. netstat 没有 -p 选项。)

4

4 回答 4

3

我已经/proc安装了bash并且readlink都安装了,你可以编写一个解析的小 bash 脚本/proc/net/tcp,并扫描/proc/*/fd/以找到相应的套接字。

我对嵌入式 linux 不是很熟悉,但是如果你找不到readlink,它可能包含在busybox.

/proc/net/tcp是这样的

sl  local_address rem_address   st tx_queue rx_queue tr tm->when retrnsmt   uid  timeout inode
0: 00000000:4E7A 00000000:0000 0A 00000000:00000000 00:00000000 00000000     0        0 13128 1 ffff8800cf960740 99 0 0 10 0

是的local_address十六进制字符串HOST:PORT,因此脚本:0016会在您要搜索 tcp 22 端口时进行搜索。

一旦找到包含:0016in的行local_addressinode就是对应的套接字号。

然后它使用命令搜索/proc/*/fd/*哪个具有套接字号。readlink

#!/bin/bash
PORT="$1"
HEX_PORT=$(printf %04X $PORT)
INODE=""
if ! [ "$PORT" ];then
  echo "usage $0 [PORT]"
  exit
fi
while read num host_port _ _ _ _ _ _ _ inode _; do
  if [[ $host_port =~ :"$HEX_PORT"$ ]];then
    INODE=$inode
  fi
done < /proc/net/tcp
if ! [ "$INODE" ];then
  echo "no process using $PORT"
  exit
fi
for fn in /proc/[1-9]*/fd/*; do
  if [ "$(readlink $fn)" = "socket:[$INODE]" ];then
    tmp=${fn%/fd*}
    echo ${tmp#/proc/}
  fi
done
于 2015-06-10T03:06:32.570 回答
2

这是在 Tomato/BusyBox 路由器上运行的 ymonad 脚本的一个版本:

#!/bin/sh

# This works with BusyBox on a Tomato router

PORT="$1"
HEX_PORT=`printf %04X $PORT`
INODE=""
if ! [ "$PORT" ]; then
    echo "Find the process that is listening on an open TCP network port."
    echo "usage $0 [PORT]"
    exit 2
fi
# sl localip:port remip:port st tx_q:rx_q tr:when retrns uid timeout inode ...
while read num host_port _ _ _ _ _ _ _ inode _; do
    port=`echo "$host_port" | awk -F: '{print $2}'`
    if [ "$port" = "$HEX_PORT" ]; then
        INODE=$inode
    fi
done < /proc/net/tcp
if ! [ "$INODE" ]; then
    echo "no process using $PORT"
    exit 1
fi
echo "found inode $INODE"
f=`ls -l /proc/[1-9]*/fd/* 2>/dev/null | fgrep "socket:[$INODE]" | awk '{print $9}'`
if ! [ "$f" ] ; then
    echo "no process found using inode $INODE"
    exit 1
fi
pid=`echo "$f" | awk -F/ '{print $3}'`
echo "Process matching PID=$pid:"
ps w | awk "\$1==$pid {print}"
于 2018-06-17T00:28:30.347 回答
1

如果您拥有或可以ss使用您的设备,它可以向您显示 PID:

ss -ltp # for TCP
ss -lup # for UDP
于 2019-08-09T16:30:43.697 回答
0

谢谢@ymonad!:) 正如您所提到的,我已经能够获得与端口相对应的 pid,如下所示。

root@imx6qsabreauto:~# cat /proc/net/tcp
  sl  local_address rem_address   st tx_queue rx_queue tr tm->when retrnsmt   uid  timeout inode

   0: 00000000:1080 00000000:0000 0A 00000000:00000000 00:00000000 00000000     0        0 1018 1 d8d90a00 100 0 0 10 0

   1: 00000000:0DA2 00000000:0000 0A 00000000:00000000 00:00000000 00000000     0        0 842 1 d8d90000 100 0 0 10 0

   2: 00000000:006F 00000000:0000 0A 00000000:00000000 00:00000000 00000000     0        0 2515 1 d8dc8000 100 0 0 10 0

   3: 0100007F:0035 00000000:0000 0A 00000000:00000000 00:00000000 00000000     0        0 877 1 d8d90500 100 0 0 10 0

root@imx6qsabreauto:~# cat /proc/net/tcp6
  sl  local_address                         remote_address                        st tx_queue rx_queue tr tm->when retrnsmt   uid  timeo
ut inode
   0: 00000000000000000000000000000000:006F 00000000000000000000000000000000:0000 0A 00000000:00000000 00:00000000 00000000     0
 0 2518 1 d8dd0000 100 0 0 10 -1
   1: 00000000000000000000000001000000:0035 00000000000000000000000000000000:0000 0A 00000000:00000000 00:00000000 00000000     0
 0 881 1 d8de0000 100 0 0 10 -1
   2: 00000000000000000000000000000000:0016 00000000000000000000000000000000:0000 0A 00000000:00000000 00:00000000 00000000     0
 0 4933 1 d8da0000 100 0 0 10 -1

您的 shell 脚本工作正常,它可以正确获取 pid,如下所示。

root@imx6qsabreauto:~# /tmp/find.sh 22
1

奇怪的是结果 pid 是 1。它是 init 进程;;

UID        PID  PPID  C STIME TTY          TIME CMD
root         1     0  0 04:21 ?        00:00:04 /sbin/init

我想我需要更多地弄清楚 init 进程如何打开 22 tcp 端口。真的很谢谢你。:D 我学到了很多。再次感谢 !!

于 2015-06-10T04:37:20.407 回答