hana_shinのLinux技術ブログ

Linuxの技術情報を掲載しています。特にネットワークをメインに掲載していきます。

DNSSECコマンドの使い方

1 はじめに

1.1 DNSSEC(DNS Security Extensions)とは?

DNSSECは、キャッシュDNSサーバの問い合わせに対して、以下を検証する仕組みです。
・応答が正当な権威DNSサーバからのものであること(真正性)
・応答が権威DNSサーバからの送信後に改ざんされていないこと(完全性)
DNSSECは、キャッシュポイズニングなどの攻撃によってキャッシュDNSサーバのキャッシュが改ざんされ、クライアントが意図しないサーバに誘導されるリスクを防ぐために使用します。ここでは、DNSSECで使うコマンドの使い方を説明します。なお、キャッシュDNSサーバと権威DNSサーバの関係は、digコマンドの使い方 - hana_shinのLinux技術ブログを参照してください。

1.2 DNSSECで使用するコマンド

DNSSECでは、以下のコマンドを使います。

コマンド 用途
dnssec-keygen ZSK(*1),KSK(*2)を作成するコマンドです。ZSK,KSKはそれぞれ秘密鍵、公開鍵のペアからなります。つまり、4つの鍵が存在します
dnssec-signzone ZSK,KSKを使ってゾーンファイルに署名するコマンドです
dnssec-dsfromkey DSレコードを作成するコマンドです。DSリソースレコードは、KSK公開鍵のハッシュ値を含む情報です。自ゾーンのKSK公開鍵を検証するために上位の権威DNSサーバに登録します

(*1) Zone Signing Key(ゾーン署名鍵)
(*2) Key Signing Key(鍵署名鍵)

ZSK,KSKの用途は以下のとおりです。

名称 用途
ZSK ゾーンファイルのリソースレコードに署名をするために使用します
KSK ZSKに署名するために使用します

2 検証環境

プライマリーサーバのAlmaLinux版数は以下のとおりです。

[root@primary ~]# cat /etc/redhat-release
AlmaLinux release 9.1 (Lime Lynx)

カーネル版数は以下のとおりです。

[root@primary ~]# uname -r
5.14.0-162.6.1.el9_1.x86_64

3 ZSK,KSKの作成方法

ZSK,KSKはdnssec-keygenコマンドを使って作成します。コマンドの書式は以下のとりです。

dnssec-keygen [オプション] ドメイン名

オプションの意味は以下のとおりです。

オプション 意味
-f KSK:KSKを作成するときに指定します
REVOKE:作成した鍵を無効化するときに指定します
未指定:ZSKを作成する場合、オプションを指定する必要はありません
-a 暗号アルゴリズムを指定します。RSASHA1, NSEC3RSASHA1, RSASHA256, RSASHA512, ECDSAP256SHA256, ECDSAP384SHA384, ED25519, ED448のいずれかを指定します
-b 鍵のサイズ(bit)を指定するオプションです。オプションを指定しなければデフォルトの鍵サイズが使用されます。たとえば、ゾーンの署名に使うRSAの場合1024(bit)、鍵の署名に使うRSAの場合2048(bit)になります
RSASHA1:1024~4096
NSEC3RSASHA1:1024~4096
-K(大文字) ZSK,KSKを作成するディレクトリを指定するオプションです
-n 鍵のオーナタイプを指定するオプションです。 ZONE,HOST,ENTITY,USER ,OTHERのいずれかを指定します

3.2 KSKの作成方法

KSKを作成します。

[root@primary ~]# dnssec-keygen -f KSK -a RSASHA256 -b 1024 -K /var/named/keys -n zone abc.test
Generating key pair............++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ .............++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Kabc.test.+008+18256

作成したKSKを確認します。KSKの公開鍵(key)と秘密鍵(private)が作成されたことがわかります。

[root@primary ~]# ls -l /var/named/keys/
合計 8
-rw-r--r--. 1 root root  424  6月 11 22:05 Kabc.test.+008+18256.key
-rw-------. 1 root root 1012  6月 11 22:05 Kabc.test.+008+18256.private

公開鍵の中身を確認してみます。

[root@primary ~]# cat  /var/named/keys/Kabc.test.+008+18256.key
; This is a key-signing key, keyid 18256, for abc.test.
; Created: 20230611130539 (Sun Jun 11 22:05:39 2023)
; Publish: 20230611130539 (Sun Jun 11 22:05:39 2023)
; Activate: 20230611130539 (Sun Jun 11 22:05:39 2023)
abc.test. IN DNSKEY 257 3 8 AwEAAbsk2bsnSHR/+xywTwKAAWZiTFHLv67DwWDxpWiu6dRq3DTH1xRL 4McB9vpCjUac8XzO4QUZKayPQ7eON0cHSroGYEcFmX3ghJ1MJu1l/FPW RMaRABD6rHaSqnStrKhlza0aZ5DXdi/VOaY2xFd1PCkFwA67FosSHFTI SfbmWoOP

DNSKEYレコードのフォーマットは以下のとおりです。
フォーマットは、RFC 4034: Resource Records for the DNS Security Extensionsで規定されています。

<ドメイン名> IN DNSKEY <フラグ> <プロトコル> <アルゴリズム> <公開鍵>
レコード 意味
フラグ 256はZSK、257はKSKを意味します
プロトコル プロトコル番号は3になります。
アルゴリズム DNSSECアルゴリズム番号を意味します。8はRSA/SHA-256アルゴリズムを示しています。詳細はhttps://www.iana.org/assignments/dns-sec-alg-numbers/dns-sec-alg-numbers.xhtmlを参照ください
公開鍵 公開鍵をBase64エンコードした文字列です

3.3 ZSKの作成方法

[root@primary ~]# dnssec-keygen -a RSASHA256 -b 1024 -K /var/named/keys -n zone abc.test
Generating key pair......................++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ ....................................................++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Kabc.test.+008+43296

作成したZSKを確認します。ZSKの公開鍵(key)と秘密鍵(private)が作成されたことがわかります。

[root@primary ~]# ls -l /var/named/keys/
合計 16
-rw-r--r--. 1 root root  424  6月 11 22:05 Kabc.test.+008+18256.key
-rw-------. 1 root root 1012  6月 11 22:05 Kabc.test.+008+18256.private
-rw-r--r--. 1 root root  425  6月 11 22:45 Kabc.test.+008+43296.key
-rw-------. 1 root root 1012  6月 11 22:45 Kabc.test.+008+43296.private
[root@primary ~]# cat /var/named/keys/Kabc.test.+008+43296.key
; This is a zone-signing key, keyid 43296, for abc.test.
; Created: 20230611134551 (Sun Jun 11 22:45:51 2023)
; Publish: 20230611134551 (Sun Jun 11 22:45:51 2023)
; Activate: 20230611134551 (Sun Jun 11 22:45:51 2023)
abc.test. IN DNSKEY 256 3 8 AwEAAdM31XgEivQjEwdaMD5Q6+4yi//wZFq3fz0WzgL/bwvIXvppyGL8 bP0yL0ILgx+tN4bNvhUvUTo7yE/C01Ra2axPyAgQ/RO4AUMxxVzagCyw JiLUPIkQCCtTCskStTVlIlhOoTL6j1S+QiQpVgaClv/o6tzItvhrJR1T EbsLjgy7

4 リソースレコードの署名方法

ゾーンファイル内のリソースレコードに署名するためには、dnssec-signzoneコマンドを使用します。以下にコマンドの書式の例を示します。

dnssec-signzone [オプション] ゾーンファイル [keys]

オプションの意味は以下のとおりです。

オプション 意味
-a 生成されたすべての署名を検証するときに指定します
-S 鍵をゾーンファイル書き込むときに指定します
-x BIND 9がDNSKEY、CDNSKEY、およびCDSのRRセットに対してのみキーサインキーで署名し、ゾーンサインキーによる署名を省略することを示します
-3 salt ソルトを指定します。このソルトを使用してNSEC3チェーンを生成します
-K(大文字) DNSSECキーを検索するためのディレクトリを指定します。指定されていない場合、デフォルトで現在のディレクトリが使用されます
-o ゾーンのオリジンを指定します

dnssec-signzoneコマンドを使ってリソースレコードに署名をします。以下の例ではソルト(-3)に1234、オリジン(-o)にabc.testを指定しています。

[root@primary ~]# dnssec-signzone -a -S -x -3 1234 -K /var/named/keys -o abc.test /var/named/abc.test.db
Fetching abc.test/RSASHA256/18256 (KSK) from key repository.
Fetching abc.test/RSASHA256/43296 (ZSK) from key repository.
Verifying the zone using the following algorithms:
- RSASHA256
Zone fully signed:
Algorithm: RSASHA256: KSKs: 1 active, 0 stand-by, 0 revoked
                      ZSKs: 1 active, 0 present, 0 revoked
/var/named/abc.test.db.signed

ゾーンファイルを確認します。abc.test.db.signedというファイルが作成されたことがわかります。

[root@primary ~]# ls -l /var/named/abc.test.db*
-rw-r--r--. 1 root root  485  6月  1 19:58 /var/named/abc.test.db
-rw-r--r--. 1 root root  451  6月  1 19:58 /var/named/abc.test.db.org
-rw-r--r--. 1 root root 3966  6月 12 21:49 /var/named/abc.test.db.signed

作成したゾーンファイルの中身を確認します。既存のレコードに加え、RRSIGレコード、NSEC3PARAMレコード、NSEC3レコードが追加されていることがわかります。

[root@primary ~]# cat /var/named/abc.test.db.signed
; File written on Mon Jun 12 21:49:47 2023
; dnssec_signzone version 9.16.23-RH
abc.test.               3600    IN SOA  primary.abc.test. root.abc.test. (
                                        2023052802 ; serial
                                        300        ; refresh (5 minutes)
                                        900        ; retry (15 minutes)
                                        3600       ; expire (1 hour)
                                        3600       ; minimum (1 hour)
                                        )
                        3600    RRSIG   SOA 8 2 3600 (
                                        20230712114947 20230612114947 43296 abc.test.
                                        zwap89WPc+C/NZD072SLvnTUD8308ZOzb8tx
                                        Hj0/o7EUyKKKO8RnsJxeAu14bWpD3bXU9YEF
                                        cL+9NwitF/pdgePSu9kLdLJOFHj+q1xdToZe
                                        ISBa+qH6DqNSds2CpH11wON3I8UmGl1cqgeB
                                        rQxoFX4OXq0n/Myegk7Ae7TMuzE= )
                        3600    NS      primary.abc.test.
                        3600    RRSIG   NS 8 2 3600 (
                                        20230712114947 20230612114947 43296 abc.test.
                                        ItAfBAP0ndlLr6Y9Zo3fiFaasOCk1lUT3q7S
                                        Rcga8f/9Uij9ASqKt+W+iBO33zCbHeUwPhtX
                                        t6C30GmPDXS4ox2OX6Xlv8NYM8ICjBHrC2pN
                                        wwM4tD+uG4DG2y6kDp/wMY5JUDwjIohVp8Ck
                                        O5zS/wIKei5s1zPtt1tx8vnyoGk= )
                        3600    DNSKEY  257 3 8 (
                                        AwEAAbsk2bsnSHR/+xywTwKAAWZiTFHLv67D
                                        wWDxpWiu6dRq3DTH1xRL4McB9vpCjUac8XzO
                                        4QUZKayPQ7eON0cHSroGYEcFmX3ghJ1MJu1l
                                        /FPWRMaRABD6rHaSqnStrKhlza0aZ5DXdi/V
                                        OaY2xFd1PCkFwA67FosSHFTISfbmWoOP
                                        ) ; KSK; alg = RSASHA256 ; key id = 18256
                        3600    DNSKEY  256 3 8 (
                                        AwEAAdM31XgEivQjEwdaMD5Q6+4yi//wZFq3
                                        fz0WzgL/bwvIXvppyGL8bP0yL0ILgx+tN4bN
                                        vhUvUTo7yE/C01Ra2axPyAgQ/RO4AUMxxVza
                                        gCywJiLUPIkQCCtTCskStTVlIlhOoTL6j1S+
                                        QiQpVgaClv/o6tzItvhrJR1TEbsLjgy7
                                        ) ; ZSK; alg = RSASHA256 ; key id = 43296
                        3600    RRSIG   DNSKEY 8 2 3600 (
                                        20230712114947 20230612114947 18256 abc.test.
                                        Sh+47dbiEg1QiUn5N4aystCzZoPioxdgtmHu
                                        hpIO9E9+VC3ZUjDKLSn9uFg64plXHgx5EG8v
                                        Wy15gSyLW5IWUEX0y3rxzi9MbwhUAe5YJm74
                                        EmwPea3dUzIpUkZZXH3vBcm9O1Ke3lv8V1Rt
                                        LiQwtksJGFzoGJpnsRI3Evc3Os4= )
                        0       NSEC3PARAM 1 0 10 1234
                        0       RRSIG   NSEC3PARAM 8 2 0 (
                                        20230712114947 20230612114947 43296 abc.test.
                                        J549EEC6bARktJaTXPKsvhF3AxK+AoCV+jt5
                                        HaAA5A3Jm1Ts6k8XQE6bjV+Pb5a8PUNrkeLM
                                        6ZEF2w9MwlLpEdmoiCHN7JpDAhfCvxSBKZ6v
                                        ueGxgoMXUdT0etaFsRVpFiAz3LZXTAd8jkcE
                                        OqHmxaTAT3dT1K044t7BXaIDf4k= )
primary.abc.test.       3600    IN A    192.168.122.16
                        3600    RRSIG   A 8 3 3600 (
                                        20230712114947 20230612114947 43296 abc.test.
                                        IMHwi3Icml76UOlEbjgQ3XkmH+s+hEWhismT
                                        J9ZyPKiXSTpcT+EAzmrRP0f0jUTXVKIT/mfv
                                        GJutJqCibE1OZv6wNBAfff1M4P9sW1ykyuUc
                                        S3kl7hgM9+r6c3fmw8TIW21rfzH8KGY3qnzl
                                        nRkM5Abd80eoGyKB8kMum6+KIWw= )
FKUSJSS19E8994LO00GH510HCD7I4AMM.abc.test. 3600 IN NSEC3 1 0 10 1234 (
                                        UBJNF1IDKRB7SGG2P11RLSAI7GBSJ38J
                                        A RRSIG )
                        3600    RRSIG   NSEC3 8 3 3600 (
                                        20230712114947 20230612114947 43296 abc.test.
                                        UVyKxOeyRyn3l+erymeb3kgknL/0TpxAlPQS
                                        A7JOK9VSXrzzKsOFCO9Ohu9laWw3ZXwcpoky
                                        +q9Vh6P6tKSlNgvQPu8p6XWCAznDXRPov2pA
                                        38NoCQsTbZY0A/Pbcalr/euK5gZRrcS3Lub1
                                        BaJ3jV/r/YyGn33fM4ma4/vYVqw= )
BK5S6VI9M6F57QF0ODM1CR8ITTMJTJ3P.abc.test. 3600 IN NSEC3 1 0 10 1234 (
                                        FKUSJSS19E8994LO00GH510HCD7I4AMM
                                        NS SOA RRSIG DNSKEY NSEC3PARAM )
                        3600    RRSIG   NSEC3 8 3 3600 (
                                        20230712114947 20230612114947 43296 abc.test.
                                        Jdhz/pK/5JxDQDpbeDXvJdfz5Qlab76uYeR/
                                        ++FMFWhSj0UkbKuRRJzZBlJaUmfzKfEed/SK
                                        Gj0isMxsw40FWxxJS4rMW3FBbl8K3PKV4KR9
                                        DJ864iZPOC6oKKb1IV4p1+oSXQQD5AQiJLDy
                                        OeCPgC/fIRy0i/TfHC+qzZM774A= )
www.abc.test.           3600    IN A    192.168.122.20
                        3600    RRSIG   A 8 3 3600 (
                                        20230712114947 20230612114947 43296 abc.test.
                                        JKMVPFA6sEChBRp8DvZnJO+UE23z6fcRAfxm
                                        BVmeln1vAcjND85+IT0vLkp3G78CZaEn5Jeg
                                        w9Fk/RM5uC3+0j1RWEfI9Ri/4Fh0IesJCgAt
                                        1od1zww6C23itIf5C0nhrb+PNn22sfy8UQQD
                                        xaMBzwrjHBBWnmV+6FsDuQoyYEo= )
UBJNF1IDKRB7SGG2P11RLSAI7GBSJ38J.abc.test. 3600 IN NSEC3 1 0 10 1234 (
                                        BK5S6VI9M6F57QF0ODM1CR8ITTMJTJ3P
                                        A RRSIG )
                        3600    RRSIG   NSEC3 8 3 3600 (
                                        20230712114947 20230612114947 43296 abc.test.
                                        ZoYTcbesk0srNmHwT/AIHNB9KY4iwt8qp0rQ
                                        ma1iX73Ixn51UbUCVIKNLPHml+8Pfm3Z6J57
                                        chg/FtfUKrj9V6P+ZcP+FpnJy0YvepIYB6ro
                                        EmwYJSqJGmJp6zlqtKhHurDWfFqeSy57YVX1
                                        mOg2rzfr6trFIDUpfkTacoKEyAU= )

各種リソースレコードの意味を以下に示します。

レコード名 意味
RRSIG 各リソースレコードに対する署名が格納されます
NSEC3 リソースレコードの情報をハッシュしたNSEC
NSEC3PARAM NSEC3の利用に必要とされる情報

5 DSリソースレコードの作成方法

DSリソースレコードは、dnssec-dsfromkeyコマンドを使って作成します。dnssec-dsfromkeyコマンドの書式は以下のとおりです。キーファイルには、KSKの公開鍵を指定します。

dnssec-dsfromkey [オプション] キーファイル 

オプションの意味は以下のとおりです。

オプション 意味
-1 ハッシュ値を生成するアルゴリズムSHA-1を使用する
-2 ハッシュ値を生成するアルゴリズムにSHA-256を使用する
-a ハッシュ値を生成するアルゴリズムを指定するオプションです

KSKの公開鍵を指定して、dnssec-dsfromkeyコマンドを実行します。

[root@server ~]# dnssec-dsfromkey /var/named/keys/Kabc.test.+008+18256.key
abc.test. IN DS 18256 8 2 9C4C6BBD44E0F04BEFB50729773F75461A166BF4823D9F911F0EACEE8E88FD45

BINDの使い方(TSIG)

1 TSIG(Transaction Signature)とは?

TSIGは次のことを保証する仕組みです。
DNSメッセージの完全性
DNSメッセージ送信元の真正性
これにより、プライマリーサーバとセカンダリーサーバの間でゾーン情報を安全に転送することができます。TSIG はDNS メッセージにTSIGレコードを付加することで、DNS メッセージに電子署名を行います。なお、ゾーン転送は、BINDの使い方(ゾーン転送) - hana_shinのLinux技術ブログを参照してください。

2 検証環境

2.1 ネットワーク構成

DNSサーバは、プライマリーサーバとセカンダリーサーバの2台構成です。

                       192.168.122.0/24
primary(eth0) ----------------------------------(eth0) secondary
             .16                             .213

2.2 版数

プライマリーサーバとセカンダリーサーバのAlmaLinux版数は以下のとおりです。

[root@primary ~]# cat /etc/redhat-release
AlmaLinux release 9.1 (Lime Lynx)

カーネル版数は以下のとおりです。

[root@primary ~]# uname -r
5.14.0-162.6.1.el9_1.x86_64

3 動作確認

bindパッケージのインストール方法やポート番号の開放は、BINDの使い方(ゾーン転送) - hana_shinのLinux技術ブログを参照ください。

3.1 共有鍵の作成

共有鍵はtsig-keygenコマンドを使って作成します。書式は以下のとおりです。tsig-keygenコマンドの引数にはハッシュ関数と共有鍵名を指定します。デフォルトのハッシュ関数はhmac-sha256です。

# tsig-keygen -a [アルゴリズム] 共有鍵名

tsig-keygenコマンドを使用して共有鍵を作成します。共有鍵の名前はprimary-secondaryとします。

[root@primary ~]# tsig-keygen primary-secondary
key "primary-secondary" {
        algorithm hmac-sha256;
        secret "QBTirziTOPJe3Fa0lA8hVXt9hNxuqAAKz8jIwYiZGck=";
};

3.2 プライマリーサーバ

作成した共有鍵をプライマリーサーバの設定ファイルに追加します。

[root@primary ~]# diff -Nur /etc/named.conf.org /etc/named.conf
--- /etc/named.conf.org 2023-06-03 23:42:27.674145301 +0900
+++ /etc/named.conf     2023-06-03 23:40:37.412881984 +0900
@@ -63,3 +63,10 @@
        allow-transfer { 192.168.122.213; };
        notify yes;
 };
+
+key "primary-secondary" {
+        algorithm hmac-sha256;
+        secret "QBTirziTOPJe3Fa0lA8hVXt9hNxuqAAKz8jIwYiZGck=";
+};
+
+

3.3 セカンダリーサーバ

作成した共有鍵をセカンダリーサーバの設定ファイルに追加します。さらに、共有鍵を使用するため、serverステートメント内でkeysサブステートメントを使って定義します。keysサブステートメント内のパラメータは鍵の名前(primary-secondary)を指定します。

[root@secondary ~]# diff -Nur /etc/named.conf.org /etc/named.conf
--- /etc/named.conf.org 2023-06-03 23:43:34.299629797 +0900
+++ /etc/named.conf     2023-06-03 23:50:39.562587606 +0900
@@ -62,3 +62,13 @@
        file "slaves/abc.test.db";
        masters { 192.168.122.16; };
 };
+
+key "primary-secondary" {
+        algorithm hmac-sha256;
+        secret "QBTirziTOPJe3Fa0lA8hVXt9hNxuqAAKz8jIwYiZGck=";
+};
+
+server 192.168.122.16 {
+        keys { primary-secondary; };
+};
+

3.4 TSIGレコードの確認

TSIG レコードを確認するため、tcpdumpコマンドを実行します。tcpdumpコマンドの使い方は、tcpdumpの使い方(基本編) - hana_shinのLinux技術ブログを参照してください。

[root@secondary ~]# tcpdump -i eth0 host 192.168.122.16 and port 53 -w dns.pcap

セカンダリーサーバのnamedを起動したらすぐにゾーン転送が行われるようにするため、セカンダリーサーバの/var/named/slaves配下のゾーンファイルを削除します(もし存在していたら)。以下の実行例では、ゾーンファイルが存在しないことがわかります。

[root@secondary ~]# ls /var/named/slaves/
[root@secondary ~]#

プライマリーサーバでnamedサービスを起動します。

[root@primary ~]# systemctl start named

セカンダリーサーバでnamedサービスを起動すると、ゾーン転送が開始されます。

[root@secondary ~]# systemctl start named

以下は、セカンダリーサーバからプライマリーサーバにゾーン転送を要求したときのWiresharkのキャプチャ画面です。Additional RRsが1となっていて、TSIGレコードが1つ追加されていることがわかります。また、TSIGレコードのMACフィールドは、DNSメッセージの完全性/真正性を実現するために使用されます。

次は、プライマリーサーバからセカンダリーサーバにゾーン転送をしている時のWiresharkのキャプチャ画面です。

BINDの使い方(ゾーン転送)

1 はじめに

DNSの運用では、複数の権威DNSサーバを用意するのが一般的です。複数の権威DNSサーバを運用する場合、全ての権威DNSサーバでゾーンファイルを一致させる必要があります。管理者がこれを手作業で行うのは手間がかかり、ミスも発生します。このため、DNSでは複数の権威DNSサーバでゾーンファイルを同期するゾーン転送という仕組みがあります。ゾーンファイルを管理する権威DNSサーバをプライマリーサーバと呼び、ゾーン転送によってゾーンファイルのコピーを受け取り運用するサーバをセカンダリーサーバと呼びます。なお、検証に使うドメイン名は、RFC 2606 - Reserved Top Level DNS Namesで以下のように記述されているので、abc.testとします。

".test" is recommended for use in testing of current or new DNS related code.

DNSの名前解決の様子は、digコマンドの使い方 - hana_shinのLinux技術ブログを参照してください。

2 検証環境

2.1 ネットワーク構成

DNSサーバは、プライマリーサーバとセカンダリーサーバの2台構成です。

                       192.168.122.0/24
primary(eth0) ----------------------------------(eth0) secondary
             .16                             .213

2.2 版数

プライマリーサーバとセカンダリーサーバのAlmaLinux版数は以下のとおりです。

[root@primary ~]# cat /etc/redhat-release
AlmaLinux release 9.1 (Lime Lynx)

カーネル版数は以下のとおりです。

[root@primary ~]# uname -r
5.14.0-162.6.1.el9_1.x86_64

3 インストール方法

プライマリーサーバとセカンダリーサーバで bindパッケージ、bind-utilsパッケージをインストールします。なお、dnfコマンドの使い方は、dnfコマンドの使い方 - hana_shinのLinux技術ブログを参照してください。

[root@primary ~]# dnf -y install bind bind-utils

BINDの版数を確認します。

[root@primary ~]# named -v
BIND 9.16.23-RH (Extended Support Version) <id:fde3b1f>

4 ポート番号の開放

ゾーン転送に使うTCP/UDPのポート番号53を解放します。なお、firewall-cmdの使い方は、firewall-cmdの使い方 - hana_shinのLinux技術ブログを参照してください。

4.1 プライマリーサーバのポート番号開放

[root@primary ~]# firewall-cmd --add-port=53/tcp
success
[root@primary ~]# firewall-cmd --add-port=53/udp
success

開放したポート番号を確認します。

[root@primary ~]# firewall-cmd --list-ports
53/tcp 53/udp

4.2 セカンダリーサーバのポート番号開放

[root@secondary ~]# firewall-cmd --add-port=53/tcp
success
[root@secondary ~]# firewall-cmd --add-port=53/udp
success

開放したポート番号を確認します。

[root@secondary ~]# firewall-cmd --list-ports
53/tcp 53/udp

5 プライマリーサーバの設定

5.1 設定ファイルの編集

設定ファイル編集前後の差分を確認するため、バックアップファイルを作成します。

[root@primary ~]# cp /etc/named.conf /etc/named.conf.org

設定ファイルの差分を確認します。

[root@primary ~]# vi /etc/named.conf
[root@primary ~]# diff -Nur /etc/named.conf.org /etc/named.conf
--- /etc/named.conf.org 2023-05-21 20:12:04.638427807 +0900
+++ /etc/named.conf     2023-05-27 19:59:22.375933433 +0900
@@ -8,7 +8,7 @@
 //

 options {
-       listen-on port 53 { 127.0.0.1; };
+       listen-on port 53 { 192.168.122.16; };
        listen-on-v6 port 53 { ::1; };
        directory       "/var/named";
        dump-file       "/var/named/data/cache_dump.db";
@@ -16,7 +16,7 @@
        memstatistics-file "/var/named/data/named_mem_stats.txt";
        secroots-file   "/var/named/data/named.secroots";
        recursing-file  "/var/named/data/named.recursing";
-       allow-query     { localhost; };
+       allow-query     { any; };

        /*
         - If you are building an AUTHORITATIVE DNS server, do NOT enable recursion.
@@ -28,7 +28,7 @@
           attacks. Implementing BCP38 within your network would greatly
           reduce such attack surface
        */
-       recursion yes;
+       recursion no;

        dnssec-validation yes;

@@ -57,3 +57,9 @@
 include "/etc/named.rfc1912.zones";
 include "/etc/named.root.key";

+zone "abc.test" IN {
+       type master;
+       file "abc.test.db";
+       allow-transfer { 192.168.122.213; };
+       notify yes;
+};

設定変更したステートメントの意味を以下に示します。

ステートメント 意味
listen-on DNSサーバが問い合わせを受け付けるIPアドレスを設定します。
allow-query DNSクエリーを受け付けるDNSクライアントのIPアドレスを設定します。ここでは、全てのDNSクライアントからのDNSクエリを受け付けるanyを設定します。
recursion 再帰問い合わせを受け付けるかどうかを設定します。DNS権威サーバは再帰クエリは受け付けないのでnoを設定します
type DNSサーバがプライマリーサーバか、セカンダリーサーバなのかを設定します。プライマリーサーバはmaster、セカンダリーサーバはslave、DNSキャッシュサーバはhintを設定します。
file ゾーンファイル名を設定します。ゾーンファイルは、directoryステートメントで指定したディレクトリ以下に格納されます
allow-transfer ゾーンファイルの転送を許可するセカンダリーサーバのIPアドレスを設定します。
notify プライマリーサーバのゾーンファイルが更新された時、セカンダリーサーバに更新があったことを通知するかどうかを設定します。通知する場合はyes、通知しない場合はnoを設定します。

5.2 ゾーンファイルの作成

ゾーン転送の動作確認をするため、正引きのゾーンファイルのみを作成します。ゾーン転送はゾーンファイルのSOAレコードで制御されます。なお、SOAレコードのパラメータの意味は、digコマンドの使い方 - hana_shinのLinux技術ブログを参照してください。

[root@primary ~]# vi /var/named/abc.test.db
[root@primary ~]# cat /var/named/abc.test.db
$ORIGIN abc.test.
$TTL 3600
@    IN SOA     primary.abc.test. root.abc.test. (
                                        2023052801 ; serial
                                        300        ; refresh
                                        900        ; retry
                                        3600       ; expire
                                        3600 )     ; minimum
           NS      primary.abc.test.
primary    A       192.168.122.16

6 セカンダリーサーバの設定

6.1 設定ファイルの編集

設定ファイル編集前後の差分を確認するため、バックアップファイルを作成します。

[root@secondary ~]# cp /etc/named.conf /etc/named.conf.org

設定ファイルの差分を確認します。

[root@secondary ~]# vi /etc/named.conf
[root@secondary ~]# diff -Nur /etc/named.conf.org /etc/named.conf
--- /etc/named.conf.org 2023-05-21 20:16:02.611164689 +0900
+++ /etc/named.conf     2023-05-21 20:18:38.335385768 +0900
@@ -8,7 +8,7 @@
 //

 options {
-       listen-on port 53 { 127.0.0.1; };
+       listen-on port 53 { 192.168.122.213; };
        listen-on-v6 port 53 { ::1; };
        directory       "/var/named";
        dump-file       "/var/named/data/cache_dump.db";
@@ -16,7 +16,7 @@
        memstatistics-file "/var/named/data/named_mem_stats.txt";
        secroots-file   "/var/named/data/named.secroots";
        recursing-file  "/var/named/data/named.recursing";
-       allow-query     { localhost; };
+       allow-query     { any; };

        /*
         - If you are building an AUTHORITATIVE DNS server, do NOT enable recursion.
@@ -28,7 +28,7 @@
           attacks. Implementing BCP38 within your network would greatly
           reduce such attack surface
        */
-       recursion yes;
+       recursion no;

        dnssec-validation yes;

@@ -57,3 +57,8 @@
 include "/etc/named.rfc1912.zones";
 include "/etc/named.root.key";

+zone "abc.test" IN {
+       type slave;
+       file "slaves/abc.test.db";
+       masters { 192.168.122.16; };
+};

7 設定ファイル、ゾーンファイルの構文チェック

設定ファイル、およびゾーンファイルの構文が正しいかどうかをチェックします。それぞれ、以下のコマンドでチェックすることができます。
・named-checkconf:設定ファイル(named.conf)の構文チェック
・named-checkzone:ゾーンファイルの構文チェック

7.1 プライマリーサーバ

named-checkconfコマンドを使って、プライマリーサーバの設定ファイルの構文をチェックします。named-checkconfコマンドが正常終了しているので、設定ファイルに誤りがないことがわかります。

[root@primary ~]# named-checkconf /etc/named.conf
[root@primary ~]#

named-checkzoneコマンドを使って、プライマリーサーバのゾーンファイルの構文をチェックします。named-checkzoneコマンドが正常終了しているので、ゾーンファイルに誤りがないことがわかります。

[root@primary ~]# named-checkzone abc.test /var/named/abc.test.db
zone abc.test/IN: loaded serial 2023052801
OK

7.2 セカンダリーサーバ

named-checkconfコマンドを使って、セカンダリーサーバの設定ファイルの構文をチェックします。named-checkconfコマンドが正常終了しているので、設定ファイルに誤りがないことがわかります。

[root@secondary ~]# named-checkconf /etc/named.conf
[root@secondary ~]#

8 セカンダリサーバ起動時のシーケンス

セカンダリサーバ起動時、プライマリサーバからセカンダリサーバにゾーンファイルが転送されます。その時の状況を確認してみます。

プライマリーサーバでnamedサービスを起動します。

[root@primary ~]# systemctl start named

セカンダリーサーバのゾーンファイルを確認すると、まだゾーンファイルが存在しないことがわかります。

[root@secondary ~]# ls -l /var/named/slaves
合計 0

セカンダリーサーバでnamedサービスを起動します。

[root@secondary ~]# systemctl start named

セカンダリーサーバでnamedサービスを起動すると、プライマリーサーバからセカンダリサーバにゾーンファイルが転送されたことがわかります。

[root@secondary ~]# ls -l /var/named/slaves/abc.test.db
-rw-r--r--. 1 named named 203  5月 31 20:03 /var/named/slaves/abc.test.db

ゾーンファイルはバイナリファイルなので、named-compilezoneコマンドを使ってテキストファイルに変換します。

[root@secondary ~]# named-compilezone -f raw -F text -o /tmp/abc.test.db abc.test. /var/named/slaves/abc.test.db
zone abc.test/IN: loaded serial 2023052801
dump zone to /tmp/abc.test.db...done
OK

ゾーンファイルを確認すると、プライマリサーバのゾーンファイルが転送されたことがわかります。

[root@secondary ~]# cat /tmp/abc.test.db
abc.test.                                     3600 IN SOA       primary.abc.test. root.abc.test. 2023052801 300 900 3600 3600
abc.test.                                     3600 IN NS        primary.abc.test.
primary.abc.test.                             3600 IN A         192.168.122.16

tcpdumpコマンドで採取したゾーン転送時のキャプチャファイルを以下に示します。

キャプチャファイルのシーケンスを以下に示します。まず、セカンダリサーバはUDPを使用してゾーンファイルの転送を要求します。そして、ゾーンファイルが存在する場合は、TCPコネクションを確立し、ゾーンファイルの転送を行います。ゾーンファイルの転送が完了すると、セカンダリサーバはTCPコネクションをクローズします。

プライマリーサーバ                      セカンダリーサーバ

TCP/53    UDP/53                         UDP/53    TCP/53
  |          |                             |          |
  |          |<----- DNS query ------------|          | ---
  |          |                             |          |  | <= ゾーンファイルの確認
  |          |------ DNS query response -->|          | ---
  |          |                             |          |
  |<---------|------ TCP SYN --------------|----------| ---
  |----------|------ TCP SYN+ACK ----------|--------->|  | <= TCPコネクションの確立
  |<---------|------ TCP ACK --------------|----------| ---
  |          |                             |          |
  |<---------|------ DNS query ------------|----------| ---
  |          |                             |          |  | <= ゾーンファイルの転送
  |----------|------ DNS query response ---|--------->| ---
  |          |                             |          |
  |<---------|------ TCP FIN --------------|----------| ---
  |----------|------ TCP FIN+ACK ----------|--------->|  | <= TCPコネクションのクローズ
  |<---------|------ TCP ACK --------------|----------| ---
  |          |                             |          |

9 セカンダリサーバ起動後のシーケンス

セカンダリサーバが起動した後、プライマリサーバとのパケットのやりとりを確認してみます。セカンダリサーバは定期的にプライマリサーバに対してゾーンファイルの更新があるかどうかをチェックします。このチェックはおおよそ4分の間隔で行われています。私はSOAレコードのrefreshで指定した間隔で行われると思っていたため、5分間隔で行われると考えていました。しかし、実際は違っていました。なぜ5分間隔でチェックが行われないのかについて、ご存じの方がいらっしゃいましたら、教えていただけませんか。

[root@secondary ~]# tcpdump -i eth0 host 192.168.122.16 and port 53 -v -nn
dropped privs to tcpdump
tcpdump: listening on eth0, link-type EN10MB (Ethernet), snapshot length 262144 bytes
21:46:00.719188 IP (tos 0x0, ttl 64, id 12655, offset 0, flags [none], proto UDP (17), length 69)
    192.168.122.213.42212 > 192.168.122.16.53: 34635 [1au] SOA? abc.test. (41)
21:46:00.724449 IP (tos 0x0, ttl 64, id 27651, offset 0, flags [none], proto UDP (17), length 152)
    192.168.122.16.53 > 192.168.122.213.42212: 34635*- 1/1/2 abc.test. SOA primary.abc.test. root.abc.test. 2023052801 300 900 3600 3600 (124)
21:49:53.730645 IP (tos 0x0, ttl 64, id 63337, offset 0, flags [none], proto UDP (17), length 69)
    192.168.122.213.32943 > 192.168.122.16.53: 17190 [1au] SOA? abc.test. (41)
21:49:53.738170 IP (tos 0x0, ttl 64, id 14792, offset 0, flags [none], proto UDP (17), length 152)
    192.168.122.16.53 > 192.168.122.213.32943: 17190*- 1/1/2 abc.test. SOA primary.abc.test. root.abc.test. 2023052801 300 900 3600 3600 (124)
21:54:36.741113 IP (tos 0x0, ttl 64, id 58342, offset 0, flags [none], proto UDP (17), length 69)
    192.168.122.213.48592 > 192.168.122.16.53: 27517 [1au] SOA? abc.test. (41)
21:54:36.747100 IP (tos 0x0, ttl 64, id 32930, offset 0, flags [none], proto UDP (17), length 152)
    192.168.122.16.53 > 192.168.122.213.48592: 27517*- 1/1/2 abc.test. SOA primary.abc.test. root.abc.test. 2023052801 300 900 3600 3600 (124)
-snip-

10 ゾーンファイル編集後のシーケンス

ゾーンファイルを編集します。シリアル番号を1増やして、wwwサーバのリソースレコードを1つ追加します。

[root@primary ~]# vi /var/named/abc.test.db
[root@primary ~]# diff -Nur /var/named/abc.test.db.org /var/named/abc.test.db
--- /var/named/abc.test.db.org  2023-06-01 19:58:07.222806548 +0900
+++ /var/named/abc.test.db      2023-06-01 19:50:41.223070363 +0900
@@ -1,10 +1,11 @@
 $ORIGIN abc.test.
 $TTL 3600
 @    IN SOA     primary.abc.test. root.abc.test. (
-                                        2023052801 ; serial
+                                        2023052802 ; serial
                                         300        ; refresh
                                         900        ; retry
                                         3600       ; expire
                                         3600 )     ; minimum
            NS      primary.abc.test.
 primary    A       192.168.122.16
+www        A       192.168.122.20

ゾーンファイルを編集したら、namedを再起動します。

[root@primary ~]# rndc reload
server reload successful

tcpdumpコマンドを使って、ゾーン転送時のパケットをキャプチャします。

[root@secondary ~]# tcpdump -i eth0 host 192.168.122.16 and port 53 -v -nn
dropped privs to tcpdump
tcpdump: listening on eth0, link-type EN10MB (Ethernet), snapshot length 262144 bytes
-snip-
19:54:33.608079 IP (tos 0x0, ttl 64, id 14416, offset 0, flags [none], proto UDP (17), length 69)
    192.168.122.213.36158 > 192.168.122.16.53: 52391 [1au] SOA? abc.test. (41)
19:54:33.612003 IP (tos 0x0, ttl 64, id 34989, offset 0, flags [none], proto UDP (17), length 152)
    192.168.122.16.53 > 192.168.122.213.36158: 52391*- 1/1/2 abc.test. SOA primary.abc.test. root.abc.test. 2023052802 300 900 3600 3600 (124)
19:54:33.613313 IP (tos 0x0, ttl 64, id 59507, offset 0, flags [none], proto TCP (6), length 60)
    192.168.122.213.34845 > 192.168.122.16.53: Flags [S], cksum 0x7665 (incorrect -> 0x89b9), seq 256144245, win 64240, options [mss 1460,sackOK,TS val 2617157140 ecr 0,nop,wscale 7], length 0
19:54:33.615881 IP (tos 0x0, ttl 64, id 0, offset 0, flags [DF], proto TCP (6), length 60)
    192.168.122.16.53 > 192.168.122.213.34845: Flags [S.], cksum 0x5884 (correct), seq 62942961, ack 256144246, win 65160, options [mss 1460,sackOK,TS val 75478619 ecr 2617157140,nop,wscale 7], length 0
19:54:33.616054 IP (tos 0x0, ttl 64, id 59508, offset 0, flags [none], proto TCP (6), length 52)
    192.168.122.213.34845 > 192.168.122.16.53: Flags [.], cksum 0x765d (incorrect -> 0x83e0), ack 1, win 502, options [nop,nop,TS val 2617157143 ecr 75478619], length 0
19:54:33.616912 IP (tos 0x0, ttl 64, id 59509, offset 0, flags [none], proto TCP (6), length 129)
    192.168.122.213.34845 > 192.168.122.16.53: Flags [P.], cksum 0x76aa (incorrect -> 0xd6cf), seq 1:78, ack 1, win 502, options [nop,nop,TS val 2617157144 ecr 75478619], length 77 9258 [1n] IXFR? abc.test. (75)
19:54:33.619731 IP (tos 0x0, ttl 64, id 65243, offset 0, flags [DF], proto TCP (6), length 52)
    192.168.122.16.53 > 192.168.122.213.34845: Flags [.], cksum 0x8388 (correct), ack 78, win 509, options [nop,nop,TS val 75478622 ecr 2617157144], length 0
19:54:33.621098 IP (tos 0x0, ttl 64, id 65244, offset 0, flags [DF], proto TCP (6), length 215)
    192.168.122.16.53 > 192.168.122.213.34845: Flags [P.], cksum 0x486d (correct), seq 1:164, ack 78, win 509, options [nop,nop,TS val 75478624 ecr 2617157144], length 163 9258*- 5/0/0 abc.test. SOA primary.abc.test. root.abc.test. 2023052802 300 900 3600 3600, abc.test. NS primary.abc.test., primary.abc.test. A 192.168.122.16, www.abc.test. A 192.168.122.20, abc.test. SOA primary.abc.test. root.abc.test. 2023052802 300 900 3600 3600 (161)
19:54:33.621139 IP (tos 0x0, ttl 64, id 59510, offset 0, flags [none], proto TCP (6), length 52)
    192.168.122.213.34845 > 192.168.122.16.53: Flags [.], cksum 0x765d (incorrect -> 0x82e7), ack 164, win 501, options [nop,nop,TS val 2617157148 ecr 75478624], length 0
19:54:33.623264 IP (tos 0x0, ttl 64, id 59511, offset 0, flags [none], proto TCP (6), length 52)
    192.168.122.213.34845 > 192.168.122.16.53: Flags [F.], cksum 0x765d (incorrect -> 0x82e4), seq 78, ack 164, win 501, options [nop,nop,TS val 2617157150 ecr 75478624], length 0
19:54:33.625855 IP (tos 0x0, ttl 64, id 65245, offset 0, flags [DF], proto TCP (6), length 52)
    192.168.122.16.53 > 192.168.122.213.34845: Flags [F.], cksum 0x82d6 (correct), seq 164, ack 79, win 509, options [nop,nop,TS val 75478629 ecr 2617157150], length 0
19:54:33.625906 IP (tos 0x0, ttl 64, id 59512, offset 0, flags [none], proto TCP (6), length 52)
    192.168.122.213.34845 > 192.168.122.16.53: Flags [.], cksum 0x765d (incorrect -> 0x82db), ack 165, win 501, options [nop,nop,TS val 2617157153 ecr 75478629], length 0

named-compilezoneコマンドを使って、ゾーンファイルをテキストファイルに変換します。

[root@secondary ~]# named-compilezone -f raw -F text -o /tmp/abc.test.db abc.test. /var/named/slaves/abc.test.db
zone abc.test/IN: loaded serial 2023052802
dump zone to /tmp/abc.test.db...done
OK

ゾーンファイルを確認すると、シリアル番号が1つ増加したことと、wwwサーバのリソースレコードが追加されたことがわかります。

[root@secondary ~]# cat /tmp/abc.test.db
abc.test.                                     3600 IN SOA       primary.abc.test. root.abc.test. 2023052802 300 900 3600 3600
abc.test.                                     3600 IN NS        primary.abc.test.
primary.abc.test.                             3600 IN A         192.168.122.16
www.abc.test.                                 3600 IN A         192.168.122.20

11 ゾーンファイルの転送確認

ゾーンファイルを転送したセカンダリーサーバに対して名前解決を要求してみます。まず、primary.abc.testのIPアドレスの解決を要求してみます。primary.abc.testのIPアドレスが192.168.122.16であることがわかります。

[root@primary ~]# dig @192.168.122.213 primary.abc.test +short
192.168.122.16

次に、www.abc.testのIPアドレスの解決を要求してみます。www.abc.testのIPアドレスが192.168.122.20であることがわかります。

[root@primary ~]# dig @192.168.122.213 www.abc.test +short
192.168.122.20

Z 参考情報

私が業務や記事執筆で参考にした書籍を以下のページに記載します。
Linux技術のスキルアップをしよう! - hana_shinのLinux技術ブログ

BIND 9 Administrator Reference Manual — BIND 9 9.19.22-dev documentation

fail2banの使い方

1 fail2banとは?

fail2banは、サーバを不正アクセスから保護するためのツールです。具体的には、ログファイルの内容を監視し、認証に何度も失敗しているログや連続アクセスしているログを検出すると、ファイアーウォールの設定を変更して、不正アクセス元からの接続を禁止します。たとえば、SSHのログインが失敗すると、/var/log/secureに以下のようなログが記録されます。fail2banは、このログを監視して、何度もSSHログインに失敗している接続元からのアクセスを禁止します。

[root@server ~]# tail -f /var/log/secure
-snip-
May 23 21:04:21 primary unix_chkpwd[1247]: password check failed for user (root)
May 23 21:04:21 primary sshd[1245]: pam_unix(sshd:auth): authentication failure; logname= uid=0 euid=0 tty=ssh ruser= rhost=192.168.122.213  user=root
May 23 21:04:23 primary sshd[1245]: Failed password for root from 192.168.122.213 port 58084 ssh2

2 検証環境

2.1 ネットワーク構成

サーバとクライアントの2台構成です。図中のeth0はNICの名前です。

                         192.168.122.0/24
client(eth0) ----------------------------------------(eth0) server
           .213                                       .16

2.2 版数

サーバのAlmaLinux版数は以下のとおりです。

[root@server ~]# cat /etc/redhat-release
AlmaLinux release 9.1 (Lime Lynx)

サーバのカーネル版数は以下のとおりです。

[root@server ~]# uname -r
5.14.0-162.6.1.el9_1.x86_64

3 インストール方法

3.1 fail2banのインストール

fail2banパッケージはepelリポジトリにあるので、まず、epel-releaseパッケージをインストールします。

[root@server ~]# dnf -y install epel-release

次に、fail2banパッケージをインストールします。

[root@server ~]# dnf -y install fail2ban

インストールしたfail2banの版数を確認します。fail2banのメジャーバージョンが1になりました。

[root@server ~]# fail2ban-server --version
Fail2Ban v1.0.2
[root@server ~]# fail2ban-client --version
Fail2Ban v1.0.2
[root@server ~]# fail2ban-regex --version
fail2ban-regex 1.0.2
[root@server ~]# fail2ban-python --version
Python 3.9.14

3.2 Apacheのインストール

検証目的のため、サーバにhttpdパッケージをインストールします。

[root@server ~]# dnf -y install httpd

httpdサービスを起動します。

[root@server ~]# systemctl start httpd

4 機能概要

4.1 fail2ban-server/fail2ban-client概要

コマンド 概要
fail2ban-server システムに常駐して,ログファイルの監視や攻撃を受けた際の処理を行う
fail2ban-client fail2ban-serverの起動・停止や各種設定をおこなう

4.2 設定ファイル

設定ファイル名 概要
/etc/fail2ban/fail2ban.conf ログの格納場所やログレベルを指定する
/etc/fail2ban/filter.d/*.conf 正規表現を使ってアクセス違反を定義する
/etc/fail2ban/action.d/*.conf アクセス違反が発生したときの動作を定義する
/etc/fail2ban/jail.conf どの程度(時間、回数)アクセスがあったらブロックするかを定義する。 ただし、このファイルは編集しない(後述)

5 サーバの起動、停止方法

fail2ban-clientコマンドを使って、fail2banの起動、停止ができます。なお、systemctlコマンドでも、fail2banの起動、停止ができます。

[root@server ~]# fail2ban-client start
Server ready

fail2banを起動すると、以下のプロセスが生成されます。なお、PIDが全て同じなので、3つのプロセスはアドレス空間を共有するスレッドとなります。

  • fail2ban-server:親プロセス
  • f2b/observer:fail2ban-serverが生成するプロセス

なお、psコマンドの使い方は、psコマンドの使い方 - hana_shinのLinux技術ブログを参照してください。

[root@server ~]# ps -LC fail2ban-server -o comm,pid,ppid,args
COMMAND             PID    PPID COMMAND
fail2ban-server    3194       1 /usr/bin/python3 -s /usr/bin/fail2ban-server --async -b -s /var/run/fail2ban/f
f2b/observer       3194       1 /usr/bin/python3 -s /usr/bin/fail2ban-server --async -b -s /var/run/fail2ban/f
f2b/observer       3194       1 /usr/bin/python3 -s /usr/bin/fail2ban-server --async -b -s /var/run/fail2ban/f

fail2banの状態は、statusオプションを使用して確認します。Number of jailが0であるため、現在アクセス禁止にされているアクセス元が存在しないことがわかります。

[root@server ~]# fail2ban-client status
Status
|- Number of jail:      0
`- Jail list:

fail2banを停止します。

[root@server ~]# fail2ban-client stop
Shutdown successful

fail2banの状態を確認します。fail2banを停止したので、"Is fail2ban running?"と聞かれます。

[root@server ~]# fail2ban-client status
2023-05-23 21:57:06,494 fail2ban                [3203]: ERROR   Failed to access socket path: /var/run/fail2ban/fail2ban.sock. Is fail2ban running?

6 設定ファイルのカスタマイズ方法

jail.confのmanを確認すると、以下の説明があります。設定のカスタマイズはjail.confではなく、jail.localを新規作成して、そこに記述するようです。

[root@server ~]# man jail.conf
-snip-
       *.conf files are distributed by Fail2Ban.  It is recommended that *.conf files should remain unchanged to ease
       upgrades.  If needed, customizations should be provided in *.local files.  For example, if you would  like  to
       enable the [ssh-iptables-ipset] jail specified in jail.conf, create jail.local containing

       jail.local
              [ssh-iptables-ipset]

              enabled = true

       In .local files specify only the settings you would like to change and the rest of the configuration will then
       come from the corresponding .conf file which is parsed first.

7 実験1(sshアクセスの禁止)

30秒間で2回、sshログインに失敗すると、サーバに60秒間アクセス禁止にする、という設定をしてみます。アクセス禁止とは、ファイアーウォールでsshパケットをREJECTする、という意味です。

7.1 設定内容

jail.localを新たに作成します。設定内容は次のとおりです。

  • bantime:対象ホストへのアクセス禁止の時間です。
  • findtime :監視時間を表します。
  • maxretry :リトライ回数を表します。findtimeで指定した時間、maxretry回続けば対象ホストへのアクセス遮断します。
[root@server ~]# vi /etc/fail2ban/jail.local
[root@server ~]# cat /etc/fail2ban/jail.local
[sshd]
enabled = true
bantime  = 60
findtime  = 30
maxretry = 2

fail2banサーバを起動します。

[root@server ~]# fail2ban-client start
Server ready

fail2banの状態を確認します。まだアクセス禁止(Banned IP list)になっているIPアドレスはありません。

[root@server ~]# fail2ban-client status sshd
Status for the jail: sshd
|- Filter
|  |- Currently failed: 0
|  |- Total failed:     0
|  `- Journal matches:  _SYSTEMD_UNIT=sshd.service + _COMM=sshd
`- Actions
   |- Currently banned: 0
   |- Total banned:     0
   `- Banned IP list:

7.2 動作確認

クライアントからサーバにsshログインを実行します。このとき、意図的に間違ったパスワードを入力します。

[root@client ~]# ssh 192.168.122.16
root@192.168.122.16's password:
Permission denied, please try again.
root@192.168.122.16's password:
Permission denied, please try again.
root@192.168.122.16's password:
root@192.168.122.16: Permission denied (publickey,gssapi-keyex,gssapi-with-mic,password).

さらにサーバにsshログインを実行してみます。fail2banがnetfilterのルールを変更して、22番ポートへのアクセスを禁止にしたため、TCPコネクション確立が拒否されていることがわかります。"Connection refused"については、ECONNREFUSEDとECONNRESETについて - hana_shinのLinux技術ブログを参照してください。

[root@client ~]# ssh 192.168.122.16
ssh: connect to host 192.168.122.16 port 22: Connection refused

fail2banの状態を確認してみます。192.168.122.213からのアクセスが禁止されたことがわかります。

[root@server ~]# fail2ban-client status sshd
Status for the jail: sshd
|- Filter
|  |- Currently failed: 1
|  |- Total failed:     3
|  `- Journal matches:  _SYSTEMD_UNIT=sshd.service + _COMM=sshd
`- Actions
   |- Currently banned: 1
   |- Total banned:     1
   `- Banned IP list:   192.168.122.213

netfilterのアクセス定義を確認してみます。22番ポートのアクセス禁止にするルールが設定されていることがわかります。

[root@server ~]# nft list ruleset|grep -A2 filter_IN_public_deny
                jump filter_IN_public_deny
                jump filter_IN_public_allow
                jump filter_IN_public_post
--
        chain filter_IN_public_deny {
                ip saddr 192.168.122.213 tcp dport 22 ct state { new, untracked } reject with icmp port-unreachable
        }

192.168.122.213からのアクセス禁止を解除します。

[root@server ~]# fail2ban-client set sshd unbanip 192.168.122.213
0

fail2banの状態を確認してみます。192.168.122.213からのアクセス禁止が解除されたことがわかります。

[root@server ~]#  fail2ban-client status sshd
Status for the jail: sshd
|- Filter
|  |- Currently failed: 0
|  |- Total failed:     3
|  `- Journal matches:  _SYSTEMD_UNIT=sshd.service + _COMM=sshd
`- Actions
   |- Currently banned: 0
   |- Total banned:     1
   `- Banned IP list:

8 実験2(HTTPアクセスの禁止)

HTTP GETやHTTP HEADを連続して送信するアクセス元をアクセス禁止にしてみます。

8.1 事前準備(fail2banの設定)

設定ファイルを作成します。設定内容は以下のとおりです。

  • 監視ポート番号(port):80,443
  • フィルタ(filter):http-get-dos.conf
  • 監視するファイル(logpath):/var/log/httpd/access_log
  • アクセス禁止時間(bantime):600秒
  • 監視時間(findtime):10秒
  • リトライ回数(maxRetry):2回
[root@server ~]# vi /etc/fail2ban/jail.local
[root@server ~]# cat /etc/fail2ban/jail.local
[http-get-dos]
enabled = true
port = http,https
filter = http-get-dos
logpath   = /var/log/httpd/access_log
bantime = 600
findtime = 10
maxRetry = 2

フィルタを作成します。フィルタの内容は次のとおりです。/var/log/httpd/access_logに次の正規表現に合致するログが出力されたら、接続元からのアクセス拒否します。

  • HOST:行頭がホスト名、またはIPアドレス(IPv4,IPv6)
  • GET|HEAD:HTTPメソッドがGETまたHEAD
[root@server ~]# vi /etc/fail2ban/filter.d/http-get-dos.conf
[root@server ~]# cat /etc/fail2ban/filter.d/http-get-dos.conf
[Definition]
failregex = ^<HOST> -.*"(GET|HEAD).*
ignoreregex =

fail2banを起動します。

[root@server ~]# fail2ban-client restart
Shutdown successful
Server ready

fail2banの状態を確認します。

[root@server ~]# fail2ban-client status
Status
|- Number of jail:      1
`- Jail list:   http-get-dos

fail2banの状態を確認します。クライアントからのアクセス拒否が解除されたことがわかります。

[root@server ~]# fail2ban-client status http-get-dos
Status for the jail: http-get-dos
|- Filter
|  |- Currently failed: 0
|  |- Total failed:     0
|  `- File list:        /var/log/httpd/access_log
`- Actions
   |- Currently banned: 0
   |- Total banned:     0
   `- Banned IP list:

8.2 事前準備(httpdの設定)

httpdの設定ファイルを作成します。

[root@server ~]# vi /var/www/html/index.html
[root@server ~]# cat /var/www/html/index.html
Hello

httpdサービスを起動します。

[root@server ~]# systemctl restart httpd

httpdがListenしているポート番号を確認します。httpdTCPの80番ポートでListenしていることがわかります。なお、lsofコマンドの使い方は、lsofコマンドの使い方 - hana_shinのLinux技術ブログを参照してください。

[root@server ~]# lsof -c httpd -a -i -a -nP
COMMAND  PID   USER   FD   TYPE DEVICE SIZE/OFF NODE NAME
httpd   1489   root    4u  IPv6  21849      0t0  TCP *:80 (LISTEN)
httpd   1492 apache    4u  IPv6  21849      0t0  TCP *:80 (LISTEN)
httpd   1493 apache    4u  IPv6  21849      0t0  TCP *:80 (LISTEN)
httpd   1494 apache    4u  IPv6  21849      0t0  TCP *:80 (LISTEN)

httpdがListenしている80番ポートへのアクセスを解放します。なお、firewall-cmdコマンドの使い方は、trace-cmdコマンドの使い方 - hana_shinのLinux技術ブログを参照してください。

[root@server ~]# firewall-cmd --add-port=80/tcp
success

開放したポート番号を確認します。80番ポートへのアクセスが解放されていることがわかります。

[root@server ~]# firewall-cmd --list-ports
80/tcp

8.3 動作確認

ここでは、curlコマンドを使って、GETメソッドをサーバに送信してみます。なお、HEADメソッドは、curlの-Iオプションを使って送信できます。どちらのメソッドを使っても、アクセスが禁止されることが確認できます。

サーバにhttpアクセスします。

[root@client ~]# date;curl http://192.168.122.16
2023年  5月 24日 水曜日 20:27:15 JST
Hello

サーバにhttpアクセスします(リトライ1回目)。

[root@client ~]# date;curl http://192.168.122.16
2023年  5月 24日 水曜日 20:27:17 JST
Hello

サーバにhttpアクセスします(リトライ2回目)。

[root@client ~]# date;curl http://192.168.122.16
2023年  5月 24日 水曜日 20:27:18 JST
Hello

サーバにhttpアクセスします。10秒間で2回目のリトライをしたので、3回目のアクセスが拒否されました。

[root@client ~]# date;curl http://192.168.122.16
2023年  5月 24日 水曜日 20:27:19 JST
curl: (7) Failed to connect to 192.168.122.16 port 80: 接続を拒否されました

fail2banの状態を確認します。クライアントからのアクセスが拒否されていることがわかります。

[root@server ~]# fail2ban-client status http-get-dos
Status for the jail: http-get-dos
|- Filter
|  |- Currently failed: 0
|  |- Total failed:     2
|  `- File list:        /var/log/httpd/access_log
`- Actions
   |- Currently banned: 1
   |- Total banned:     1
   `- Banned IP list:   192.168.122.213

クライアントからのアクセス拒否を解除します。

[root@server ~]# fail2ban-client set http-get-dos unbanip 192.168.122.213
1

fail2banの状態を確認します。

[root@server ~]# fail2ban-client status http-get-dos
Status for the jail: http-get-dos
|- Filter
|  |- Currently failed: 0
|  |- Total failed:     2
|  `- File list:        /var/log/httpd/access_log
`- Actions
   |- Currently banned: 0
   |- Total banned:     1
   `- Banned IP list:

Z 参考情報

私が業務や記事執筆で参考にした書籍を以下のページに記載します。
Linux技術のスキルアップをしよう! - hana_shinのLinux技術ブログ


https://www.linode.com/docs/guides/using-fail2ban-to-secure-your-server-a-tutorial/

rpmコマンドの使い方(query-options編)

1 はじめに

rpmコマンドの--query-optionsオプションは、パッケージに関する様々な情報を表示するためのオプションです。ここでは、--query-optionsオプションを使用してパッケージに関するさまざまな情報を表示してみます。

2 検証環境

AlmaLinux版数は以下のとおりです。

[root@server ~]# cat /etc/redhat-release
AlmaLinux release 8.6 (Sky Tiger)

カーネル版数は以下のとおりです。

[root@server ~]# uname -r
4.18.0-372.9.1.el8.x86_64

rpmの版数は以下のとおりです。

[root@server ~]# rpm --version
RPM バージョン 4.14.3

3 オプション一覧

query-optionsの一覧は以下のとおりです。

[root@server ~]# man rpm
-snip-
   query-options(検索オプション)
       [--changelog] [-c,--configfiles] [-d,--docfiles] [--dump]
       [--filesbypkg] [-i,--info] [--last] [-l,--list]
       [--provides] [--qf,--queryformat QUERYFMT] [-R,--requires]
       [--scripts] [-s,--state] [--triggers,--triggerscripts]

4 変更履歴を表示する方法(--changelog)

--changelogは、パッケージの変更履歴を表示するオプションです。ここでは、httpdパッケージの変更履歴を確認してみます。左端に*印の行が変更日付と変更者名を表しています。-印は変更内容を表しています。

[root@server ~]# rpm -q --changelog httpd
* 土  3月 18 2023 Lubo? Uhliarik <luhliari@redhat.com> - 2.4.37-51.5
- Resolves: #2177747 - CVE-2023-25690 httpd:2.4/httpd: HTTP request splitting
  with mod_rewrite and mod_proxy

* 火  1月 31 2023 Lubo? Uhliarik <luhliari@redhat.com> - 2.4.37-51.1
- Resolves: #2165967 - prevent sscg creating /dhparams.pem
- Resolves: #2165976 - CVE-2006-20001 httpd: mod_dav: out-of-bounds read/write
  of zero byte
- Resolves: #2165977 - CVE-2022-37436 httpd: mod_proxy: HTTP response splitting
- Resolves: #2165978 - CVE-2022-36760 httpd: mod_proxy_ajp: Possible request
  smuggling
-snip-

5 パッケージに含まれる設定ファイルを表示する方法(-c)

-cは、パッケージに含まれる設定ファイルの一覧を表示するオプションです。ここでは、httpdパッケージに含まれる設定ファイルの一覧を表示してみます。

[root@server ~]# rpm -qc httpd
/etc/httpd/conf.d/autoindex.conf
/etc/httpd/conf.d/userdir.conf
/etc/httpd/conf.d/welcome.conf
-snip-

6 パッケージに含まれるドキュメントファイルを表示する方法(--docfiles )

--docfilesは、パッケージに含まれるドキュメントファイル一覧を表示するオプションです。ここでは、httpdパッケージに含まれるドキュメントファイル一覧を表示してみます。

[root@server ~]# rpm -q --docfiles httpd
/usr/share/doc/httpd/ABOUT_APACHE
/usr/share/doc/httpd/CHANGES
/usr/share/doc/httpd/LICENSE
/usr/share/doc/httpd/NOTICE
/usr/share/doc/httpd/README
-snip-

7 パッケージの情報を表示する方法(-i)

-iは、パッケージの情報を表示するオプションです。ここでは、httpdパッケージの情報を表示してみます。

[root@server ~]# rpm -qi httpd
Name        : httpd
Version     : 2.4.37
Release     : 51.module_el8.7.0+3405+9516b832.1
Architecture: x86_64
Install Date: 2023年03月31日 21時26分04秒
Group       : System Environment/Daemons
Size        : 4500255
License     : ASL 2.0
Signature   : RSA/SHA256, 2023年02月21日 20時19分50秒, Key ID 51d6647ec21ad6ea
Source RPM  : httpd-2.4.37-51.module_el8.7.0+3405+9516b832.1.src.rpm
Build Date  : 2023年02月21日 19時24分32秒
Build Host  : x64-builder01.almalinux.org
Relocations : (not relocatable)
Packager    : AlmaLinux Packaging Team <packager@almalinux.org>
Vendor      : AlmaLinux
URL         : https://httpd.apache.org/
Summary     : Apache HTTP Server
Description :
The Apache HTTP Server is a powerful, efficient, and extensible
web server.

8 パッケージのインストール履歴を表示する方法(--last)

--lastは、パッケージのインストール履歴を表示するオプションです。インストール履歴を確認すると、最後にbcパッケージがインストールされたことがわかります。

[root@server ~]# rpm -qa --last |head -n 3
bc-1.07.1-5.el8.x86_64                        2023年05月22日 21時56分53秒
bind-9.11.36-5.el8_7.2.x86_64                 2023年05月05日 20時36分33秒
mailx-12.5-29.el8.x86_64                      2023年04月22日 20時50分07秒
-snip-

9 パッケージに含まれるファイル一覧を表示する方法(-l)

-lは、パッケージに含まれるファイル一覧を表示するオプションです。ここはで、httpdパッケージに含まれるファイル一覧を表示してみます。

[root@server ~]# rpm -ql httpd 
/etc/httpd/conf
/etc/httpd/conf.d/autoindex.conf
/etc/httpd/conf.d/userdir.conf
-snip-

10 パッケージの特定の情報を取り出す方法(--queryformat)

--queryformatは、パッケージ情報(名前やサイズ等)のフォーマットを指定するためのオプションです。

httpdパッケージの名前を表示してみます。

[root@server ~]# rpm -q httpd --queryformat '%{NAME}\n'
httpd

httpdパッケージの名前、バージョンを表示してみます。

[root@server ~]# rpm -q httpd --queryformat '%{NAME}-%{VERSION}\n'
httpd-2.4.37

httpdパッケージの名前とパッケージ提供元のURLを表示してみます。

[root@server ~]# rpm -q httpd --queryformat '%{NAME}:%{URL}\n'
httpd:https://httpd.apache.org/

httpdパッケージの名前とライセンスを表示してみます。

[root@server ~]# rpm -q httpd --queryformat '%{NAME}:%{LICENSE}\n'
httpd:ASL 2.0

httpdパッケージの名前とパッケージ提供元を表示してみます。

[root@server ~]# rpm -q httpd --queryformat '%{NAME}:%{VENDOR}\n'
httpd:AlmaLinux

最後にシステムにインスールされている全てのパッケージ名とサイズを表示してみます。

[root@server ~]# rpm -qa --queryformat "%{NAME} %{SIZE}\n" 
ghc-mtl 222647
libXxf86vm 26424
tzdata 1891990
-snip

11 パッケージのインストール/アンインストール時に実行するスクリプトを表示する方法(--scripts)

--scriptsは、パッケージに含まれるインストールやアンインストール時に実行するスクリプトを表示するオプションです。ここでは、chronyパッケージに含まれるスクリプトを表示してみます。以下の実行結果より、4種類のスクリプトが実行されることがわかります。

  • preinstall :インストール前に実行
  • postinstall :インストール完了後に実行
  • preuninstall:アンインストール前に実行
  • postuninstall :アンインストール完了後に実行
[root@server ~]# rpm -q --scripts chrony
preinstall scriptlet (using /bin/sh):
getent group chrony > /dev/null || /usr/sbin/groupadd -r chrony
getent passwd chrony > /dev/null || /usr/sbin/useradd -r -g chrony \
       -d /var/lib/chrony -s /sbin/nologin chrony
:
postinstall scriptlet (using /bin/sh):
# fix PIDFile in local chronyd.service on upgrades from chrony < 3.3-2
if grep -q 'PIDFile=/var/run/chronyd.pid' \
                /etc/systemd/system/chronyd.service 2> /dev/null && \
        ! grep -qi '^[ '$'\t'']*pidfile' /etc/chrony.conf 2> /dev/null
then
        sed -i '/PIDFile=/s|/run/|/run/chrony/|' \
                /etc/systemd/system/chronyd.service
fi
# workaround for late reload of unit file (#1614751)
/usr/bin/systemctl daemon-reload

if [ $1 -eq 1 ] ; then
        # Initial installation
        systemctl --no-reload preset chronyd.service chrony-wait.service &>/dev/null || :
fi
preuninstall scriptlet (using /bin/sh):

if [ $1 -eq 0 ] ; then
        # Package removal, not upgrade
        systemctl --no-reload disable --now chronyd.service chrony-wait.service &>/dev/null || :
fi
postuninstall scriptlet (using /bin/sh):

if [ $1 -ge 1 ] ; then
        # Package upgrade, not uninstall
        systemctl try-restart chronyd.service &>/dev/null || :
fi

12 パッケージに含まれる全てのファイルを表示する方法

--filesbypkgは、パッケージに含まれる全てのファイルを表示するオプションです。

[root@server ~]# rpm -q --filesbypkg httpd
httpd                     /etc/httpd/conf
httpd                     /etc/httpd/conf.d/autoindex.conf
httpd                     /etc/httpd/conf.d/userdir.conf
httpd                     /etc/httpd/conf.d/welcome.conf
httpd                     /etc/httpd/conf.modules.d
-snip-

Z 参考情報

私が業務や記事執筆で参考にした書籍を以下のページに記載します。
Linux技術のスキルアップをしよう! - hana_shinのLinux技術ブログ

rpm: Query formats

tcpdumpのフックポイント、Netfilterのチェイン、Qdiscのカーネル内の場所

1 はじめに

tcpdumpのフックポイント、Netfilterのチェイン、Qdiscの場所についてまとめました。これらの位置を理解しておくと、ネットワークのトラブルシューティング等に役立ちます。

2 検証環境

AlmaLinuxの版数は以下のとおりです。

[root@server ~]# cat /etc/redhat-release
AlmaLinux release 8.6 (Sky Tiger)

カーネル版数は以下のとおりです。

[root@server ~]# uname -r
4.18.0-372.9.1.el8.x86_64

3 鳥瞰図

ドライバとトランスポート層の間の関数の呼び出し関係を以下に図示します。この図は、systemtapを使ってサーバ/クライアントの2台構成の環境でncコマンドを実行した際の関数呼び出しを確認したもので、図の左側が受信処理、右側が送信処理を表しています。楕円の内側には関数名が表示されていますが、すべての関数が図示されているわけではありません。また、ドライバとトランスポート層の間の適切な用語が見当たらないため、便宜上デバイス層と呼ぶことにします。


図中の網掛け部分について以下に説明します。

網掛けの色 概要
黄色 iptablesコマンドでパケット廃棄等のルールを設定する場所です。チェインと呼ばれています。デフォルトで5つのチェインが定義されています。
緑色 ルーティング処理を実行する場所です。宛先IPアドレスをキーにルーティングテーブルを検索して宛先を決定します。
オレンジ色 ルーティング処理を実行すると、その結果に応じて dst_input および dst_output に関数へのポインタが設定されます。たとえば、受信パケットに対してルーティング処理を実行すると、宛先IPアドレスが自分宛のパケットの場合には dst_input に ip_local_deliver 関数へのポインタ、他のサーバ宛ての場合にはdst_input に ip_forward 関数へのポインタが設定されます。
赤色 tcpdumpのフックポイントです。tcpdump/tsharkコマンドを実行すると、フックポイントの関数が呼び出され、送受信のパケットがキャプチャされます。
青色 Qdiscと呼ばれる場所です。Traffic Control(交通整理)を実行する場所です。tcコマンドは、Qdiscに対してパケットの遅延、廃棄、並び替えを実行します。
灰色 ドライバ関数へのポインタが設定されています。ops->ndo_start_xmitを呼び出すと、NICに対応したドライバ関数が実行されます。ここでは、e1000_xmit_frame関数(Intelのe1000eドライバ)を図示しています。

4 関数の概要

4.1 受信処理

レイヤ 関数名 概要
トランスポート層 tcp_v4_rcv TCPの受信処理入り口関数です。
udp_rcv UDPの受信処理入り口関数です。
インターネット層 ip_protocol_deliver_rcu IPヘッダに設定されているプロトコル番号(TCP=6,UDP=17)にしたがって、TCPまたはUDPの受信処理入り口関数を呼び出します。
ip_local_deliver ルーティング処理の結果、受信パケットが自分宛のパケットを処理します。フラグメントされたIPパケットを元の1つのIPパケットに再構築します。そして、INPUTチェインを実行します。
        ip_rcv_finish ルーティング処理を呼び出します。
      ip_rcv IPの受信処理入り口の関数です。IPヘッダのサイズやIPのバージョンをチェックします。そして、PREROUTINGチェインを実行します。
バイス net_rx_action ソフト割り込みの入り口関数です。ソフト割り込みの延長でプロトコルの受信処理が行われます。
ドライバ e1000_intr_msix_rx NICの受信バッファからドライバのリングバッファ(受信バッファ)に受信パケットのDMA転送が完了すると、受信完了割り込みが発生します。この受信完了割り込みで呼び出す関数です。この関数はrequest_irq関数で事前に登録したものです。

4.2 送信処理

レイヤ 関数名 概要
トランスポート層 tcp_transmit_skb TCPヘッダを組み立てて、送信パケットをIP層に引き渡します。
udp_send_skb UDPヘッダを組み立てて、送信パケットをIP層に引き渡します。
インターネット層 ip_local_out IPの送信処理入り口の関数です。IPヘッダにIPパケット長、チェックサム値を設定したあと、OUTPUTチェインを実行します。
ip_output 送信パケットの管理情報(sk_buff構造体)を更新します。そして、POSTROUTINGチェインを実行します。
バイス qdisc_run Qdiscを呼び出して、Traffic Controlを実行します。
ドライバ e1000_xmit_frame 送信パケットをドライバのリングバッファ(送信バッファ)にマッピングしたあと、NICに対してDMA転送を要求します。
e1000_intr_msix_tx リングバッファからNICの送信バッファに送信パケットのDMA転送が完了すると、送信完了割り込みが発生します。この送信完了割り込みで呼び出す関数です。この関数はrequest_irq関数で事前に登録したものです。

4.3 転送処理

レイヤ 関数名 概要
インターネット層 ip_forward パケットの転送処理をします。IPヘッダのTTL(Time To Live)が1以下のパケットは廃棄します。それ以外のパケットはTTLを1減算します。そして、FORWARDINGチェインを実行します。
ip_forward_finish dst_outputを実行します。dst_outputにはip_output関数へのポインタが設定されています。

Linux Malware Detectの使い方

1 LMD(Linux Malware Detect)とは

LMDはマルウェアを検出するツールです。さらに、ファイル/ディレクトリ等の作成、変更、削除を検知することができます。これにより、マルウェアが新しいファイルを作成するなどの不審な動きを検出することができます。なお、ファイル/ディレクトリ等の作成、変更、削除は、AIDEの使い方 - hana_shinのLinux技術ブログを使っても検知することができます。

2 検証環境

AlmaLinux版数は以下のとおりです。

[root@server ~]# cat /etc/redhat-release
AlmaLinux release 8.6 (Sky Tiger)

カーネル版数は以下のとおりです。

[root@server ~]# uname -r
4.18.0-372.9.1.el8.x86_64

3 インストール方法

以下の公式ページをもとに、LMDをインストールしました。
Linux Malware Detect – R-fx Networks

公式ページの説明にしたがって、LMDのtar.gzファイルをダウンロードします。

[root@server ~]# wget https://www.rfxn.com/downloads/maldetect-current.tar.gz

ダウンロードしたファイルを確認します。

[root@server ~]# ls -l maldetect-current.tar.gz
-rw-r--r--. 1 root root 1647506  4月 10 21:58 maldetect-current.tar.gz

ダウンロードしたファイルを解凍します。

[root@server ~]# tar xvf maldetect-current.tar.gz

解凍したディレクトリに移動します。

[root@server ~]# cd maldetect-1.6.5/
[root@server maldetect-1.6.5]# ls
CHANGELOG  CHANGELOG.RELEASE  CHANGELOG.VARIABLES  COPYING.GPL  README  cron.d.pub  cron.daily  files  install.sh

install.shを実行してLMDをインストールします。LMVの版数がv1.6.5であることがわかります。

[root@server maldetect-1.6.5]# ./install.sh
Created symlink /etc/systemd/system/multi-user.target.wants/maldet.service → /usr/lib/systemd/system/maldet.service.
Linux Malware Detect v1.6.5
            (C) 2002-2023, R-fx Networks <proj@r-fx.org>
            (C) 2023, Ryan MacDonald <ryan@r-fx.org>
This program may be freely redistributed under the terms of the GNU GPL

installation completed to /usr/local/maldetect
config file: /usr/local/maldetect/conf.maldet
exec file: /usr/local/maldetect/maldet
exec link: /usr/local/sbin/maldet
exec link: /usr/local/sbin/lmd
cron.daily: /etc/cron.daily/maldet
maldet(2681): {sigup} performing signature update check...
maldet(2681): {sigup} local signature set is version 20230331490193
maldet(2681): {sigup} new signature set 202304191182804 available
maldet(2681): {sigup} downloading https://cdn.rfxn.com/downloads/maldet-sigpack.tgz
maldet(2681): {sigup} downloading https://cdn.rfxn.com/downloads/maldet-cleanv2.tgz
maldet(2681): {sigup} verified md5sum of maldet-sigpack.tgz
maldet(2681): {sigup} unpacked and installed maldet-sigpack.tgz
maldet(2681): {sigup} verified md5sum of maldet-clean.tgz
maldet(2681): {sigup} unpacked and installed maldet-clean.tgz
maldet(2681): {sigup} signature set update completed
maldet(2681): {sigup} 17637 signatures (14801 MD5 | 2053 HEX | 783 YARA | 0 USER)

設定ファイル(conf.maldet)を確認すると、ClamAVは、大量のファイルをスキャンする場合、パフォーマンスを向上する、と説明があります。私の環境では、ClamAVがインストールされていなかったので、ClamAVをインストールしました。

[root@server ~]# less /usr/local/maldetect/conf.maldet
-snip-
# If installed, use ClamAV clamscan binary as default scan engine which
# provides improved scan performance on large file sets. The clamscan
# engine is used in conjunction with native ClamAV signatures updated
# through freshclam along with LMD signatures providing additional
# detection capabilities.
# [ 0 = disabled, 1 = enabled ]
scan_clamscan="1"

clamavはepelリポジトリに含まれているため、まずepel-releaseパッケージをインストールします。

[root@server ~]# dnf -y install epel-release

次に、clamavパッケージをインストールします。

[root@server ~]# dnf -y install clamav*

インストールしたパッケージを確認します。以下のパッケージがインストールされました。

[root@server ~]# rpm -qa|grep clamav
clamav-update-0.103.8-3.el8.x86_64
clamav-doc-0.103.8-3.el8.noarch
clamav-milter-0.103.8-3.el8.x86_64
clamav-filesystem-0.103.8-3.el8.noarch
clamav-unofficial-sigs-7.2.5-4.el8.noarch
clamav-0.103.8-3.el8.x86_64
clamav-devel-0.103.8-3.el8.x86_64
clamav-lib-0.103.8-3.el8.x86_64
clamav-data-0.103.8-3.el8.noarch

4 オプション一覧

オプションは以下のとおりです。

[root@server ~]# maldet -h
Linux Malware Detect v1.6.5
            (C) 2002-2023, R-fx Networks <proj@rfxn.com>
            (C) 2023, Ryan MacDonald <ryan@rfxn.com>
This program may be freely redistributed under the terms of the GNU GPL v2

signature set: 202304191182804
usage /usr/local/sbin/maldet [ OPTION ]
    -b, --background
      Execute operations in the background, ideal for large scans
      e.g: maldet -b -r /home/?/public_html 7

    -u, --update-sigs [--force]
       Update malware detection signatures from rfxn.com

    -d, --update-ver [--force]
       Update the installed version from rfxn.com

    -f, --file-list
       Scan files or paths defined in line spaced file
       e.g: maldet -f /root/scan_file_list

    -r, --scan-recent PATH DAYS
       Scan files created/modified in the last X days (default: 7d, wildcard: ?)
       e.g: maldet -r /home/?/public_html 2

    -a, --scan-all PATH
       Scan all files in path (default: /home, wildcard: ?)
       e.g: maldet -a /home/?/public_html

    -i, --include-regex REGEX
       Include paths/files from file list based on supplied posix-egrep regular
       expression.
       e.g: To include only paths named wp-content and files ending in .php:
       --include-regex ".*/wp-content/.*|.*.php$"

    -x, --exclude-regex REGEX
       Exclude paths/files from file list based on supplied posix-egrep regular
       expression.
       e.g: To exclude paths containing 'wp-content/w3tc/' and core files:
       --exclude-regex ".*wp-content/w3tc/.*|.*core.[0-9]+$"

    -m, --monitor USERS|PATHS|FILE|RELOAD
       Run maldet with inotify kernel level file create/modify monitoring
       If USERS is specified, monitor user homedirs for UID's > 500
       If FILE is specified, paths will be extracted from file, line spaced
       If PATHS are specified, must be comma spaced list, NO WILDCARDS!
       e.g: maldet --monitor users
       e.g: maldet --monitor /root/monitor_paths
       e.g: maldet --monitor /home/mike,/home/ashton

    -k, --kill-monitor
       Terminate inotify monitoring service

    -c, --checkout FILE
       Upload suspected malware to rfxn.com for review & hashing into signatures

    -l, --log
       View maldet log file events

    -e, --report SCANID email
       View scan report of most recent scan or of a specific SCANID and optionally
       e-mail the report to a supplied e-mail address
       e.g: maldet --report
       e.g: maldet --report list
       e.g: maldet --report 050910-1534.21135
       e.g: maldet --report SCANID user@domain.com

    -s, --restore FILE|SCANID
       Restore file from quarantine queue to orginal path or restore all items from
       a specific SCANID
       e.g: maldet --restore /usr/local/maldetect/quarantine/config.php.23754
       e.g: maldet --restore 050910-1534.21135

    -q, --quarantine SCANID
       Quarantine all malware from report SCANID
       e.g: maldet --quarantine 050910-1534.21135

    -n, --clean SCANID
       Try to clean & restore malware hits from report SCANID
       e.g: maldet --clean 050910-1534.21135

    -U, --user USER
       Set execution under specified user, ideal for restoring from user quarantine or
       to view user reports.
       e.g: maldet --user nobody --report
       e.g: maldet --user nobody --restore 050910-1534.21135

    -co, --config-option VAR1=VALUE,VAR2=VALUE,VAR3=VALUE
       Set or redefine the value of conf.maldet config options
       e.g: maldet --config-option email_addr=you@domain.com,quarantine_hits=1

    -p, --purge
       Clear logs, quarantine queue, session and temporary data.

    --web-proxy IP:PORT
       Enable use of HTTP/HTTPS proxy for all remote URL calls.

5 設定ファイルの編集

次の設定項目をデフォルト値から変更しました。

設定項目 意味
scan_ignore_root rootが所有者のファイルもスキャンします。ただし、スキャン対象のファイルが多くなるため、スキャン完了までの時間が増えます
quarantine_hits ウィルスに感染したファイルを検出すると、そのファイルをユーザがアクセスできないディレクトに移動します(ここでは検疫と呼びます)

デフォルトの設定ファイルを保存します。

[root@server ~]# cp /usr/local/maldetect/conf.maldet /usr/local/maldetect/conf.maldet.org

デフォルト値から変更した値を確認します。scan_ignore_rootは1から0、quarantine_hitsは0から1に変更しました。

[root@server ~]# diff -Nur /usr/local/maldetect/conf.maldet.org /usr/local/maldetect/conf.maldet
--- /usr/local/maldetect/conf.maldet.org        2023-04-20 21:11:35.472656234 +0900
+++ /usr/local/maldetect/conf.maldet    2023-04-20 21:12:18.022149296 +0900
@@ -191,7 +191,7 @@
 # and as such it makes sense to ignore files that are root owned. It is
 # recommended to leave this enabled for best performance.
 # [ 0 = disabled, 1 = enabled ]
-scan_ignore_root="1"
+scan_ignore_root="0"

 # This allows for specific user or groups to be ignored entirely from scan
 # file lists. This option should be used with care and is not ideal for
@@ -225,7 +225,7 @@
 ##
 # The default quarantine action for malware hits
 # [0 = alert only, 1 = move to quarantine & alert]
-quarantine_hits="0"
+quarantine_hits="1"

 # Try to clean string based malware injections
 # [NOTE: quarantine_hits=1 required]

6 LMDのバージョンをアップデートする方法(-d)

"-d"はLMDのバージョンをアップデートするオプションです。以下の実行結果より、”latest version already installed"が出力されているので、LMDの最新バージョンがインストールされていることがわかります。

[root@server ~]# maldet -d
Linux Malware Detect v1.6.5
            (C) 2002-2023, R-fx Networks <proj@rfxn.com>
            (C) 2023, Ryan MacDonald <ryan@rfxn.com>
This program may be freely redistributed under the terms of the GNU GPL v2

maldet(3243): {update} checking for available updates...
maldet(3243): {update} hashing install files and checking against server...
maldet(3243): {update} latest version already installed.

7 署名をアップデートする方法(-u)

"-u"は署名をアップデートするオプションです。署名の最新は202304191182804であることがわかります。署名は簡単に言うとスキャン対象のマルウェア一覧のことです。

[root@server ~]# maldet -u
Linux Malware Detect v1.6.5
            (C) 2002-2023, R-fx Networks <proj@rfxn.com>
            (C) 2023, Ryan MacDonald <ryan@rfxn.com>
This program may be freely redistributed under the terms of the GNU GPL v2

maldet(3406): {sigup} performing signature update check...
maldet(3406): {sigup} local signature set is version 202304191182804
maldet(3406): {sigup} latest signature set already installed

8 指定したパスをスキャンする方法(-a)

"-a"は指定したパスをスキャンするオプションです。ここでは、/root/bashdb-4.4-1.0.1配下のファイルをスキャンしてみます。

[root@server ~]# maldet -a /root/bashdb-4.4-1.0.1
Linux Malware Detect v1.6.5
            (C) 2002-2023, R-fx Networks <proj@rfxn.com>
            (C) 2023, Ryan MacDonald <ryan@rfxn.com>
This program may be freely redistributed under the terms of the GNU GPL v2

maldet(11704): {scan} signatures loaded: 17637 (14801 MD5 | 2053 HEX | 783 YARA | 0 USER)
maldet(11704): {scan} building file list for /root/bashdb-4.4-1.0.1, this might take awhile...
maldet(11704): {scan} setting nice scheduler priorities for all operations: cpunice 19 , ionice 6
maldet(11704): {scan} file list completed in 0s, found 593 files...
maldet(11704): {scan} found clamav binary at /usr/bin/clamscan, using clamav scanner engine...
maldet(11704): {scan} scan of /root/bashdb-4.4-1.0.1 (593 files) in progress...

maldet(11704): {scan} scan completed on /root/bashdb-4.4-1.0.1: files 593, malware hits 0, cleaned hits 0, time 59s
maldet(11704): {scan} scan report saved, to view run: maldet --report 230420-2214.11704

スキャンを実行している間、プロセスの状態を確認するために ps コマンドを使用します。maldet コマンドを実行すると、clamscan プロセスが動作していることが分かります。

[root@server ~]# ps -p 12064 -o comm,pid,ppid,%cpu,args
COMMAND             PID    PPID %CPU COMMAND
bash              12064    2924  0.0 bash /usr/local/sbin/maldet -a /root/bashdb-4.4-1.0.1

[root@server ~]# ps -C clamscan -o comm,pid,ppid,%cpu,args
COMMAND             PID    PPID %CPU COMMAND
clamscan          12280   12064 96.9 /usr/bin/clamscan --max-filesize=6947618 --max-scansize=13895236 -d /usr/local/maldetect/tmp/.runtime.user.12064.hdb -d

実行結果の最後の行に"run :maldet --report 230420-2214.11704"とあるので、そのとおり実行してみます。マルウェアは存在しなかったことがわかります(TOTAL HITS: 0)。

[root@server ~]# maldet --report 230420-2214.11704
HOST:      server
SCAN ID:   230420-2214.11704
STARTED:    4月 20 2023 22:14:51 +0900
COMPLETED:  4月 20 2023 22:15:50 +0900
ELAPSED:   59s [find: 0s]

PATH:          /root/bashdb-4.4-1.0.1
TOTAL FILES:   593
TOTAL HITS:    0
TOTAL CLEANED: 0

===============================================
Linux Malware Detect v1.6.5 < proj@rfxn.com >

9 ログを確認する方法(-l)

"-l"はLMDが出力するログを確認するオプションです。

[root@server ~]# maldet -l
-snip-
 4月 20 2023 22:14:52 server maldet(11704): {scan} scan of /root/bashdb-4.4-1.0.1 (593 files) in progress...
 4月 20 2023 22:15:50 server maldet(11704): {scan} scan completed on /root/bashdb-4.4-1.0.1: files 593, malware hits 0, cleaned hits 0, time 59s
 4月 20 2023 22:15:50 server maldet(11704): {scan} scan report saved, to view run: maldet --report 230420-2214.11704

10 ログをクリアする方法(-p)

"-p"はログをクリアするオプションです。

[root@server ~]# maldet -p
Linux Malware Detect v1.6.5
            (C) 2002-2023, R-fx Networks <proj@rfxn.com>
            (C) 2023, Ryan MacDonald <ryan@rfxn.com>
This program may be freely redistributed under the terms of the GNU GPL v2

/usr/bin/wc: /usr/local/maldetect/logs/inotify_log: そのようなファイルやディレクトリはありません
cat: /usr/local/maldetect/tmp/inotify: そのようなファイルやディレクトリはありません
maldet(12241): {glob} logs and quarantine data cleared by user request (-p)

ログを確認します。ログがクリアされたことがわかります。

[root@server ~]# maldet -l
Linux Malware Detect v1.6.5
            (C) 2002-2023, R-fx Networks <proj@rfxn.com>
            (C) 2023, Ryan MacDonald <ryan@rfxn.com>
This program may be freely redistributed under the terms of the GNU GPL v2

Viewing last 50 lines from /usr/local/maldetect/logs/event_log:
 4月 20 2023 22:18:40 server maldet(12241): {mon} inotify log file trimmed
 4月 20 2023 22:18:40 server maldet(12241): {glob} logs and quarantine data cleared by user request (-p)

11 スキャン対象のパスをファイルで指定する方法(-f)

"-f"はスキャン対象のパスをファイルで指定するオプションです。今回は、/sbinと/usr/binをスキャン対象に指定するためのファイル(ここではリストファイルと呼びます)を作成します。

[root@server ~]# cat scan_file_list
/sbin/
/usr/bin

"-f"オプションに続けて、リストファイルの絶対パスを指定します。

[root@server ~]# maldet -f /root/scan_file_list
Linux Malware Detect v1.6.5
            (C) 2002-2023, R-fx Networks <proj@rfxn.com>
            (C) 2023, Ryan MacDonald <ryan@rfxn.com>
This program may be freely redistributed under the terms of the GNU GPL v2

maldet(19372): {scan} signatures loaded: 17637 (14801 MD5 | 2053 HEX | 783 YARA | 0 USER)
maldet(19372): {scan} user supplied file list '/root/scan_file_list', found 2 files...
maldet(19372): {scan} found clamav binary at /usr/bin/clamscan, using clamav scanner engine...
maldet(19372): {scan} scan of  (2 files) in progress...

maldet(19372): {scan} scan completed on : files 2, malware hits 0, cleaned hits 0, time 96s
maldet(19372): {scan} scan report saved, to view run: maldet --report 230422-2126.19372

12 スキャンの結果を確認する方法(-e)

maldet -eを実行すると、最後に実行したスキャンのレポートが表示されます。

[root@server ~]# maldet -e
HOST:      server
SCAN ID:   230422-2126.19372
STARTED:    4月 22 2023 21:26:37 +0900
COMPLETED:  4月 22 2023 21:28:13 +0900
ELAPSED:   96s [find: s]

PATH:
RANGE:         /root/scan_file_list days
TOTAL FILES:   2
TOTAL HITS:    0
TOTAL CLEANED: 0

===============================================
Linux Malware Detect v1.6.5 < proj@rfxn.com >

maldet -eコマンドの引数にlistを指定すると、スキャンの実行履歴一覧を表示することができます。

[root@server ~]# maldet -e list
Linux Malware Detect v1.6.5
            (C) 2002-2023, R-fx Networks <proj@rfxn.com>
            (C) 2023, Ryan MacDonald <ryan@rfxn.com>
This program may be freely redistributed under the terms of the GNU GPL v2

4月  22  2023  21:26:37  |  SCANID:  230422-2126.19372  |  RUNTIME:  96s   |  FILES:  2       |  HITS:  0   |  CLEANED:  0
4月  22  2023  21:09:33  |  SCANID:  230422-2109.17242  |  RUNTIME:  102s  |  FILES:  2       |  HITS:  0   |  CLEANED:  0
-snip-

maldet -eコマンドの引数にSCANIDを指定することで、特定のスキャンの詳細情報を表示することができます。

[root@server ~]# maldet -e 230422-2109.17242
HOST:      server
SCAN ID:   230422-2109.17242
STARTED:    4月 22 2023 21:09:33 +0900
COMPLETED:  4月 22 2023 21:11:15 +0900
ELAPSED:   102s [find: s]

PATH:
RANGE:         /root/scan_file_list days
TOTAL FILES:   2
TOTAL HITS:    0
TOTAL CLEANED: 0

===============================================
Linux Malware Detect v1.6.5 < proj@rfxn.com >

13 検疫したファイルを元の場所に戻す方法(-s)

"-s"は検疫したファイルを元のディレクトリに戻すためのオプションです。もしマルウェアに感染していないファイルを誤って検疫してしまった場合には、このオプションを使ってファイルを元の場所に戻すことができます。

テスト用のマルウェアを/tmpにダウンロードします。

[root@server ~]# wget -P /tmp https://secure.eicar.org/eicar.com

ダウンロードしたテスト用のマルウェアを確認します。

[root@server ~]# ls -l /tmp/eicar.com
-rw-r--r--. 1 root root 68  7月  2  2020 /tmp/eicar.com

/tmpディレクトリ以下のファイルをスキャンしたところ、1つのマルウェアが検出されたというメッセージ(malware hits 1)が表示されました。

[root@server ~]# maldet -a /tmp
Linux Malware Detect v1.6.5
            (C) 2002-2023, R-fx Networks <proj@rfxn.com>
            (C) 2023, Ryan MacDonald <ryan@rfxn.com>
This program may be freely redistributed under the terms of the GNU GPL v2

maldet(6017): {scan} signatures loaded: 17637 (14801 MD5 | 2053 HEX | 783 YARA | 0 USER)
maldet(6017): {scan} building file list for /tmp, this might take awhile...
maldet(6017): {scan} setting nice scheduler priorities for all operations: cpunice 19 , ionice 6
maldet(6017): {scan} file list completed in 0s, found 2 files...
maldet(6017): {scan} found clamav binary at /usr/bin/clamscan, using clamav scanner engine...
maldet(6017): {scan} scan of /tmp (2 files) in progress...
maldet(6017): {scan} processing scan results for hits: 1 hits 0 cleaned
maldet(6017): {scan} scan completed on /tmp: files 2, malware hits 1, cleaned hits 0, time 39s
maldet(6017): {scan} scan report saved, to view run: maldet --report 230423-1930.6017
[root@server ~]# maldet --report 230423-1930.6017

実行結果の詳細を確認すると、/tmpのテスト用マルウェアが検疫されたことがわかります。

[root@server ~]# maldet --report 230423-1930.6017
HOST:      server
SCAN ID:   230423-1930.6017
STARTED:    4月 23 2023 19:30:09 +0900
COMPLETED:  4月 23 2023 19:30:48 +0900
ELAPSED:   39s [find: 0s]

PATH:          /tmp
TOTAL FILES:   2
TOTAL HITS:    1
TOTAL CLEANED: 0

FILE HIT LIST:
{HEX}EICAR.TEST.3 : /tmp/eicar.com => /usr/local/maldetect/quarantine/eicar.com.2599910771
===============================================
Linux Malware Detect v1.6.5 < proj@rfxn.com >

/tmpにダウンロードしたテスト用のマルウェアを確認すると、検疫されたため/tmpには存在しないことがわかります。

[root@server ~]# ls -l /tmp/eicar.com
ls: '/tmp/eicar.com' にアクセスできません: そのようなファイルやディレクトリはありません

一方、検疫したファイルを格納するディレクトリを確認すると、テスト用のマルウェアが存在していることがわかりました。

[root@server ~]# ls -l /usr/local/maldetect/quarantine/eicar.com.2599910771
----------. 1 root root 68  4月 23 19:30 /usr/local/maldetect/quarantine/eicar.com.2599910771

検疫したファイルを元のディレクトリに戻します。

[root@server ~]# maldet -s 230423-1930.6017
Linux Malware Detect v1.6.5
            (C) 2002-2023, R-fx Networks <proj@rfxn.com>
            (C) 2023, Ryan MacDonald <ryan@rfxn.com>
This program may be freely redistributed under the terms of the GNU GPL v2

maldet(6743): {restore} quarantined file '/usr/local/maldetect/quarantine/eicar.com.2599910771' restored to '/tmp/eicar.com'

/tmpを確認すると、検疫したファイルが存在することがわかります。

[root@server ~]# ls -l /tmp/eicar.com
-rw-r--r--. 1 root root 68  7月  2  2020 /tmp/eicar.com

14 リアルタイムモニタリングを開始/終了する方法

リアルタイムモニタリングは、ファイルやディレクトリの作成、変更、削除をリアルタイムで監視する機能です。これにより、マルウェアが新しいファイルを作成するなどの不審な動きを検出することができます。

14.1 開始方法(--monitor)

”--monitor"はリアルタイムモニタリングを有効にするオプションです。この機能を実現するために、maldetはinotifywaitコマンドを使用します。例えば、/tmpディレクトリをリアルタイムでモニタリングするには、以下のようにコマンドを入力します。

[root@server ~]# maldet --monitor /tmp
Linux Malware Detect v1.6.5
            (C) 2002-2023, R-fx Networks <proj@rfxn.com>
            (C) 2023, Ryan MacDonald <ryan@rfxn.com>
This program may be freely redistributed under the terms of the GNU GPL v2

maldet(12999): {mon} added /tmp to inotify monitoring array
maldet(12999): {mon} starting inotify process on 1 paths, this might take awhile...
maldet(12999): {mon} inotify startup successful (pid: 13140)
maldet(12999): {mon} inotify monitoring log: /usr/local/maldetect/logs/inotify_log
[root@server ~]#

psコマンドを実行してプロセスの状態を確認します。リアルタイムモニタリングを有効にすると、inotifywaitプロセスが起動します。このプロセスが/tmp配下のファイルの作成、削除等を監視します。なお、inotifywaitコマンドについては、inotifywaitコマンドの使い方 - hana_shinのLinux技術ブログを参照してください。

[root@server ~]# ps -C inotifywait -o comm,pid,ppid,args
COMMAND             PID    PPID COMMAND
inotifywait       13140       1 /usr/bin/inotifywait -r --fromfile /usr/local/maldetect/sess/inotify.paths.12999 --exclud

inotifywaitプロセスが監視しているパスを確認すると、/tmpディレクトリであることがわかります。

[root@server ~]# cat /usr/local/maldetect/sess/inotify.paths.12999
/tmp

リアルタイムモニタリングのログを確認するため、tail -fコマンドを実行します。

[root@server ~]# tail -f /usr/local/maldetect/logs/inotify_log

/tmp配下にファイルを作成します。

[root@server ~]# touch /tmp/test.txt

ファイルを作成すると、inotify_logに以下のログが記録されることがわかります。

[root@server ~]# tail -f /usr/local/maldetect/logs/inotify_log
-snip-
/tmp/test.txt CREATE 21 Apr 22:46:08

14.2 終了方法(--kill-monitor)

"--kill-monitor"はリアルタイムモニタリングを終了するオプションです。リアルタイムモニタリングを終了するには、以下のようにコマンドを入力します。

[root@server ~]# maldet --kill-monitor
Linux Malware Detect v1.6.5
            (C) 2002-2023, R-fx Networks <proj@rfxn.com>
            (C) 2023, Ryan MacDonald <ryan@rfxn.com>
This program may be freely redistributed under the terms of the GNU GPL v2

maldet(14243): {mon} sent kill to monitor service (pid: 13140)

psコマンドを実行すると、inotifywaitプロセスが終了していることがわかります。

[root@server ~]# ps -C inotifywait -o comm,pid,ppid,args
COMMAND             PID    PPID COMMAND

Z 参考情報

私が業務や記事執筆で参考にした書籍を以下のページに記載します。
Linux技術のスキルアップをしよう! - hana_shinのLinux技術ブログ

How to use Linux Malware Detect (LMD) on Linux | LinTut