はじめに
こんにちは。T.H.です。
掲題通りssもnetstatも入っていないLinuxでポートの使用状況を把握する手順を記載します。
背景
Dockerによって最小構成のLinuxを使用することもあるため、1周まわってほぼ何も入っていないLinuxに触れる機会が増えてきました。
そういった状況でポートの競合が発生した場合の調査やプロセスkillなどが必要な場合を想定しています。
手順
ポートを使用しているプロセスを確認する
/proc/net/tcpに必要な情報が記載されています。表示してみましょう。
細かい仕様は
https://www.kernel.org/doc/Documentation/networking/proc_net_tcp.txt
や、man procで読めます。
ここではWSL Ubuntuで実施していきます。
$ cat /proc/net/tcpcat
sl local_address rem_address st tx_queue rx_queue tr tm->when retrnsmt uid timeout inode
0: 0100007F:18EB 00000000:0000 0A 00000000:00000000 00:00000000 00000000 113 0 334 1 0000000000000000 100 0 0 10 0
1: 3600007F:0035 00000000:0000 0A 00000000:00000000 00:00000000 00000000 101 0 5865 1 0000000000000000 100 0 0 10 5
st=0AがLISTENのポートです。
例の場合は2件portをListenしている状態となります。
local_addressの値が<ID>:<PORT>となっています。ですがこのままだと読みにくいため、下記のようにして一旦なじみのある表示に変換してみましょう。
port
local_addressの右側18EBを10進変換
$ printf "%d\n" 0x18EB
6379
IP
IPアドレスも一応確認しておきましょう。
0100007Fを2バイトずつ逆順に読みます。
7F/00/00/01
↓
127.0.0.1
ポートを使用しているプロセスを特定する
プロセスは/proc/<PID>/fdinfo/<FD>のファイル内にinodeが記載されているためそこから検索します。
ここではsudoを使用していますが、psが入っていない環境の場合、sudoもなくrootで入ることも多いでしょう。適宜読み替えてください。
$ inode=334
$ sudo grep -R "ino:\s*$inode" /proc/[0-9]*/fdinfo 2>/dev/null
/proc/504/fdinfo/6:ino: 334
この場合"504"がプロセスIDです。
なお、/proc/504/fdinfo/6の中身は下記のようになっています。
$ sudo cat /proc/504/fdinfo/6
pos: 0
flags: 02004002
mnt_id: 9
ino: 334
プロセス名は/proc/<PID>/commや/proc/<PID>/cmdlineに記載されています。
$ sudo cat /proc/504/comm
redis-server
これで必要な情報はそろいました。状況に応じてkillなど実行するとよいでしょう。
最後に
以上、限定的な状況でしか使いませんが、知っていれば役立つかもしれない知識でした。何かの参考になれば幸いです。