叶润生的博客» 利用BIND工具搭建根DNS镜像

镜花水月组员:叶润生??? 张志超??? 杨乐??? 郝恩楠?

?

?

做一个根域名服务器或{dj0}域名服务器的镜像。

Mirror a Root DNS server or TLD Server.?

?

?

DNS根服务器:??

  • ??????? 操作系统:windows 7 ;
  • ????????DNS平台:BIND 9.7.0-P1;
  • ??????? IP地址 :59.66.124.202 (此为宿舍笔记本分配得到的动态IP);

DNS本地服务器:??

  • ????????操作系统:windows 7;
  • ??????? DNS平台:BIND 9.7.0-P1;
  • ??????? IP 地址 : 192.168.1.69 (此为实验室的内网IP地址);

测试工具:??

  • ??????? BIND工具自带DIG解析器;
  • ??????? Windows自带的nslookup解析器;

抓包工具:??

  • ??????? Wireshark-win32-1.2.7;

?

?

根DNS服务器在整个DNS层次化结构中发挥着重要作用,当本地DNS服务器面临一个全新的查询请求时(所谓全新是指连{dj0}域名的信息都没有缓存),就会将该请求报文发给根DNS,从根DNS返回的报文中得知下一级要查询的DNS服务器地址。

归纳地来讲,我们认为根DNS的主要特点有如下两条:

1.管理{dj0}域名的信息。所谓的{dj0}域名是包括.com等通用{dj0}域名以及.cn等国家{dj0}域名在内的200多个域名。根DNS中保存着这么多域名所对应的NS及其地址。

2.不提供递归查询。如果根DNS提供递归查询的话,由于它在{zg}一层,因此面临的负担将是非常繁重的。

我们所要做的根DNS镜像服务器也要满足这两个特点,可以说这也是指导我们实验步骤的方向。

?

?

我们利用BIND在windows系统中搭建了一个本地DNS服务器以及根DNS镜像服务器。安装BIND的过程如下:

1.到上下载BIND开源工具,目前{zx1}版本是BIND 9.7.0-P1,由于我们的实验环境是在Windows底下,因此选择“Windows Download”下载Windows下的BIND工具。Linux平台下的BIND可以选择下载源码然后编译。

2.下载安装压缩包解压后,以管理员身份运行文件夹中的BINDInstall.exe,其中“Service Account Name”栏填当前操作系统的用户名,密码为当前系统的用户密码,并将“Options”中的“Start BIND Service After Install”勾掉,选择“Install”。安装完成后的界面如图1所示。

3.BIND安装完成后,会生成“DNS”文件夹,这个文件夹通常位于“C:\Windows\system32\”中。在“DNS”文件夹的属性页中,赋予第2步所填用户名以xx的控制权限。

4.进入安装目录下的bin目录,在命令行运行“rndc-confgen -a”,在etc目录下生成rndc.key;运行“rndc-confgen > ..\\etc\\rndc.conf”,在etc目录下生成rndc.conf文件。

5.在etc目录中,按照rndc.conf的提示,修改named.conf,完成初步的配置。

6.当所有的配置文件都配置完毕后,可以运行Bin下的named-checkconf检查配置文件的正确性。

7.启动“ISC BIND”服务,完成BIND的搭建。在这里需要说明的是,由于BIND在windows下的一些缺陷,需要在“ISC BIND”属性页的“登陆”选项卡中,手动填写系统账户的密码,否则服务启动不成功。这点也是比较诡异的地方。当然,也可以选择“本地系统账户”直接启动BIND服务。

图1. BIND安装界面

?

?

在开始介绍我们的配置之前,有必要先简单介绍BIND的配置文件格式含义,这也是我们前期花了很多时间调研所得的心得。

下面是一个Zone文件的示例,假设我们要说明的这个域名为abc.com(实际上这个域名时真实存在的):

?

第1行,给出了该域名(abc.com)各种记录的默认TTL值,这里为6小时。即如果该域名的记录没有特别定义TTL,则默认TTL为有效值。

第2行,这行内容标识出该ZONE文件是隶属哪个域名的,这里为dns1.cp.msft.net。

第3行,从这行开始到第8行为该域名的SOA记录部分,这里的@代表域名本身。orns01.dig.com表示该域名的主xxDNS。dns-ops.dig.com.表示该主xxDNS管理员邮箱,等价于。

第4行,Serial部分,这部分用来标记ZONE文件更新,如果发生更新则Serial要单增,否则MASTER不会通知SLAVE进行更新。

第5行,Refresh部分,这个标记SLAVE服务器多长时间主动(忽略MASTER的更新通知)向MASTER复核Serial是否有变,如有变则更新之。

第6行,Retry部分,如Refresh不能完成,重试的时间间隔。

第7行,Expire部分,如SLAVE无法与MASTER取得联系,SLAVE继续提供DNS服务的时间。Expire时间到期后SLAVE仍然无法联系MASTER则停止工作,拒绝继续提供服务。Expire的实际意义在于它决定了MASTER服务器的最长下线时间(如MASTER迁移,DOWN机等)。

第8行,Minimum部分,这个部分定义了DNS对否定回答(NXDOMAIN即访问的记录在xxDNS上不存在)的缓存时间。

第9-11行,定义了该域名的3个xxDNS服务器。通常NS记录的TTL大些为宜,这里为2天。设置过小只会增加服务器无谓的负担,同时解析稳定性会受影响。

第12-14行,给出了本机、NS以及邮箱服务器的A地址(也就是IPv4地址)。BIND的大部分zone文件都按照这样的格式来配置,当然也有一些其他的配置语句,在这里由于篇幅所限,就不详加论述了,感兴趣的同学可以参考Paul Albitz & Cricket Liu所著的《DNS and BIND》这本书[1]。接下来我们的BIND配置文件也是按照这个格式来编写。

?

?

由于我们要搭建的是一个根DNS的镜像,因此,我们也需要搭建一个DNS本地服务器,将它的根服务器指向我们所搭建起来的DNS服务端地址,这里为“59.66.124.202”。

在本地服务器配置中,最主要的文件是named.root以及named.conf文件的配置。下面依次进行介绍:

?

说明:这个文件的作用是告诉本地DNS服务器根DNS服务器的名字为“A.ROOT-SERVERS.NET.”(这个名字并不重要,名字以根的NS名字为准,在实验测试中就能看出来),其IPv4地址为“59.66.124.202”;

?

说明:

named.conf文件的作用如同上文中注释所示,主要是在953端口监听DNS查询请求,为本机提供递归查询服务,指明根DNS所在的位置。这样,当启动本地DNS服务之后,服务器收到一个DNS查询请求,在本机缓存中没有找到记录后,则会以此向本次实验搭建起的DNS根服务器、国际上的{dj0}服务器、……等一级一级DNS服务器发出迭代查询,{zh1}再将得到的结果返回给用户,完成递归查询的过程。

所有文件配置完毕,重启“ISC BIND”服务,将本地连接的默认DNS服务器指向“127.0.0.1”地址,我们自己搭建的本地DNS服务器已经准备为本机提供DNS查询服务了,并且,根指向了我们配置的“59.66.124.202”这台主机。

在开始测试之前,建议将windows自带的DNS服务器禁掉,方法是停止“DNS Client”服务即可。

在调试过程中,本地DNS服务器远比远程根镜像DNS服务器来得稳定。在远程根镜像服务器因为配置文件改写重启服务后,为了避免每次都重启本地的服务,我们采用的方法是清空BIND的DNS缓存。具体操作是,在bin目录下,运行“rndc flush”命令即可。这样,每次本机DNS服务器都会到我们配置的远程根镜像服务器进行查询。

?

?

这个也是实验目的中一开始就提出的问题。根DNS服务器负责{dj0}域的管理,也就是说,我们自己搭建的根DNS服务器必须有{dj0}域名服务器的NS以及其对应的地址。在本次实验中,我们通过BIND安装后在bin目录中的dig解析工具来获得{dj0}域名的信息(实际上通过windows自带nslookup也可以,但是为了数据导入方便,我们还是决定使用dig来完成这个任务)。

举一个例子,比如我们的根服务器需要提供com.域的NS信息以及其对应的IP地址,先进入bin所在的目录,然后在命令行中运行“dig ns com.”,这样在命令提示符中就能打印出我们所需要的信息,如下图所示:

图2. dig工具查询com.域名信息

图中可知,在返回报文的ANSWER段中,负责{dj0}域名“com”的总共有13个NS,在ADDITIONAL段中,给出了这些NS的IPv4或者IPv6地址(AAAA代表IPv6地址)。利用这两个字段的信息,我们就能在自己搭建的根DNS镜像服务器中完成com域的管理。

包括国家(地区)在内(如cn域名),目前全球总共有200多个{dj0}域名[1],为了让我们的镜像服务器能够更切实地镜像根DNS服务器的数据,我们需要对这200多个域名通过dig的方法一一找到其NS以及IP地址,这显然是一件非常枯燥的体力活。庆幸的是,dig工具解析出来的内容已经xx符合BIND配置文件的编写格式了,因此,我们决定通过windows脚本语言实现这些{dj0}域名信息的自动获取。

关于这个脚本语言的内容,具体可以参考本文的附录部分。

?

这个文件与6.2节介绍的“named.conf”文件的大体结构是相同的。一个很显然的不同点是,我们的根DNS镜像服务器不会也不能支持递归查询,因此需要在options中禁掉递归查询的选项。如下所示:

还有一个{zd0}的不同点是,作为一个根DNS的镜像,我们需要告诉BIND说:“我是根DNS,那些像com的{dj0}域名都受我管理”,因此,我们需要将根“.”配置成受我们管理的域,这也就是我们根DNS镜像服务器中named.conf域普通服务器{zd0}的不同点,如下所示:

说明:这个文件中,将“.”域类型置为“master”,说明要定义的是一个主域名服务器,而不定义为“hint”(也就是根服务器的索引,显然我们要自己定义一个新的)。根服务器所管理的域名信息都位于“root.zone”中,也就是说,root.zone文件将是根DNS镜像服务器的核心所在。

?

鉴于全球{dj0}域名太多,root.zone文件内容过于庞大,这里只摘抄了文件首部以及具有代表性的cn{dj0}域名的信息配置。如下文所示:

说明:我们将自定义的根DNS的NS称呼为yezi(当然,这点也是为了实验测试时证明该DNS镜像的确能够正确服务,方便观察实验结果),并将本地服务器里根的地址指向为镜像所在的地址(非目前国际上的13个根DNS)。

接下来,文件中配置了根DNS所管辖的{dj0}域名列表及其NS地址。比如,对于cn这个{dj0}域名来说,它共有6个NS,其中a.dns.cn这个NS的地址为203.119.25.1,以此类推可以配置其他{dj0}域名的NS信息,这里要注意的是,这个文件中并不会涉及更进一层次的域名信息。这样,当这个根DNS收到一个DNS查询请求,比如某主机查询“yahoo.cn”的地址,由于根中没有缓存这条记录信息(也不可能缓存这类信息),也不支持递归查询,我们的根镜像服务器将会返回管理cn域名的6个NS地址,以便对方去进行迭代查询过程。

所有的文件配置完毕,重启“ISC BIND”服务,我们的根镜像DNS服务器已经准备开始服务了。

?

?

这一部分内容是验证我们搭建的根DNS服务器能否正确工作。

利用windows自带的nslookup工具,将DNS服务端设为本地BIND的服务器,地址为127.0.0.1;

建议禁掉windows自带的“DNS Client”服务,避免系统自己缓存信息,以更好测试根DNS镜像服务器是否能正常工作。

?

输入“yahoo.com”,本地服务器返回了若干个IP地址。

图3. nslookup 查找 yahoo.com 返回的信息

注意到此时本地服务器指向的根DNS已经改为我们自己的根“59.66.124.202”了,那么是否意味着我们的实验系统已经成功完成了呢?

可以进一步验证一下。

在nslookup中,输入“set type=ns”,指定查询根DNS的NS,当然我们期望返回的结果是“yezi”,以证实的确在根DNS地址上我们没有xx。如下图所示:

图4. nslookup查找根返回的信息

谢天谢地,结果就是我们所想的。

?

当然,包括我们在内的很多人也愿意深入了解真实的DNS迭代查询的过程是怎样的(其实更想看看我们的根DNS镜像是否真的完成了根DNS的功能,毕竟配置文件看起来怎么那么简单),我们决定采用抓包工具捕获本机与各个DNS之间的迭代查询过程,顺便细致地回顾下DNS迭代查询的流程。

我们采用的是Wireshark网络封包软件,版本是1.2.7,关于该软件的下载、使用及介绍可以在http://www.wireshark.org/网站中找到。

下面是我们的测试步骤:

1. 启动Wireshark,利用快捷键“Ctrl+I”,调出要抓包的网卡列表,选择合适的网卡,点击“Start”开始抓包;

2. 将默认DNS服务器指定为127.0.0.1指向本机的BIND服务器,在命令行中进入nslookup,输入“yahoo.com”,回车;

3. 当nslookup返回“yahoo.com”的信息后,观察到Wireshark中捕获了一些信息,停止抓包过程;

4. 为了方便我们观察实验结果,在Wireshark的“Filter”栏中输入过滤条件,这里输入“dns && (ip.src_host==192.168.1.69 || ip.dst_host==192.168.1.69)”,代表我们希望看到本机的DNS数据包。

Wireshark显示的信息如下图所示,下面我们一一进行说明。

图5. Wireshark抓包结果

从图中可以看出,整个查询过程总共有8个DNS数据包来往,序号从68到93。

1. 序号68和69的数据包: 本机DNS服务器向根DNS镜像服务器发出查询“yahoo.com”的地址以及根DNS的NS的请求;

2. 序号71和73的数据包:根DNS镜像服务器返回了com域名的NS地址,以及根的NS是yezi和yezi的地址。其中,通过查看数据包内容,我们发现,根DNS镜像返回的com域名的NS地址为“192.5.6.30”;

3. 序号72和88的数据包:本机DNS服务器向192.5.6.30的DNS服务器查询yahoo.com的地址,远程DNS服务器返回yahoo.com的NS地址为68.180.131.16;

4. 序号90和93的数据包:本机DNS向yahoo.com的NS查询yahoo.com的地址,该NS返回了最终结果,说明yahoo.com对应的地址。如下图所示。

图6. 序号93数据包的内容

序号93数据包中“Answer”字段的内容,也就是我们通过nslookup查找到的yahoo.com的地址。

至此为止,我们的根DNS镜像服务器的搭建及测试任务已经圆满完成。

?

?

[1] Paul Albitz & Cricket Liu. DNS and BIND, Fourth Edition. O’Reilly & Associates, Inc. 2001

?

?

首先我们手头上必须有份{dj0}域名的列表文件,假设它叫做“topdomainlist.txt”,节选如下:

假设我们的dig工具安装在“c:windows\system32\dns\bin\dig.exe”目录下,将以下代码拷贝至“dnsconf.bat”文件中:

运行该文件,输出的“conf.txt”文件中就保存了符合BIND配置文件格式的{dj0}域名信息,那么加上根的SOA头部之后,是否可直接用于7.3节中root.zone文件的编写呢?

在实践过程中,我们小组发现,直接用脚本文件生成的这些信息用于配置文件将会出现远程根DNS镜像服务器不能服务的情况(用nslookup得出的提示信息是server fail)。我们刚开始怀疑是文件格式不对的问题、文件大小太大问题、域名顺序不对的问题,在排除了这三类问题后,我们决定采用二分排除查错法来检验文件的问题。方法就是每次只保留一半大小的配置文件依次进行测试,直到某一次服务成功后,添加一部分信息后服务又失败时,就能定位到问题所在。这样一步步把错误范围缩小,{zh1}我们发现了一个很奇妙的配置信息。

我们发现,当用dig工具查找某些域名的ns时,返回的是根dns所在SOA地址。比如我们查cq域名时返回的信息如下图所示:

图7. dig查找cq域名返回的结果

在上图中,返回消息的授权段中存放的是根DNS的SOA信息。这一点将是非常重要的!也就是说,如果我们将这个条目写入配置文件,那么在我们的根DNS镜像服务器中,将会发现“.”域有多个SOA的声明,这显然是不正确的配置,服务当然也不会成功启动。

查找生成的配置文件,我们发现除了cq域名,还有eh,ev,nt,yu,zr这5个域名会返回根的SOA信息。这样,我们在topdomainlist.txt中删除了这6个域名信息,将重新生成的配置文件添加到root.zone文件中,重启服务,至此我们的根DNS镜像服务器终于成功完成配置。

?

附:本地DNS配置文件,根镜像DNS配置文件,{dj0}域名列表文件,自动获取{dj0}域名配置信息脚本文件(,下载后改为rar后缀即可解压)
郑重声明:资讯 【叶润生的博客» 利用BIND工具搭建根DNS镜像】由 发布,版权归原作者及其所在单位,其原创性以及文中陈述文字和内容未经(企业库qiyeku.com)证实,请读者仅作参考,并请自行核实相关内容。若本文有侵犯到您的版权, 请你提供相关证明及申请并与我们联系(qiyeku # qq.com)或【在线投诉】,我们审核后将会尽快处理。
—— 相关资讯 ——