Bind Primary/Secondary (running on different ports)
If you’ve recently read my guide on running BIND, pihole and DoH in particular the section about BIND you may have noticed we are running on a non-standard port. The setup is surprisingly easy 😊
A follow up question that was asked is how this works when running separate BIND servers (like I do) in a primary/secondary configuration. Most users of BIND are probably running a Primary/Secondary deployment. In large internet-facing environments there may be many secondary servers that external users query, with a primary hidden and secured in a separate network. If you’re unsure how zone transfers/updates are made in a Primary/Secondary configuration, here is the quick summary:
- A user modifies the zone on the primary server (adding a new record, updating a record etc)
- They also increment the serial (we will get to that) on the primary server
- They perform a reload / refresh of the zone configuration on the primary server
- The primary server “notifies” (push) all of its secondarys that an update is available
- The secondary servers read the serial record from the primary to see if there is in fact an update
- If there is an update, the secondarys perform a zone transfer from the primary to themselves (pull)
- The secondarys servers load the new/updated records
There are a few different things that happen in the background, but that is the very basic working of how zone transfers operate in a simple primary/secondary configuration. There are other configurations like multi primary, but we won’t get into that now.
Coming back to the original question of how to configure BIND on a non-standard port, let’s make a few assumptions. My setup is as follows:
- Two servers running Ubuntu 16.04 with BIND installed
- The primary server is running on 192.168.211.11
- The secondary server is running on 10.152.0.3
The Primary server
In my setup, I have the primary running on the IP 192.168.211.11 so be sure to substitute my IP with whatever your one will be. As per one of my previous articles on Setting up BIND we configured it to respond on port 5354. We are going to roll with that since we are half way there. The other options you need to configure relate to notify and transfer.
You will need to include the following lines in /etc/bind/named.conf.options:
also-notify
allow-transfer
This is how the last few lines of my named.conf.options look:
listen-on port 5354 { 192.168.211.11; };
listen-on-v6 { none; };
also-notify { 10.152.0.3 port 5354;};
allow-transfer { 10.152.0.3; };
So what we are doing here is telling BIND that it should notify our secondary server (10.152.0.3) on port 5354 whenever there are updates. We are also telling BIND that we should allow zone transfers to the server 10.152.0.3. Make sure you include this last part otherwise the secondary won’t be authorised to transfer zones!
The Secondary Server
On the secondary server, make sure you have BIND listening on port 5354 (as per the above, that’s the “listen-on-port” section. My setup has a few other bits I wont include here like internal routing interfaces, but to summarise my named.conf.options on the secondary server looks like this:
listen-on port 5354 { 10.152.0.3; };
listen-on-v6 { none; };
transfer-source 10.152.0.3;
use-alt-transfer-source yes;
Then you need to configure your secondary zones. Your secondary server will only pick up DNS zones from the primary after they have been configured on the secondary. This means you need to tell BIND that it should host the relevant zone files. There is a new feature in BIND called Catalog zones which makes this process easier in large deployments, but I haven’t had time to test it out so I wont get into that just yet. So on your secondary server, you need to adjust /etc/bind/named.conf.local so that it looks like this:
//
// Do any local configuration here
//
// Consider adding the 1918 zones here, if they are not used in your
// organization
//include "/etc/bind/zones.rfc1918";
zone "mycoolzone" {
type secondary;
primarys { 192.168.211.11 port 5354; };
primaryfile-format text;
file "mycoolzone.db";
};
Simple, isn’t it? Here you are telling BIND that the zone is a secondary, that its primary is 192.168.211.11 running on port 5354. The “primaryfile-format text” is a personal preference. This tells bind to store the files in a text format (that can easily be read) instead of binary. While this slightly hinders performance, in most environments its probably worth doing if you want to compare zone files on primary/secondarys.
So with the above two changes made to the primary/secondary, you just need to give bind a reload;
systemctl reload bind9
Do that on the secondary first, then the primary. If you monitor /var/log/syslog by using the command
tail -f /var/log/syslog
on the secondary, you should also see something like this show up:
Dec 18 00:10:47 dns2 named[17106]: client 192.168.211.11#47194: received notify for zone 'mycoolzone'
Dec 18 00:10:47 dns2 named[17106]: zone mycoolzone/IN: notify from 192.168.211.11#47194: serial 2018121803
Dec 18 00:10:47 dns2 named[17106]: zone mycoolzone/IN: Transfer started.
Dec 18 00:10:47 dns2 named[17106]: transfer of 'mycoolzone/IN' from 192.168.211.11#5353: connected using 10.152.0.3#52097
Dec 18 00:10:47 dns2 named[17106]: zone mycoolzone/IN: transferred serial 2018121803
Dec 18 00:10:47 dns2 named[17106]: transfer of 'mycoolzone/IN' from 192.168.211.11#5353: Transfer status: success
Dec 18 00:10:47 dns2 named[17106]: transfer of 'mycoolzone/IN' from 192.168.211.11#5353: Transfer completed: 1 messages, 27 records, 684 bytes, 0.019 secs (36000 bytes/sec)
Dec 18 00:10:47 dns2 named[17106]: zone mycoolzone/IN: sending notifies (serial 2018121803)
Keeping tail running, modify the contents of your zone file on the primary server, add a new record or maybe change one of the records to a different IP.
Make sure you also increase the serial!
At present the serial for my zone is 2018121803. While it isn’t required, a good way to keep track of changes in zone files is to date them. 2018121803 represents:
Year: 2018
Month: 12 (December)
Day: 18th
Increment: 03
So if I am making a change to the zone on the same day, i simply increase the increment by 1. This means the serial would become 2018121804 If i am making a change to the zone in a few days’ time, it would become something like 2018122101.
As long as the serial is higher than the previous value, it will be pushed out to secondarys. Once you have made the change to your zone, you can simply type the following on your primary server
rndc reload
This will load the zone configuration into bind, sending any updates out to secondarys. Again, if you’ve got tail running on your secondary, you should see the new updates replicating correctly:
Dec 18 00:20:01 dns2 named[17106]: client 192.168.211.11#46856: received notify for zone 'mycoolzone'
Dec 18 00:20:01 dns2 named[17106]: zone mycoolzone/IN: notify from 192.168.211.11#46856: serial 2018121804
Dec 18 00:20:01 dns2 named[17106]: zone mycoolzone/IN: Transfer started.
Dec 18 00:20:01 dns2 named[17106]: transfer of 'mycoolzone/IN' from 192.168.211.11#5353: connected using 10.152.0.3#53809
Dec 18 00:20:01 dns2 named[17106]: zone mycoolzone/IN: transferred serial 2018121804
Dec 18 00:20:01 dns2 named[17106]: transfer of 'mycoolzone/IN' from 192.168.211.11#5353: Transfer status: success
Dec 18 00:20:01 dns2 named[17106]: transfer of 'mycoolzone/IN' from 192.168.211.11#5353: Transfer completed: 1 messages, 27 records, 684 bytes, 0.025 secs (27360 bytes/sec)
Dec 18 00:20:01 dns2 named[17106]: zone mycoolzone/IN: sending notifies (serial 2018121804)
And there you have it. If you have any issues getting this setup, feel free to hit me up. While I do read my emails I tend to be a bit more responsive on Twitter these days. Enjoy.