サービス名に対応するポート番号や、ポート番号に対応するサービス名を調べたいときは、getent servicesを使う。プロトコル名とプロトコル番号の対応は、getent protocolsで調べられる。

$ getent services https
https                 443/tcp
$ getent services 22/tcp
ssh                   22/tcp
$ getent protocols tcp
tcp                   6 TCP

getent servicesは/etc/services、getent protocolsは/etc/protocolsの内容を/etc/nsswitch.confに従って引く。実行例はUbuntu 24.04(glibc 2.39)のもの。

サービス名からポート番号を調べる

引数にサービス名を渡すと、ポート番号とプロトコルが表示される。

$ getent services http
http                  80/tcp www

出力は「サービス名、ポート番号/プロトコル、別名」の順である。wwwはhttpの別名で、別名でも引ける。

$ getent services www
http                  80/tcp www

ポート番号だけを取り出すには、awkで/の前の部分を切り出す。

$ getent services https | awk '{split($2,a,"/"); print a[1]}'
443

複数のサービス名を並べることもできる。

$ getent services http https ssh
http                  80/tcp www
https                 443/tcp
ssh                   22/tcp

ポート番号からサービス名を調べる

引数にポート番号/プロトコルを渡すと、サービス名を引ける。

$ getent services 22/tcp
ssh                   22/tcp
$ getent services 53/udp
domain                53/udp

サービス名だけを取り出すには、1列目を切り出す。

$ getent services 443/tcp | awk '{print $1}'
https

プロトコルを省略して、ポート番号だけを渡すこともできる。同じポート番号にTCPとUDPがある場合は、先に登録されているエントリが返る。/etc/servicesではTCPが先に書かれている。

$ getent services 53
domain                53/tcp

サービス名でもプロトコルを指定できる。サービス名/プロトコルの形式にする。

$ getent services domain/udp
domain                53/udp

getent services ssh tcpのように空白で区切ると、tcpが別のサービス名として扱われる。tcpというサービスは無いので、終了コードが2になる。

$ getent services ssh tcp
ssh                   22/tcp
$ echo $?
2

存在しないサービスは終了コード2になる

存在しないサービス名やポート番号では、何も表示されず終了コードが2になる。

$ getent services nosuch
$ echo $?
2
$ getent services 65000/tcp
$ echo $?
2

独自のサービスを登録して引く

/etc/servicesに行を追加すると、getent servicesで引けるようになる。

$ echo "myapp 9000/tcp" | sudo tee -a /etc/services
$ getent services myapp
myapp                 9000/tcp
$ getent services 9000/tcp
myapp                 9000/tcp

全件を一覧する

引数を省略すると、すべてのエントリが表示される。

$ getent services | head -4
tcpmux                1/tcp
echo                  7/tcp
echo                  7/udp
discard               9/tcp sink null
$ getent services | wc -l
318

エントリの件数は、環境によって異なる。

grep /etc/servicesとの違い

/etc/servicesをgrepすると、行末のコメントや複数のタブも含めて、行がそのまま表示される。getent servicesは、空白を整えて表示する。

$ grep -E '^https\s' /etc/services
https		443/tcp				# http protocol over TLS/SSL
https		443/udp				# HTTP/3

getent services httpsは、最初に見つかったhttps 443/tcpの1行だけを返す。

/etc/nsswitch.confでは、services: db filesのようにfiles以外の参照元も指定される。getent servicesは、/etc/servicesに無くても、他の参照元にあれば見つけられる。特定の参照元だけで調べたいときは、-sオプションを使う。

参考: 【getent】参照元を指定して取得する (-s)

最小のコンテナでは何も表示されない

ubuntu:24.04などの最小のコンテナイメージには、/etc/servicesと/etc/protocolsが無い。getent servicesとgetent protocolsは、何も表示せず終了コード2になる。

$ getent services http
$ echo $?
2
$ ls /etc/services /etc/protocols
ls: cannot access '/etc/services': No such file or directory
ls: cannot access '/etc/protocols': No such file or directory

2つのファイルは、netbaseパッケージに含まれる。apt-get install netbaseで入れると、引けるようになる。

プロトコル名とプロトコル番号を調べる

getent protocolsは、プロトコル名またはプロトコル番号を引数に取る。

$ getent protocols tcp
tcp                   6 TCP
$ getent protocols 17
udp                   17 UDP
$ getent protocols icmp
icmp                  1 ICMP

出力は「プロトコル名、プロトコル番号、別名」の順である。別名のTCPのように、大文字の名前でも引ける。

$ getent protocols TCP
tcp                   6 TCP

番号だけを取り出すには、2列目を切り出す。

$ getent protocols tcp | awk '{print $2}'
6

引数を省略すると、すべてのプロトコルが表示される。存在しないプロトコルは、getent servicesと同じく終了コード2になる。

$ getent protocols | head -4
ip                    0 IP
hopopt                0 HOPOPT
icmp                  1 ICMP
igmp                  2 IGMP
$ getent protocols nosuch
$ echo $?
2