一、DNS资源记录(这一节来源于《计算机网络:自顶向下方法》)
资源记录是域名与IP映射信息在DNS服务器中存储的方式,即服务器如何组织、存放、管理这些信息。他是一个包含了下列字段的4元组:
(Name, Value, Type, TTL)
TTL是该记录的生存时间,它决定了资源记录什么时候应当从缓存中删除。Name和Value的值取决于Type:
(1)Type = A,则Name是主机名,Value是对应的IP。这是标准的主机名到IP的映射,显然最底层的权威服务器中充满这种类型的记录。
(2)Type = NS, 则Name是域,而Value是管理该域的DNS服务器的主机名,NS记录后面一般要跟着一条A记录以之处该DNS服务器的主机名的IP。高级别的权威服务器存储的一般是这种类型的记录。
(3)Type = CNAME,则Name是主机的别名,Value是对应的规范主机名。
(4)Type = MX,则Value是别名为Name的邮件服务器的规范主机名
通过使用MX记录,一个公司的邮件服务器和其他服务器可以使用相同别名。为了获得邮件服务器的规范主机名,DNS客户机应当请求一条MX记录;而为了获得其他访问其他的规范主机名,DNS客户机应当请求一条CNAME记录。
二、DNS协议
DNS协议是应用层协议,运行在UDP之上,使用53号端口。改天会写一篇文章分析一下什么是所谓的应用层协议,这里可以简单的把DNS协议理解为一种规定:规定了支撑DNS的应用层软件通信的方式以及对应的动作。通信的方式就是所谓的报文。DNS只有查询和回答报文,并且它们的格式是一样的。如下图:
一条DNS报文被分成几个字段,每个字段都有不同的功能,只说比较重要的几个:
(1)标志字段的“权威”标志位:如果一条回答正好是请求域名的权威服务器,那么该标志就会被设置成1(我也不确定,但不是1就是0)。
(2)标志字段的“递归”标志位:查询动作有两种类型,即迭代查询还递归查询。打个比方,甲向乙问路,乙虽然不知道,但是他会自己去问丙然后告诉甲,这就是递归;而如果乙不知道就对甲说你自己去问丙,然后甲从丙那里得到答案,这就是迭代。一般来讲,客户端向本地缓存服务器发起的查询都是递归的,而本地缓存服务器向权威服务器发起的查询是迭代的。
(2)问题区域:这里存放正在进行的查询,包括要查询的域名以及需要的记录类型。
三、DNS查询详细过程
在Linux系统上,可以直接使用nslookup命令解析一个域名的IP,如:nslookup www.baidu.com, 就会给出这个域名的IP。
我在终端使用dig命令来追踪一下解析过程,如下图:
图中,127.0.1.1是我的本地缓存服务器的IP,这个服务器会配置根域名服务器的IP,这几个IP基本是不会变化的;
有了根域名服务器的IP,向其中的一个(本例是g.root-servers.net.)发起查询,得到的回答是com顶级域DNS服务器的IP;
向其中一个com服务器发起查询(k.gtld-servers.net),得到baidu.com二级域名的DNS服务器IP;
向其中一个百度的服务器发起查询(ns4.baidu.com),得到的是一个规范名bk.n.shifen.com. 也就是说,baike.baidu.com只是一个别名;
于是只好再次使用dig,参数改成bk.n.shifen.com. 然后就能得到最终答案(自己动一下手吧)。
然后就是几个没有搞清楚的问题:
(1)根域名服务器里面存放的只是顶级域名的DNS服务器 的IP,但顶级域名实际上数量相对较少,所以其存储量应该不大。但是根域名服务器却做成一个系统。共有13个IP,每个IP下都有至少几十台服务器,全球大概有1000多台。为什么需要这么多?不完全出于备份的目的吧?
(2)入网的主机都会分配IP,DNS服务器本身也不例外。在第4步中,顶级域的DNS服务器一般存放的信息仍然是其子域名的DNS服务器的IP,而不会是某个非DNS服务器的IP,即只存放NS记录以及对应的DNS服务器的A记录,这在资源记录中有提到。但是我还不是很确定。
(3)不同com顶级域的DNS服务器存放的内容一致吗?如果不一致,那么到底该向哪台com服务器发送请求呢?如果一样的话,第四步中该向哪一个IP发送请求呢?选择离自己“最近”的?
(3)本地缓存服务器每次从权威服务器那里得到应答都会保存记录(似乎所有的DNS服务器都会这么做),比如刚才执行dig +trace baike.baidu.com的时候,会保存从根域名服务器到百度自己的DNS服务器的IP,那么再次执行dig +trace bk.n.shifen.com时,它会从根域名服务器开始查询呢还是直接问百度的DNS服务器?
后来查到一些资料说,根域名一般是可以绕过的,例子就是DDos攻击,这些攻击本来是指向根域名服务器的,但是本地缓存中已经有了顶级域IP的缓存,于是攻击直接绕过根域名服务器而向顶级域服务器发起。不过顶级域是否也能被绕过呢?本地缓存服务器如何控制以及实现查询的深度呢?语言识别?智能匹配?