内部向け+社内参照 DNS キャッシュサーバ構築

前回に続いて、今回は、Dnsmasq を使って、以下の機能を持つ軽量 DNS キャッシュサーバを構築します。

  • ローカルネットワーク環境用の内部向け my-local-domain.com の名前解決は、Dnsmasq を使う
  • ローカルドメイン以外の社内ドメイン my-company.comグローバル側 の問い合わせについては、Dnsmasq のリゾルバを使って社内ネットワーク上にある DNS サーバ (BIND) に名前を解決してもらう
  • 一回目の名前解決結果をキャッシュし、二回目以降の名前解決はキャッシュから返す

System Configuration Diagram システム構成図

dnsmasq 内部向けとリゾルバ

Dnsmasq 内部向け + リゾルバの組み合わせ (ローカルドメイン以外の社内ドメイン・グローバル側の問い合わせについては社内 DNS に名前を解決してもらう)

サーバ構成

サーバ構成については、前回と同じで以下の 2台になりますが、上記構成図の黄色い部分は構築対象外です。

  • dns-server
  • dns-client
サーバ名 IP アドレス FQDN
dns-server 192.168.20.200 dns-server.my-local-domain.com
dns-client 192.168.20.100 dns-client.my-local-domain.com

以下は、各サーバのリゾルバ設定情報です。

サーバ名 リゾルバ IP 設定ファイル 用途
dns-server 127.0.0.0 /etc/resolv.conf ローカルドメイン名前解決用 / キャッシュ用
200.200.20.200 /etc/resolv_dnsmasq.conf 社内ドメイン / グローバル名前解決用
dns-client 192.168.20.200 /etc/resolv.conf ローカルドメイン名前解決用

以下は、各サーバのゲートウェイ・ルーティング情報です。

基本的にデフォルトゲートウェイは設定しておらず、dns-server 側に eth1 に社内ネットワーク上にある DNS サーバと疎通するためのスタティックルートだけ切ってあります。

サーバ名 デフォルト GW スタティックルート
dns-server なし 200.200.20.0/24 → gw 100.100.20.1 (eth1)
dns-client なし なし

DNS-SERVER 側

基本的な構築の流れは、前回とさほど変わりませんが、dns-server/etc/hosts に登録された名前以外の問い合わせについては、別 DNS を参照して名前を解決してもらうために、今回は、dns-server 側に dnsmasq 独自のリゾルバ設定ができるように /etc/dnsmasq.conf を作成する必要があります。

Step 1. dnsmasq インストール

yum で dnsmasq をインストールし、サービス登録を実施します。

dnsmasq : yum インストールRaw Code(S)Raw Code(T)
# yum -y install dnsmasq

# chkconfig dnsmasq on

Step 2. dnsmasq コンフィグ確認

dnsmasq をインストールするとデフォルトコンフィグファイルが配置されるので、コンフィグの中身を軽く確認しておきます。

ちなみに、デフォルトコンフィグの中身は、全てコメントアウトされています。

/etc/dnsmasq.conf 確認Raw Code(S)Raw Code(T)
# cat /etc/dnsmasq.conf
---------------------- ここから ----------------------
# Configuration file for dnsmasq.
#
# Format is one option per line, legal options are the same
# as the long options legal on the command line. See
# "/usr/sbin/dnsmasq --help" or "man 8 dnsmasq" for details.

・・・

# Never forward plain names (without a dot or domain part)
#domain-needed
# Never forward addresses in the non-routed address spaces.
#bogus-priva

・・・
---------------------- ここまで ----------------------
/etc/dnsmasq.conf 確認 (コメント・空行除外)Raw Code(S)Raw Code(T)
# cat /etc/dnsmasq.conf | grep -v "^#" | grep -v "^$"
(コメント・空行を除外して grep すると何も出力されない)

Step 3. dnsmasq コンフィグ設定

ここでは、dnsmasq を内部向け+社内参照 DNS (リゾルバキャッシュ) サーバとして動かすための最低限の設定を実施します。

line: 6 は、my-local-domain.com 以外の問い合わせに使うリゾルバ設定ファイル名を指定してください。

resolv_dnsmasq.conf は、後で新規作成する必要があります。 また、コメントにも書いてあるように /etc/resolv.conf 以外のファイル名を指定する必要があります。

line: 14 は、問い合わせする際に /etc/resolv.conf に書いてるネームサーバの順番通りに問い合わせを行うようにする設定です。

line: 19・24 にそれぞれローカルドメイン名と IP アドレスをフォーマットに合わせて設定してください。

line: 27・28 は、Dnsmasq のクエリログを出力する設定です。 ログを出力したい場合には、コメントを外してください。

以下の例では、内部用のドメイン名として my-local-domain.com を、内部ドメイン以外の問い合わせ用のリゾルバとして /etc/resolv_dnsmasq.conf ファイルを使うように指定しています。

/etc/dnsmasq.confRaw Code(S)Raw Code(T)
・・・

# Change this line if you want dns to get its upstream servers from
# somewhere other that /etc/resolv.conf
#resolv-file=
resolv-file=/etc/resolv_dnsmasq.conf
・・・
# By  default,  dnsmasq  will  send queries to any of the upstream
# servers it knows about and tries to favour servers to are  known
# to  be  up.  Uncommenting this forces dnsmasq to try each query
# with  each  server  strictly  in  the  order  they   appear   in
# /etc/resolv.conf
#strict-order
strict-order
・・・
# Add other name servers here, with domain specs if they are for
# non-public domains.
#server=/localnet/192.168.0.1
server=/my-local-domain.com/192.168.20.200
・・・
# Example of routing PTR queries to nameservers: this will send all
# address->name queries for 192.168.3/24 to nameserver 10.1.2.3
#server=/3.168.192.in-addr.arpa/10.1.2.3
server=/20.168.192.in-addr.arpa/192.168.20.200
・・・
#### ログを出力したい時には、以下のコメントアウトを解除
#log-queries
#log-facility=/var/log/dnsmasq.log
/etc/dnsmasq.conf 確認 (コメント・空行除外)Raw Code(S)Raw Code(T)
# cat /etc/dnsmasq.conf | grep -v "^#" | grep -v "^$"
resolv-file=/etc/resolv_dnsmasq.conf
strict-order
server=/my-local-domain.com/192.168.20.200
server=/20.168.192.in-addr.arpa/192.168.20.200

Step 4. リゾルバ設定

まずは、dns-server 側の通常のリゾルバ設定ファイル /etc/resolv.conf にローカル側のドメイン名 my-local-domain.com とネームサーバの IP アドレスとして 127.0.0.1 を設定します。

/etc/resolv.confRaw Code(S)Raw Code(T)
domain    my-local-domain.com
nameserver    127.0.0.1

それから /etc/dnsmasq.conf に設定したリゾルバ設定ファイル /etc/resolv_dnsmasq.conf (ローカルドメイン以外の名前解決用) を以下の内容で新規作成します。

/etc/resolv_dnsmasq.confRaw Code(S)Raw Code(T)
search    my-company.com
nameserver    200.200.20.200

Step 5. 静的ルーティング設定

もちろん、ローカルドメイン以外の名前を解決してもらうために、dns-server 自身が社内網につながっている必要があるので、社内 DNS サーバ 200.200.20.200 と疎通するための NIC (eth1) に静的ルーティングを設定します。

以下の設定は、200.200.20.0/24 へ行きたいときには、dns-server 側の eth1 を通って、100.100.20.0/24 のデフォルトゲートウェイである 100.100.20.1 へ行ってねーという意味です。

ちなみに、dns-clientdns-server のデフォルトゲートウェイは特に何も設定していません

設定が終わった後は、ネットワークサービスを再起動してください。

/etc/sysconfig/static-routesRaw Code(S)Raw Code(T)
any net 200.200.20.0 netmask 255.255.255.0 gw 100.100.20.1 dev eth1
ネットワーク再起動Raw Code(S)Raw Code(T)
# service network restart

Step 6. /etc/hosts に名前登録

待ちに待った名前登録設定です。

/etc/hosts に登録したいローカルドメイン用のサーバの IP アドレス・FQDN・サーバ名を全て登録します。

以下の例では、10台のサーバ server01 ~ server10 を登録します。

dns-server 自身のIP アドレス・FQDN・サーバ名を必ず登録してください。

127.0.0.1   localhost localhost.localdomain localhost4 localhost4.localdomain4
192.168.20.1    server01.my-local-domain.com server01
192.168.20.2    server02.my-local-domain.com server02
192.168.20.3    server03.my-local-domain.com server03
192.168.20.4    server04.my-local-domain.com server04
192.168.20.5    server05.my-local-domain.com server05
192.168.20.6    server06.my-local-domain.com server06
192.168.20.5    server07.my-local-domain.com server07
192.168.20.8    server08.my-local-domain.com server08
192.168.20.9    server09.my-local-domain.com server09
192.168.20.10    server10.my-local-domain.com server10
192.168.20.100    dns-client.my-local-domain.com dns-client
192.168.20.200    dns-server.my-local-domain.com dns-server

Step 7. 重要 : dns-server 自身のドメイン名設定確認

dnsmasq サービスを開始する前に以下を必ずチェックしてください。

サーバ自身のマシン名が設定されていなかったり、/etc/hostsdns-server の FQDN が登録されていなかったり、各ドメイン名情報とホスト名が一致しない場合、サービス起動に失敗します。

  • dns-server 自身の IP アドレス確認
  • /etc/hosts に dns-server の IP と FQDN が登録されていること
  • /etc/sysconfig/network に dns-server の FQDN が設定されていること
  • hostname コマンドを実行したときに、dns-server の FQDN が表示されること
最終チェックRaw Code(S)Raw Code(T)
# ip addr | grep inet | fgrep -v "127.0.0.1"
inet 192.168.20.200/24 brd 192.168.20.255 scope global eth0

# cat /etc/hosts | fgrep "192.168.20.200"
192.168.20.200    dns-server.my-local-domain.com dns-server

# cat /etc/sysconfig/network | grep "HOSTNAME"
HOSTNAME=dns-server.my-local-domain.com

# hostname
dns-server.my-local-domain.com

Step 8. dnsmasq サービス起動

最後に、以下のコマンドを実行し、dnsmasq サービスを開始します。

サービスが問題なく立ち上がったら 53番ポートが LISTEN 状態であることを確認してください。

dnsmasq サービス起動Raw Code(S)Raw Code(T)
# service dnsmasq start
Starting dnsmasq:                [  OK  ]
53番ポート LISTEN 状態確認Raw Code(S)Raw Code(T)
# netstat -anp | fgrep ':53'
tcp     0      0  0.0.0.0:53      0.0.0.0:*     LISTEN      5647/dnsmasq
tcp     0      0  :::53           :::*          LISTEN      5647/dnsmasq
udp     0      0  0.0.0.0:53      0.0.0.0:*                 5647/dnsmasq
udp     0      0  :::53           :::*                      5647/dnsmasq

LISTEN 状態について

上記の結果 0.0.0.0 は、検証のため全て受け付けるようになっています。

また、UDP ポートには、LISTEN というステータスが付きませんので、上記のような結果が出ていれば大丈夫です。

DNS-CLIENT 側

後は、dns-client 側でリゾルバのネームサーバとして dns-server の IP アドレスを設定した上で、名前が引けることを確認します。

  • ローカルドメインの名前を引く (my-local-domain.com)
  • 社内ドメインの名前を引く (my-company.com)
  • グローバルの名前を引く (yahoo.co.jp)

Step 1. リゾルバ設定

リゾルバの検索ドメインに dns-server のドメイン名を。 ネームサーバとして dns-server の IP アドレスを設定します。

/etc/resolv.confRaw Code(S)Raw Code(T)
search    my-local-domain.com
nameserver    192.168.20.200

ちなみに、/etc/hosts は、特に何も設定していません。

(デフォルトゲートウェイも設定していません)

127.0.0.1   localhost localhost.localdomain localhost4 localhost4.localdomain4

Step 2. ローカルドメインの名前を引く

まずは、簡単に dig コマンドでローカルドメイン my-local-domain.com の名前が引けるか確認します。

ローカルドメインの名前解決Raw Code(S)Raw Code(T)
# dig +short server02.my-local-domain.com
192.168.20.2

# dig +short -x 192.168.20.2
server01.my-local-domain.com.

Step 3. 社内ドメインの名前を引く

dig コマンドで社内ドメイン my-company.com の名前が引けるか確認します。

2回目以降の問い合わせについてはキャッシュから返すので、クエリタイムが 1回目より速くなっていることが分かります。

dns-client : 社内ドメイン 名前解決 1回目
# dig hogehoge.my-company.com

; <<>> DiG 9.8.2rc1-RedHat-9.8.2-0.37.rc1.el6_7.6 <<>> hogehoge.my-company.com
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 56551
;; flags: qr aa rd ra; QUERY: 1, ANSWER: 1, AUTHORITY: 1, ADDITIONAL: 1

;; QUESTION SECTION:
;hogehoge.my-company.com. IN   A

;; ANSWER SECTION:
hogehoge.my-company.com.  86400 IN A    200.200.20.2

;; AUTHORITY SECTION:
my-company.com.           86400   IN      NS      ns.named.my-company.com.

;; ADDITIONAL SECTION:
ns.named.my-company.com.  86400   IN      A       200.200.20.200

;; Query time: 2 msec
;; SERVER: 192.168.20.200#53(192.168.20.200)
;; WHEN: Fri Feb 26 08:44:19 2016
;; MSG SIZE  rcvd: 185
dns-client : 社内ドメイン 名前解決 2回目
# dig hogehoge.my-company.com

; <<>> DiG 9.8.2rc1-RedHat-9.8.2-0.37.rc1.el6_7.6 <<>> hogehoge.my-company.com
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 64024
;; flags: qr rd ra; QUERY: 1, ANSWER: 1, AUTHORITY: 0, ADDITIONAL: 0

;; QUESTION SECTION:
;hogehoge.my-company.com. IN   A

;; ANSWER SECTION:
hogehoge.my-company.com. 86395 IN A    200.200.20.2

;; Query time: 1 msec
;; SERVER: 192.168.20.200#53(192.168.20.200)
;; WHEN: Fri Feb 26 08:44:24 2016
;; MSG SIZE  rcvd: 66





 

以下は、上記の問い合わせ時に出力された dns-server 側のログです。

1回目の問い合わせのときにはフォワーディング、2回目の問い合わせについてはキャッシュから返していることが分かります。

dns-server : /var/log/dnsmasq.log (1回目)
Feb 26 08:44:19 dnsmasq[19091]: query[A] hogehoge.my-company.com from 192.168.20.100
Feb 26 08:44:19 dnsmasq[19091]: forwarded hogehoge.my-company.com to 200.200.20.200
Feb 26 08:44:19 dnsmasq[19091]: reply hogehoge.my-company.com is 200.200.20.2
dns-server : /var/log/dnsmasq.log (2回目)
Feb 26 08:44:24 dnsmasq[19091]: query[A] hogehoge.my-company.com from 192.168.20.100
Feb 26 08:44:24 dnsmasq[19091]: cached hogehoge.my-company.com is 200.200.20.2
 

Step 4. グローバルの名前を引く

最後に、dig コマンドで dns-server → 社内の DNS サーバ 経由で yahoo.co.jp の名前が引けるか確認します。

2回目以降の問い合わせについてはキャッシュから返すので、クエリタイムが 1回目より速くなっていることが分かります。

dns-client : グローバル 名前解決 1回目
# dig yahoo.co.jp

; <<>> DiG 9.8.2rc1-RedHat-9.8.2-0.37.rc1.el6_7.6 <<>> yahoo.co.jp
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 52048
;; flags: qr rd ra; QUERY: 1, ANSWER: 2, AUTHORITY: 4, ADDITIONAL: 4

;; QUESTION SECTION:
;yahoo.co.jp.                   IN      A

;; ANSWER SECTION:
yahoo.co.jp.            300     IN      A       182.22.59.229
yahoo.co.jp.            300     IN      A       183.79.135.206

;; AUTHORITY SECTION:
yahoo.co.jp.            1256    IN      NS      ns01.yahoo.co.jp.
yahoo.co.jp.            1256    IN      NS      ns12.yahoo.co.jp.
yahoo.co.jp.            1256    IN      NS      ns02.yahoo.co.jp.
yahoo.co.jp.            1256    IN      NS      ns11.yahoo.co.jp.

;; ADDITIONAL SECTION:
ns01.yahoo.co.jp.       16924   IN      A       118.151.254.133
ns02.yahoo.co.jp.       31132   IN      A       118.151.254.149
ns11.yahoo.co.jp.       29686   IN      A       124.83.255.37
ns12.yahoo.co.jp.       1256    IN      A       124.83.255.101

;; Query time: 9 msec
;; SERVER: 192.168.20.200#53(192.168.20.200)
;; WHEN: Fri Feb 26 08:46:36 2016
;; MSG SIZE  rcvd: 201
dns-client : グローバル 名前解決 2回目
# dig yahoo.co.jp

; <<>> DiG 9.8.2rc1-RedHat-9.8.2-0.37.rc1.el6_7.6 <<>> yahoo.co.jp
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 40854
;; flags: qr rd ra; QUERY: 1, ANSWER: 2, AUTHORITY: 0, ADDITIONAL: 0

;; QUESTION SECTION:
;yahoo.co.jp.                   IN      A

;; ANSWER SECTION:
yahoo.co.jp.            294     IN      A       183.79.135.206
yahoo.co.jp.            294     IN      A       182.22.59.229

;; Query time: 1 msec
;; SERVER: 192.168.20.200#53(192.168.20.200)
;; WHEN: Fri Feb 26 08:46:42 2016
;; MSG SIZE  rcvd: 61











 

以下は、上記の問い合わせ時に出力された dns-server 側のログです。

1回目の問い合わせのときにはフォワーディング、2回目の問い合わせについてはキャッシュから返していることが分かります。

dns-server : /var/log/dnsmasq.log (1回目)
Feb 26 08:46:36 dnsmasq[19091]: query[A] yahoo.co.jp from 192.168.20.100
Feb 26 08:46:36 dnsmasq[19091]: forwarded yahoo.co.jp to 200.200.20.200
Feb 26 08:46:36 dnsmasq[19091]: reply yahoo.co.jp is 182.22.59.229
Feb 26 08:46:36 dnsmasq[19091]: reply yahoo.co.jp is 183.79.135.206
dns-server : /var/log/dnsmasq.log (2回目)
Feb 26 08:46:42 dnsmasq[19091]: query[A] yahoo.co.jp from 192.168.20.100
Feb 26 08:46:42 dnsmasq[19091]: cached yahoo.co.jp is 183.79.135.206
Feb 26 08:46:42 dnsmasq[19091]: cached yahoo.co.jp is 182.22.59.229
 

終わりに

これで軽量内部向け+社内参照用のリゾルバキャッシュ DNS サーバが出来上がりました。

内容的には少し長くなった気がしますが、設定のポイントだけ簡単に整理すると以下のようになります。

  • dns-server : ローカルドメインの名前解決 : /etc/resolv.conf
  • dns-server : ローカルドメイン以外の名前解決 : /etc/resolv_dnsmasq.conf
  • dns-server : 上記 2つが機能するように設定 : /etc/dnsmasq.conf
  • dns-server : 社内 DNS と疎通するための静的ルート設定
  • dns-client : /etc/resolv.conf リゾルバに dns-server を設定して問い合わせ

閉じられたネットワーク環境内でのローカルドメインの名前解決に加えて、社内ドメイン (もしくは、社内ドメインとグローバル側) の名前解決が必要な場合には Dnsmasq が役に立つと思います。

特に、2回目以降の問い合わせについてはキャッシュから返すので、社内 DNS サーバの負荷軽減に貢献できるのも一つのメリットです。

/etc/hosts を修正したらサービス再起動

dns-server 側の /etc/hosts ファイルを編集した後、設定を反映するためには、dnsmasq サービスの再起動が必要です。

# service dnsmasq restart

以上、Dnsmasq 軽量 DNS サーバ構築(内部向け+リゾルバキャッシュ) でした。