featured image retrieved from http://www.techrepublic.com/blog/it-security/dns-resource-record-integrity-is-still-a-big-big-problem/
I had the chance to buckle down and get some DNS servers running in the lab. The process, although not painless, was not terribly difficult, and the upshot is that my lab is far more scalable than it was previously. I used a good guide that I found at Unixmen.
First, a primer on DNS. We all use DNS and we know that it provides name resolution against IP addresses, resulting in a far easier way to access our favorite servers than remembering a set of numbers. What do the core components of DNS do? I am going to assume you know what an IP address, host name, FQDN, etc. mean, so here’s a quick vocabulary list for us to get started:
- Name server: this is a system running DNS server software and is intended to provide name resolution. DNS server software may include Microsoft’s built-in DNS server or something like BIND. Speaking of BIND…
- BIND: Stands for Berkeley Internet Name Domain. This is the software package that I used for my DNS servers.
- Zone files: Text documents that associate names to IP addresses (and vice versa). Zone files contain records (another term) which determine what sort of servers those IP addresses are resolving to. We’ll talk about specific types of records shortly.
Now that we know what we’re talking about, how do we go about setting up BIND? First, start with installing a minimal CentOS 7 image.
You’re going to want to do this twice, assuming that you want a primary and secondary DNS server. Read the Unixmen guide above for the differences in slave setup; if you’re able to set up a master DNS server you will have no problem setting up a slave. A primary server will be sufficient for some, but I plan on abusing these systems a bit down the line.
With CentOS installed and running, assign the systems static IP addresses and make sure that they can access the internet. The tool you want to use in a minimal install of CentOS 7 is nmtui.
OS installed, networking set up and blinking… let’s install bind!
sudo yum install bind bind-utils -y
After that’s done, we need to edit /etc/named.conf.
[aschenck@dns1 ~]$ sudo cat /etc/named.conf // // named.conf // // Provided by Red Hat bind package to configure the ISC BIND named(8) DNS // server as a caching only nameserver (as a localhost DNS resolver only). // // See /usr/share/doc/bind*/sample/ for example named configuration files. // options { listen-on port 53 { 127.0.0.1; 192.168.1.2;}; # listen-on-v6 port 53 { ::1; }; directory "/var/named"; dump-file "/var/named/data/cache_dump.db"; statistics-file "/var/named/data/named_stats.txt"; memstatistics-file "/var/named/data/named_mem_stats.txt"; allow-query { localhost; 192.168.1.0/24;}; allow-transfer { localhost; 192.168.1.3;}; /* - If you are building an AUTHORITATIVE DNS server, do NOT enable recursion. - If you are building a RECURSIVE (caching) DNS server, you need to enable recursion. - If your recursive DNS server has a public IP address, you MUST enable access control to limit queries to your legitimate users. Failing to do so will cause your server to become part of large scale DNS amplification attacks. Implementing BCP38 within your network would greatly reduce such attack surface */ recursion yes; dnssec-enable yes; dnssec-validation yes; /* Path to ISC DLV key */ bindkeys-file "/etc/named.iscdlv.key"; managed-keys-directory "/var/named/dynamic"; pid-file "/run/named/named.pid"; session-keyfile "/run/named/session.key"; }; logging { channel default_debug { file "data/named.run"; severity dynamic; }; }; zone "." IN { type hint; file "named.ca"; }; zone "vlab.local" IN { type master; file "forward.vlab"; allow-update { none; }; }; zone "1.168.192.in-addr.arpa" IN { type master; file "reverse.vlab"; allow-update { none; }; }; include "/etc/named.rfc1912.zones"; include "/etc/named.root.key";
Everything in bold needs to be edited, or in the case of the allow-transfer line, added. What we are telling named.conf to do is listen for DNS traffic on our IP and port, allow for anyone on our subnet to query for DNS information, and transfer zone files to any specified slaves. Finally, we need to add references to our forward and reverse zone files. Obviously, change things like “vlab.local” to whatever your own personal private domain happens to be.
With /etc/named.conf ready, we now need to create our zone files, located at /var/named/.
Start with the forward zone file.
[aschenck@dns1 ~]$ sudo cat /var/named/forward.vlab [sudo] password for aschenck: $TTL 86400 @ IN SOA dns1.vlab.local. root.vlab.local. ( 00001 ;Serial 3600 ;Refresh 1800 ;Retry 604800 ;Expire 86400 ;Minimum TTL ) @ IN NS dns1.vlab.local. @ IN NS dns2.vlab.local. @ IN A 192.168.1.2 @ IN A 192.168.1.3 @ IN A 192.168.1.175 dns1 IN A 192.168.1.2 dns2 IN A 192.168.1.3 aveproxy IN A 192.168.1.175 [aschenck@dns1 ~]$
Now, what the heck does all of this mean? Let’s go through it line by line:
- $TTL 86400 – This specifies the time to live. This is the amount of time in seconds after which a DNS client must discard an old record and grab an updated version.
- IN SOA – “Internet Start of Authority”
- dns1.vlab.local. – Primary master domain server.
- root.vlab.local. – Email address of administrator for this zone. The . after root automatically becomes a @.
- Serial – This is an arbitrary number that must be incremented every time you update the zone file so that it propagates correctly.
- Refresh – Amount of time slaves will wait before polling the master for changes.
- Retry – Amount of time a slave will wait before polling the master in case it is unreachable.
- Expire – Amount of time a slave will wait before no longer returning DNS results as authoritative in case of master failure.
- Minimum TTL – Amount of time that the name server will cache an error if it cannot find the requested name.
Finally, let’s talk about the record types found in the forward zone file:
- NS records: These are name servers. Notice that we have NS records for both dns1.vlab.local as well as dns2.vlab.local.
- A records: These map a host to an IPv4 addresses. Notice I have records for three hosts, including the already-mentioned dns1 and dns2 hosts.
Our reverse zone file looks similar, but serves a different purpose. Forward lookups resolve hostnames to IP addresses; reverse lookups associate IP addresses to hostnames!
[aschenck@dns1 ~]$ sudo cat /var/named/reverse.vlab [sudo] password for aschenck: $TTL 86400 @ IN SOA dns1.vlab.local. root.vlab.local. ( 2011071001 ;Serial 3600 ;Refresh 1800 ;Retry 604800 ;Expire 86400 ;Minimum TTL ) @ IN NS dns1.vlab.local. @ IN NS dns2.vlab.local. @ IN PTR vlab.local. dns1 IN A 192.168.1.2 dns2 IN A 192.168.1.3 aveproxy IN A 192.168.1.175 2 IN PTR dns1.vlab.local. 3 IN PTR dns2.vlab.local. 175 IN PTR aveproxy.vlab.local. [aschenck@dns1 ~]$
As you can see, the beginning of these files are the same, but now we introduce PTR (pointer) records. PTR records do the bulk of work when it comes to reverse DNS lookups.
With our zone files created, we can now enable and start the DNS service on CentOS, as well as poking the appropriate hole through the firewall.
systemctl enable named systemctl start named firewall-cmd --permanent --add-port=53/tcp firewall-cmd --permanent --add-port=53/udp firewall-cmd --reload
Just a few more things to do… change the group of /var/named to named, change the owner and group of /etc/named.conf, and tell SELinux about the new defaults for /var/named as well as /etc/named.conf.
chgrp named -R /var/named chown -v root:named /etc/named.conf restorecon -rv /var/named restorecon /etc/named.conf
The last thing you need to do, assuming all is well, is go back into nmtui and change your DNS IP to your DNS server’s static ip address!
Now, the moment of truth… let’s test our DNS server using dig.
[aschenck@dns1 ~]$ dig google.com ; <<>> DiG 9.9.4-RedHat-9.9.4-29.el7_2.1 <<>> google.com ;; global options: +cmd ;; Got answer: ;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 58864 ;; flags: qr rd ra; QUERY: 1, ANSWER: 1, AUTHORITY: 4, ADDITIONAL: 5 ;; OPT PSEUDOSECTION: ; EDNS: version: 0, flags:; udp: 4096 ;; QUESTION SECTION: ;google.com. IN A ;; ANSWER SECTION: google.com. 300 IN A 216.58.219.206 ;; AUTHORITY SECTION: google.com. 148671 IN NS ns1.google.com. google.com. 148671 IN NS ns3.google.com. google.com. 148671 IN NS ns2.google.com. google.com. 148671 IN NS ns4.google.com. ;; ADDITIONAL SECTION: ns2.google.com. 148671 IN A 216.239.34.10 ns1.google.com. 148671 IN A 216.239.32.10 ns3.google.com. 148671 IN A 216.239.36.10 ns4.google.com. 148671 IN A 216.239.38.10 ;; Query time: 260 msec ;; SERVER: 192.168.1.2#53(192.168.1.2) ;; WHEN: Mon Dec 21 18:37:13 EST 2015 ;; MSG SIZE rcvd: 191 [aschenck@dns1 ~]$
If you get similar output to what you see above, and your “SERVER” output is your DNS server’s IP address, you’re all set and you can start using your DNS server to resolve names on your lab’s network.
Now that DNS is up and running, I have been able to install the Avamar image proxy on my machine without any problems 🙂 We’ll go over Avamar in a future post.
Things learned today: take the time to set up basic services like DNS as opposed to relying on your consumer router to do it for you. It’s a lot less frustrating to get it set up correctly and then have a dedicated VM to serve your lab than it is to fight with a router that’s marketed towards people who would have zero clue what a pointer record or zone file is!
-ajs