BIND9.18.xをインストールする(ソースからビルド) for RockyLinux 9.x

DNSサーバーの代表格BIND。最近は脆弱性問題がしばしば出ることから常に最新版での運用が推奨される製品。この記事では、BINDをソースからコンパイルしてインストールする方法を記載しています。
（ソースからのビルドのため、常に最新版での運用が可能となります）
2024年5月現在のBINDは、「9-18-26」が最新版です。
RockyLinuxでの手順を書いていますが、RHEL互換OSであればどれも同じ方法で作業が可能です。

## ダウンロード先
https://www.isc.org/downloads/

## 検証環境バージョン
| ソフトウェア | バージョン |
|:-:|:-:|
|  BIND| 9-18-26 |
|  OS | RockyLinux 9.3 |


## 事前インストール
OpenSSLが事前に必要です。以下を参考に事前にインストールをしておきます。
[RockyLinux 9.xにOpenSSL 3.0.xをインストールする（ソースからビルド）](https://qiita.com/shadowhat/items/e8adf371a198d7555422)
Python 3.x系をインストールします
(https://qiita.com/shadowhat/items/025c49df5e45d6c1b665)

## PowerToolsの有効化
以下のライブライをdnfでインストールするためには、PowerToolsのインストール必要
（参考）[https://qiita.com/koizumistr/items/f8e2eece3a4b5fb2fa03](Rocky Linux 9でPowerToolsリポジトリを使いたい)

```
sudo dnf config-manager --set-enabled crb
```

###libpcap-develとlibuvをインストールする

```
dnf install libpcap-devel libuv-devel
```

※RockyLinux9では、autoconfとaclocalのバージョンが異なっており。libuvは、ビルドが出来ない

```bash:
#cd /usr/local/src
#wget https://dist.libuv.org/dist/v1.44.2/libuv-v1.44.2.tar.gz
#tar xvzf libuv-v1.44.2.tar.gz
#cd libuv-v1.44.2
#./autogen.sh
#./configure
#make -j 8
#make install
```

### nghttp2をインストール
※RockyLinuxのPythonが3.6のためそちらにパスがあるとconfigureでこける
（configure: error: Python interpreter is too old　と言われる）
その場合、一時的に、「mv /usr/bin/python3 /usr/bin/python3.def」と変更してconfigureを実行する

もしくは「dnf install python3-devel」でインストールする

```
cd /usr/local/src
wget https://github.com/nghttp2/nghttp2/releases/download/v1.61.0/nghttp2-1.61.0.tar.gz
tar xvzf nghttp2-1.61.0.tar.gz
cd nghttp2-1.61.0/
./configure
make -j 8
make install
```

### Python3のインストール


#インストールはこちらを参照する
[https://qiita.com/shadowhat/items/025c49df5e45d6c1b665](Python3.xをインストール（ソースからビルド）for RockyLinux 8.4)

```
/usr/local/python-3.11.3/bin/pip3 install ply
/usr/local/python-3.11.3/bin/python3.11 -m pip install --upgrade pip
```


```bash:
cd /usr/local/src
wget https://github.com/nghttp2/nghttp2/releases/download/v1.56.0/nghttp2-1.56.0.tar.gz
tar xvzf nghttp2-1.56.0.tar.gz
cd nghttp2-1.56.0
export LD_LIBRARY_PATH=/usr/local/python-3.11.3/lib:/usr/local/ssl/lib:/usr/local/lib
export LD_RUN_PATH=/usr/local/lib64:/usr/local/lib:/usr/local/ssl/lib:/usr/lib:/usr/lib64
export PKG_CONFIG_PATH=/usr/local/python-3.11.3/lib/pkgconfig:/usr/local/ssl/lib/pkgconfig:/usr/local/lib/pkgconfig

./configure PYTHON=/usr/local/python-3.11.3/bin/python3 --with-openssl=/usr/local/ssl
make
make install
```

## インストール

```bash:
cd /usr/local/src
wget https://downloads.isc.org/isc/bind9/9.18.26/bind-9.18.26.tar.xz
tar xvJf bind-9.18.26.tar.xz
cd bind-9.18.26/
#export LD_LIBRARY_PATH=/usr/local/lib:/usr/local/python-3.11.3/lib:/usr/local/ssl/lib
export PKG_CONFIG_PATH=/usr/local/lib/pkgconfig:/usr/local/python-3.11.3/lib/pkgconfig:/usr/local/ssl/lib/pkgconfig
export LD_RUN_PATH=/usr/local/lib:/usr/local/python-3.11.3/lib:/usr/local/ssl/lib
#export OPENSSL_CFLAGS=/usr/local/ssl
#export OPENSSL_LIBS=/usr/local/ssl/lib
#LDFLAGS=-ldl
./configure --disable-linux-caps --with-python=/usr/local/python-3.11.3/bin/python3

#RHEL8の場合
./configure --disable-linux-caps --with-python=/usr/local/python-3.11.3/bin/python3 --disable-linux-caps
make
# makeは-j Xで複数スレッド走らせずシングルスレッドでビルドしないとInternal Errorでこける。
# makeでinternal errorが出るときは、一度OS再起動で再実行する
make install
```

## 初期設定
### 事前準備
bind起動用のユーザーを作成します。

```bash:
useradd named
mkdir -p /var/named
chown named:named -R /var/named/
mkdir -p /run/named
chown named:named -R /run/named
#PIDファイル置き場所指定
mkdir -p /usr/local/var/run/named
chown named:named /usr/local/var/run/named
```

### キーの生成を行う

```bash:
#/etc/rndc.keyのファイルを作成
#/usr/local/sbin/rndc-confgen -a
/usr/local/sbin/rndc-confgen -a -b 512 -k rndckey

#rndc.confを作成
ln -s /usr/local/lib/libuv.so.1 /usr/lib64/libuv.so.1
/usr/local/sbin/rndc-confgen > /etc/rndc.conf

cat /usr/local/etc/rndc.key | grep secret
#key項目の中身を控える
mv /usr/local/etc/rndc.key /usr/local/etc/rndc.key.def

vi /etc/rndc.conf
- key "rndc-key"以下を先ほど控えたもの置き換え -
touch /etc/named.conf
ln -s /etc/named.conf /usr/local/etc/named.conf
```



## ヒントファイルを取得する

```bash:
mkdir -p /var/named
cd /var/named
wget https://www.internic.net/domain/named.root
```

##named.confを配置する

```bash:
cat > /etc/named.conf << EOF
options {
    directory "/var/named";
    recursion yes;
    allow-recursion{ 192.168.0.0/16; localhost; };
    version "unknow";
#    listen-on { WW.XX.YY.ZZ; 127.0.0.1;}; #公開するインターフェースのIP
    listen-on { any;}; #すべてのインターフェースの場合
#    dnssec-enable yes; 
};

key "rndc-key" {
      algorithm hmac-sha256;
      //rdnc.keyのキーをここに入れる
      secret "XXXXXXXXXXXXXXXXXXXXXX==";
};

controls {
      inet 127.0.0.1 port 953
              allow { 127.0.0.1; } keys { "rndc-key"; };
};

zone "." IN {
    type hint;
    file "named.root";
};

zone "localhost" IN {
    type master;
    file "named.localhost";
};

zone "0.0.127.in-addr.arpa" IN {
    type master;
    file "named.loopback";
};


EOF
```

## Zoneファイルを用意する

```bash
### localhost正引き
cat >  /var/named/named.localhost << EOF
\$TTL 1D
@	IN SOA	@ rname.invalid. (
					0	; serial
					1D	; refresh
					1H	; retry
					1W	; expire
					3H )	; minimum
	NS	@
	A	127.0.0.1
	AAAA	::1

EOF
```

```bash:
### localhost逆引き
cat > /var/named/named.loopback << EOF
\$TTL 1D
@	IN SOA	@ rname.invalid. (
					0	; serial
					1D	; refresh
					1H	; retry
					1W	; expire
					3H )	; minimum
	NS	@
	A	127.0.0.1
	AAAA	::1
	PTR	localhost.

EOF
```

##起動スクリプトを配置

```bash:
cat > /usr/lib/systemd/system/named.service << EOF
[Unit]
Description=Berkeley Internet Name Domain (DNS)
After=network-online.target

[Service]
Type=forking
PIDFile=/usr/local/var/run/named/named.pid

ExecStartPre=/bin/bash -c 'if [ ! "\$DISABLE_ZONE_CHECKING" == "yes" ]; then /usr/local/bin/named-checkconf -z /etc/named.conf; else echo "Checking of zone files is disabled"; fi'
ExecStart=/usr/local/sbin/named -u named \$OPTIONS

ExecReload=/bin/sh -c '/usr/local/sbin/rndc reload > /dev/null 2>&1 || /bin/kill -HUP \$MAINPID'

ExecStop=/bin/sh -c '/usr/local/sbin/rndc stop > /dev/null 2>&1 || /bin/kill -TERM \$MAINPID'

PrivateTmp=true

[Install]
WantedBy=multi-user.target

EOF
```

## サービスを起動し、自動起動を設定

```bash:
mkdir -p /usr/local/var/run/named/
ln -s /etc/named.conf /usr/local/etc/named.conf
ln -s /etc/rndc.conf /usr/local/etc/rndc.conf
chown -R named:named /usr/local/var/run/named
chown -R named:named /var/named
systemctl start named
systemctl enable named
```

## 正しく動作しないとき
- SELinuxは、Offで試してみる
- /var/namedの権限は、660 /varにも権限付与を確認（namedユーザーにsuして、ファイルが見れるかを確認する）
- /run/namedが、namedユーザーが所持しているか？