ntpd: use UCI to synthesize minimal conf file
Borrowed code from Busybox's sysntpd. Signed-off-by: Philip Prindeville <philipp@redfish-solutions.com>
This commit is contained in:
parent
fb54ca1ef5
commit
f5ca3ea50f
2 changed files with 149 additions and 1 deletions
86
net/ntpd/README.md
Normal file
86
net/ntpd/README.md
Normal file
|
@ -0,0 +1,86 @@
|
|||
# Configuring NTPD with UCI
|
||||
|
||||
## Precedent
|
||||
Sysntpd is the lightweight implementation of the NTP protocol under
|
||||
Busybox. It supports many (but not all) of the same parameters.
|
||||
|
||||
It is configured as a `config timeserver ntp` section in `/etc/config/system`,
|
||||
below.
|
||||
|
||||
## Configuration
|
||||
|
||||
A sample configuration looks like:
|
||||
|
||||
**/etc/config/system**:
|
||||
|
||||
```
|
||||
config timeserver ntp
|
||||
option enabled 1
|
||||
option enable_server 1
|
||||
list server tick.udel.edu
|
||||
list server tock.udel.edu
|
||||
list interface eth0
|
||||
list interface eth1
|
||||
list interface eth2
|
||||
```
|
||||
|
||||
If you want to temporarily disable the service without deleting all of the
|
||||
configuration state, this is done by clearing the `enabled` parameter. If
|
||||
this parameter is `1` (the default), the service is enabled.
|
||||
|
||||
The service can run as a stand-alone client (`enable_server 0`, the default)
|
||||
or it can also operate as a server in turn to local clients, by setting this
|
||||
parameter to `1`.
|
||||
|
||||
The parameter(s) `server` enumerate a list of servers to be used for
|
||||
reference NTP servers by the local daemon. At least one is required,
|
||||
and two or more are recommended (unless you have an extremely available
|
||||
local server). They should be picked to be geographically divergent,
|
||||
and preferrably reachable via different network carriers to protect
|
||||
against network partitions, etc. They should also be high-quality
|
||||
time providers (i.e. having stable, accurate clock sources).
|
||||
|
||||
The `interface` parameter enumerates the list of interfaces on which
|
||||
the server is reachable (see `enable_server 1` above), and may be a
|
||||
subset of all of the interfaces present on the system. For security
|
||||
reasons, you may elect to only offer the service on internal networks.
|
||||
If omitted, it defaults to _all_ interfaces.
|
||||
|
||||
## Differences with `sysntpd`
|
||||
|
||||
Busybox `sysntpd` supports configuring servers based on DHCP
|
||||
provisioning (option 6, per the [DHCP and BOOTP
|
||||
Parameter](https://www.iana.org/assignments/bootp-dhcp-parameters/bootp-dhcp-parameters.xhtml)
|
||||
list from IANA). This functionality is enabled (in Busybox) with the
|
||||
`use_dhcp` boolean parameter (default `1`), and the `dhcp_interface`
|
||||
list parameter, which enumerates the interfaces whose provisioning
|
||||
is to be utilized.
|
||||
|
||||
### Considerations for DHCP-provisioned NTP servers
|
||||
|
||||
Most terrestrial and satellite ISPs have access to very high-quality
|
||||
clock sources (these are required to maintain synchronization on T3,
|
||||
OC3, etc trunks or earth terminals) but seldom offer access to those
|
||||
time sources via NTP in turn to their clients, mostly from a misplaced
|
||||
fear that their time source might come under attack (a slave closely
|
||||
tied to the master could also provide extremely high-quality time
|
||||
without the risk of network desynchronization should it come under
|
||||
sophisticated attack).
|
||||
|
||||
As a result, the NTP servers that your ISP may point you at are
|
||||
often of unknown/unverified quality, and you use them at your own
|
||||
risk.
|
||||
|
||||
Early millenial versions of Windows (2000, XP, etc) used NTP only
|
||||
to _initially set_ the clock to approximately 100ms accuracy (and
|
||||
not maintain sychronization), so the bar wasn't set very high.
|
||||
Since then, requirements for higher-qualty timekeeping have
|
||||
arisen (e.g. multi-master SQL database replication), but most ISPs
|
||||
have not kept up with the needs of their users.
|
||||
|
||||
Current releases of Windows use Domain Controllers for time
|
||||
acquisition via the [NT5DS protocol](https://blogs.msdn.microsoft.com/w32time/2007/07/07/what-is-windows-time-service/)
|
||||
when domain joined.
|
||||
|
||||
Because of the unreliable quality of NTP servers DHCP-provisioned by
|
||||
ISPs, support for this functionality was deemed unnecessary.
|
|
@ -8,12 +8,74 @@ USE_PROCD=1
|
|||
PROG=/sbin/ntpd
|
||||
HOTPLUG_HELPER=/usr/sbin/ntpd.hotplug-helper
|
||||
|
||||
config_file=/var/run/ntpd.conf
|
||||
|
||||
trunc() {
|
||||
echo -n "" > $config_file
|
||||
}
|
||||
|
||||
emit() {
|
||||
echo -e "$@" >> $config_file
|
||||
}
|
||||
|
||||
validate_ntp_section() {
|
||||
uci_validate_section system timeserver "${1}" \
|
||||
'server:list(host)' 'enabled:bool:1' 'enable_server:bool:0' \
|
||||
'interface:list(string)'
|
||||
}
|
||||
|
||||
start_service() {
|
||||
local server enabled enable_server interface intf
|
||||
|
||||
validate_ntp_section ntp || {
|
||||
echo "validation failed"
|
||||
return 1
|
||||
}
|
||||
|
||||
[ "$enabled" = 0 ] && return
|
||||
|
||||
[ -z "$server" -a "$enable_server" = 0 ] && return
|
||||
|
||||
# not sure that the interfaces enumerated should be validated,
|
||||
# since some of them might be dynamic interfaces (like IPsec
|
||||
# tunnels) which aren't known by ubus.
|
||||
|
||||
trunc
|
||||
emit "driftfile /var/lib/ntp/ntp.drift\n"
|
||||
|
||||
if [ "$enable_server" != 0 ]; then
|
||||
emit "restrict default limited kod nomodify notrap nopeer"
|
||||
emit "restrict -6 default limited kod nomodify notrap nopeer"
|
||||
else
|
||||
emit "restrict -4 default noserve"
|
||||
emit "restrict -6 default noserve"
|
||||
fi
|
||||
emit "restrict source noquery"
|
||||
|
||||
emit "\n# No limits for local monitoring"
|
||||
emit "restrict 127.0.0.1"
|
||||
emit "restrict -6 ::1\n"
|
||||
|
||||
if [ -n "$interface" ]; then
|
||||
local loopback=$(ubus call network.interface dump | jsonfilter -e "@.interface[@.interface='loopback']['device']")
|
||||
|
||||
local saw_lo=
|
||||
for intf in $interface; do
|
||||
emit "interface listen $intf"
|
||||
[ "$intf" = "$loopback" ] && saw_lo=1
|
||||
done
|
||||
[ -z "$saw_lo" ] && emit "interface listen $loopback"
|
||||
emit ""
|
||||
fi
|
||||
|
||||
emit "server $server iburst"
|
||||
|
||||
mkdir -p /var/lib/ntp
|
||||
chown -R ntp:ntp /var/lib/ntp
|
||||
|
||||
procd_open_instance
|
||||
procd_set_param command $PROG -g -u ntp:ntp -p /var/run/ntpd.pid -n
|
||||
procd_set_param command $PROG -g -u ntp:ntp -p /var/run/ntpd.pid -n \
|
||||
-c $config_file
|
||||
procd_close_instance
|
||||
|
||||
procd_open_instance
|
||||
|
|
Loading…
Reference in a new issue