~$100 Stratum 1 NTP server
For about a year now I have been running two identical Stratum 1 NTP servers. These servers, running on Raspberry Pi 2’s, use a GPS module to get a PPS (Pulse Per Second) signal that comes straight from the GPS satellites atom clock. I use these two NTP servers as a time source for my public Stratum 2 server which runs on my ESXi Cluster.
This system has always been very stable up until just a few days ago when one of the raspberry servers suddenly crashed and no longer booted to its OS. After inspecting all the hardware and logs I determined it was a case of bad luck as the microSD card simply gave up. Luckily because of the redundant nature of my setup the crash did not effect my public NTP, but of course I need to re-install the crashed NTP.
Now I could turn this into a very boring blog where I show you how I install the backup image but I decided this was a good opportunity to write a guide for anyone who was thinking about setting up their own “cheap” stratum 1 NTP server.
Also, before you continue, I do expect you to have some basic Linux know-how, but don’t worry as long as you know how to use apt-get and nano you’r basically good to go!
This entire project only required 4 screws to be turn and just a few lines of code to be entered but sadly the Raspberry Pi ins’t very quick at recompiling so count about an hour of work for this project.
The BOM and hardware assembly
Lets start of with the Bill of Matarials (BOM) listing all the parts you will need for this project. Obviously we are going to need a Raspberry Pi, when I build these servers the Raspberry Pi 2 was the latest version but all the software and hardware used in this guide is compatible with the Raspberry Pi 3.
Besides a Raspberry Pi you will also need a GPS HAT or Module, when I originally bought mine the GPS hat made by habsupplies was regarded as one of the most stable ones on the market, since then habsupplies has been renamed to Upurtronics but luckily they still carry a (updated) version of their GPS hat.
Of course the GPS module is nothing without a antenna, I originally bought one from habsupplies with a 0.5 meter cable, but any GPS antenna with SMA connector from you favorite Chinese website will do.
Last but not least you will need a microSD card and a power-supply for your Raspberry Pi, I have listed them as 0$ as I have yet to come across a DIY enthusiast that doesn’t have a microSD cards and microUSB phone chargers laying around.
Part Price (USD) Raspberry Pi 3 Model B+ Board $47.50 Raspberry Pi+ GPS Expansion Board $44.50 Active GPS Patch Antenna with SMA Connector $13 microSD card of at least 8GB 0$ MicroUSB power supply 0$
That totals out to round about $105 US excluding shipping and import taxes.
Once you have received all these components its as easy as screwing the hat onto the Pi using the provided standoffs that came with the GPS HAT. Then simply attach the GPS antenna and your good to go. Leave the microSD card out of it for now as we still need to install a OS on it.
At this point I should mention that Uptronics also has a nice case for the Pi + Hat if you want to be fancy. My other NTP server is in fact equipped with this case.
OS, boot settings and software install
Once you have loaded the image onto the microSD card please put it in the Raspberry Pi and boot it up. After its booted you log in with the default credentials: user=pi, password=raspberry
First we will edit the boot config.
$ sudo nano /boot/config.txt
Edit the config by adding the following to the bottom of the config file:
# Set PPS GPIO pins dtoverlay=pi3-miniuart-bt dtoverlay=pps-gpio,gpiopin=18
Save this edit with CTRL+X > Y > Enter.
Next up is installing and updating the required software packages, this may take a few minutes depending on your internet connection, you will also have to confirm some edits by pressing the Y key every now and again.
$ sudo apt-get update $ sudo apt-get dist-upgrade $ sudo apt-get install pps-tools $ sudo apt-get install libcap-dev $ sudo systemctl disable hciuart $ sudo systemctl mask serial-getty@ttyAMA0.service
At this point there is only one thing left to do before rebooting the Pi:
$ sudo raspi-config
A nice GUI should pop up now, go to advanced options (9), then to serial (A8) and then select yes when it asks you if you want shell over serial. At this point you may also use this menu to change your password, timezone, keyboard layouts and your hostname. I have renamed my Raspberry to srv-ntp-stratum1-1 to fit my internal naming scheme. After all this the GUI should ask you if you want to reboot, feel free to press yes, or simply run sudo reboot to restart your Pi now.
Setting up PPS and NTPD
Now that the Pi has rebooted we should be able to test the PPS signal from the GPS, make sure that the antenna is near a window or something and check the GPS hat for a blinking green light. if there is no blinking light then re-position the GPS antenna. When its blinking you can run the following commands and check if the output is similar to the ones listed here.
$ dmesg | grep pps [ 6.945199] pps_core: LinuxPPS API ver. 1 registered [ 6.945242] pps_core: Software ver. 5.3.6 - Copyright 2005-2007 Rodolfo Giometti <firstname.lastname@example.org> [ 6.955073] pps pps0: new PPS source pps.-1 [ 6.955219] pps pps0: Registered IRQ 184 as PPS source $ sudo ppstest /dev/pps0 trying PPS source "/dev/pps0" found PPS source "/dev/pps0" ok, found 1 source(s), now start fetching data... source 0 - assert 1479661157.000359166, sequence: 241 - clear 0.000000000, sequence: 0 source 0 - assert 1479661158.000359010, sequence: 242 - clear 0.000000000, sequence: 0 source 0 - assert 1479661159.000357447, sequence: 243 - clear 0.000000000, sequence: 0 source 0 - assert 1479661160.000359634, sequence: 244 - clear 0.000000000, sequence: 0 source 0 - assert 1479661161.000360623, sequence: 245 - clear 0.000000000, sequence: 0 source 0 - assert 1479661162.000362133, sequence: 246 - clear 0.000000000, sequence: 0 source 0 - assert 1479661163.000364268, sequence: 247 - clear 0.000000000, sequence: 0 source 0 - assert 1479661164.000365310, sequence: 248 - clear 0.000000000, sequence: 0
At this point a new line should print every second indicating that the PPS signal is working, use CTRL+C to exit the test.
At point all we need to do is recompile NTPD to work with the PPS signal using the following commands, be warned, some of these commands can take up to 30 minutes to complete.
$ wget http://www.eecis.udel.edu/~ntp/ntp_spool/ntp4/ntp-4.2/ntp-4.2.8p7.tar.gz $ tar zxvf ntp-4.2.8p7.tar.gz $ cd ntp-4.2.8p7 $ ~/ntp-4.2.8p7 $ ./configure -enable-linuxcaps # This last command may take a while.... feel free to grab a schnitzel or something while you wait. $ ~/ntp-4.2.8p7 $ make -j4 # Hope you didn't finish your schnitzel already on the first long command because honestly this one takes just as long... $ ~/ntp-4.2.8p7 $ sudo make install $ ~/ntp-4.2.8p7 $ sudo service ntp stop $ ~/ntp-4.2.8p7 $ sudo cp /usr/local/bin/ntp* /usr/bin/ && sudo cp /usr/local/sbin/ntp* /usr/sbin/
Next up we will need to edit some config files again
$ sudo nano /etc/ntp.conf
Add the folling lines to this config file:
# GPS PPS signal server 127.127.22.0 minpoll 4 maxpoll 4 fudge 127.127.22.0 flag3 1 refid PPS
Also amend one of the default servers from iburst to prefer, that part of the config should look something like this at this point:
# You do need to talk to an NTP server or two (or three). #server ntp.your-provider.example # pool.ntp.org maps to about 1000 low-stratum NTP servers. Your server will # pick a different set every time it starts up. Please consider joining the # pool: <http://www.pool.ntp.org/join.html> server 0.debian.pool.ntp.org prefer server 1.debian.pool.ntp.org iburst server 2.debian.pool.ntp.org iburst server 3.debian.pool.ntp.org iburst # GPS PPS signal server 127.127.22.0 minpoll 4 maxpoll 4 fudge 127.127.22.0 flag3 1 refid PPS
Again exit and save nano with CTRL+X > Y > Enter.
After this we only need to edit init.d/ntp
$ sudo nano /etc/init.d/ntp
Find the folowing segement:
RUNASUSER=ntp UGID=$(getent passwd $RUNASUSER | cut -f 3,4 -d:) || true if test "$(uname -s)" = "Linux"; then NTPD_OPTS="$NTPD_OPTS -u $UGID" fi
And amend it to this:
RUNASUSER=ntp UGID=$(getent passwd $RUNASUSER | cut -f 3,4 -d:) || true if test "$(uname -s)" = "Linux"; then NTPD_OPTS="$NTPD_OPTS" fi
Save the file and After that we can restart NTP for the last time.
$ sudo systemctl daemon-reload $ sudo service ntp restart
After that give it a few minutes to restart and run the test command to see if the NTP is up and running.
$ ntpq -crv -pn associd=0 status=0115 leap_none, sync_pps, 1 event, clock_sync, version="ntpd email@example.com Sun Nov 20 17:21:32 UTC 2016 (1)", processor="armv7l", system="Linux/4.4.21-v7+", leap=00, stratum=1, precision=-19, rootdelay=0.000, rootdisp=7939.485, refid=PPS, reftime=dbdc62ca.8421123b Sun, Nov 20 2016 18:58:34.516, clock=dbdc62cc.00c67053 Sun, Nov 20 2016 18:58:36.003, peer=18868, tc=4, mintc=3, offset=1.932974, frequency=7.264, sys_jitter=0.001907, clk_jitter=2.122, clk_wander=0.000 remote refid st t when poll reach delay offset jitter ============================================================================== o127.127.22.0 .PPS. 0 l 2 16 1 0.000 1.933 0.002 *18.104.22.168 .GPS. 1 u 11 64 77 7.332 2.397 0.485 +22.214.171.124 126.96.36.199 2 u 1 64 77 7.684 2.892 0.821 -188.8.131.52 184.108.40.206 2 u 4 64 77 12.986 0.243 3.667 +220.127.116.11 18.104.22.168 2 u 2 64 77 6.337 4.453 0.925
As you can see the PPS signal under the line is listed as a stratum 0 and in the summary above the line it lists the server as stratum=1. And that’s it, you are now running a stratum 1 NTP server.
At this point I would urge you to consider adding your server to the pool, please note that this is not for everyone, you will need to run your server 24/7 on a good connection and preferably redundant. It will also require you to edit the ntp config a bit so it will be more secure and so that it wont use pool servers to keep its own time. please read the following page carefully if you’r interested in helping the NTP project: http://www.pool.ntp.org/en/join.html
And on a final note I want to thank Anthony Stirk from upuaut.net for writing the original tutorial that I used over a year ago when I was setting my NTP server up for the first time, Stirk is also the owner of uputronics.com.
~$100 Stratum 1 NTP server