Configuring a DNS server in Linux

Introduction

Ever wanted to refer to your machines in your lab environment by a name instead of an IP address? I mean, you could use the hosts file and replicate that across every computer in your network. Or, you can be really cool, waste a lot of time, and come up with your own name server that centrally does that for you. How do you do that? Welp, grab your Linux install, and your 2 large cups of coffee because we’re going to creates us a DNS server.

Network Requirements

Since I am using virt-manager in Linux, a lot of things will be different compared to Virtualbox and VMware. The short of it is to create your own isolated NAT network using the hypervisor of your choosing. Here is what mine looks like:

I have disabled DHCP in this network. Also, it is safe to assume that the hypervisor takes up at least the first 4 addresses of the subnet. So I only have from .5-.254 to use. So that is what I did to my debian machine. (Keep in mind that you can use any distro as long you can install bind9. And if you don’t have a system with systemd in it, you know what you’re doing 😉 )

Bind9: First Contact

First you’re gonna want to install bind9. This is the software we need to turn our machine into a DNS server. Here is an example of how to basically install it on almost every distro I know:

# Debian/Ubuntu based systems (like mint, pop os, and hannah montana linux)
sudo apt update && sudo apt install bind9

# Red Hat/Fedora based systems (Like CentOS and Rocky)
# Depending on the distro, you'll need to enable some repos or might need to change the package name to "bind". And the service name might be different too
sudo yum install bind9
# or
sudo dnf install bind9

# Arch based systems (Like Artix and Manjaro)
sudo pacman -Sy bind9

# Gentoo based systems
you're on your own son. emerge to victory!

Now that that’s out of the way, lets configure the config file (/etc/bind/named.conf.options) I add these options to the default file:

        forwarders {
                8.8.8.8;
        };
        recursion yes;
        allow-query { any; };
        dnssec-enable yes;
        dnssec-validation yes;

What these options do is forward all unknown request to google, and also allows anybody to query our dns server recursively. Here is what mine looks like

Now enable and restart the service like so:

sudo systemctl enable bind9
sudo systemctl reload bind9

That should get the daemon up and going. But we should also set our main DNS to point to our-self. (and in the future, other VMs should point to this VM) I will make some changes in /etc/networking/interfaces and /etc/resolv.conf.

/etc/networking/interfaces

iface enp1s0 inet static
        address 10.0.0.254/24
        gateway 10.0.0.1
        dns-nameservers 127.0.0.1
        dns-search xavierlc.lab

/etc/resolv.conf

search xavierlc.lab
nameserver 127.0.0.1

Bind9: Forward Lookup Zones

Now I’m getting into the meat and potatoes of this thing. A “universal hosts file” for all your VMs in that NAT network. Let’s start by editing /etc/bind/named.conf.local

The things I highlighted is the domain I want to use for my internal lab environment. I used “xavierlc.lab” for this example

zone "xavierlc.lab" IN {
        type master;
        file "/etc/bind/xavierlc.lab.db";
        allow-query { any; };
};

Now we have to make a database file. Let’s make a file in /etc/bind called “xavierlc.lab.db”. Edit the contents like so:

@       IN SOA ns.xavierlc.lab. xavier.xavierlc.lab. (
                        2022050801      ; serial
                        1D              ; refresh
                        1H              ; retry
                        1W              ; expire
                        3H )            ; minimum

@       NS      ns.xavierlc.lab.
ns      IN      A       10.0.0.254
commodore       IN      A       10.0.0.254

This is what mine looks like:

For the serial, the format is yyyymmddss. The rest of the config is nessecary, but the exact values for a home lab don’t really matter. What they mean is refresh after, retry after, expire after, and i’m not too sure what the bottom one means if I’m being honest. The NS option specifies our default dns server, the first A record entry points to the dns server so that it can resolve “ns.xavierlc.lab”. And the second A record is just what the dns server is named so that other computers in the lab network can refer to this server as “commodore”.

Testing it all

After restarting and enabling the bind9 service. We can use ping to see if it worked.