From 0d35a866ba12e66e504e1f575a04429c5d8cb9be Mon Sep 17 00:00:00 2001 From: Christian Breunig Date: Fri, 13 Jan 2023 22:07:34 +0100 Subject: ntp: T3008: migrate from ntpd to chrony * Move CLI from "system ntp" -> "service ntp" * Drop NTP server option preempt as not supported by chrony --- data/templates/chrony/chrony.conf.j2 | 58 +++++++++ data/templates/chrony/override.conf.j2 | 17 +++ data/templates/ntp/ntpd.conf.j2 | 49 ------- data/templates/ntp/override.conf.j2 | 14 -- data/templates/telegraf/telegraf.j2 | 2 +- debian/control | 3 +- .../include/version/ntp-version.xml.i | 2 +- interface-definitions/ntp.xml.in | 25 ++-- op-mode-definitions/date.xml.in | 22 ---- op-mode-definitions/monitor-log.xml.in | 6 + op-mode-definitions/show-log.xml.in | 6 + op-mode-definitions/show-ntp.xml.in | 17 +-- smoketest/scripts/cli/test_service_ntp.py | 141 +++++++++++++++++++++ smoketest/scripts/cli/test_system_ntp.py | 129 ------------------- src/conf_mode/ntp.py | 23 ++-- src/migration-scripts/ntp/1-to-2 | 67 ++++++++++ src/op_mode/show_ntp.sh | 31 ++--- 17 files changed, 344 insertions(+), 268 deletions(-) create mode 100644 data/templates/chrony/chrony.conf.j2 create mode 100644 data/templates/chrony/override.conf.j2 delete mode 100644 data/templates/ntp/ntpd.conf.j2 delete mode 100644 data/templates/ntp/override.conf.j2 create mode 100755 smoketest/scripts/cli/test_service_ntp.py delete mode 100755 smoketest/scripts/cli/test_system_ntp.py create mode 100755 src/migration-scripts/ntp/1-to-2 diff --git a/data/templates/chrony/chrony.conf.j2 b/data/templates/chrony/chrony.conf.j2 new file mode 100644 index 000000000..b3bfc8c0c --- /dev/null +++ b/data/templates/chrony/chrony.conf.j2 @@ -0,0 +1,58 @@ +### Autogenerated by ntp.py ### + +# This would step the system clock if the adjustment is larger than 0.1 seconds, +# but only in the first three clock updates. +makestep 1.0 3 + +# The rtcsync directive enables a mode where the system time is periodically +# copied to the RTC and chronyd does not try to track its drift. This directive +# cannot be used with the rtcfile directive. On Linux, the RTC copy is performed +# by the kernel every 11 minutes. +rtcsync + +# This directive specifies the maximum amount of memory that chronyd is allowed +# to allocate for logging of client accesses and the state that chronyd as an +# NTP server needs to support the interleaved mode for its clients. +clientloglimit 1048576 + +driftfile /run/chrony/drift +dumpdir /run/chrony +pidfile {{ config_file | replace('.conf', '.pid') }} + +# Determine when will the next leap second occur and what is the current offset +leapsectz right/UTC + +user {{ user }} + +# NTP servers to reach out to +{% if server is vyos_defined %} +{% for server, config in server.items() %} +{% set association = 'server' %} +{% if config.pool is vyos_defined %} +{% set association = 'pool' %} +{% endif %} +{{ association }} {{ server | replace('_', '-') }} iburst {{ 'noselect' if config.noselect is vyos_defined }} {{ 'prefer' if config.prefer is vyos_defined }} +{% endfor %} +{% endif %} + +# Allowed clients configuration +{% if allow_client.address is vyos_defined %} +{% for address in allow_client.address %} +allow {{ address }} +{% endfor %} +{% endif %} +deny all + +{% if listen_address is vyos_defined or interface is vyos_defined %} +# NTP should listen on configured addresses only +{% if listen_address is vyos_defined %} +{% for address in listen_address %} +bindaddress {{ address }} +{% endfor %} +{% endif %} +{% if interface is vyos_defined %} +{% for ifname in interface %} +binddevice {{ ifname }} +{% endfor %} +{% endif %} +{% endif %} diff --git a/data/templates/chrony/override.conf.j2 b/data/templates/chrony/override.conf.j2 new file mode 100644 index 000000000..9eaea7608 --- /dev/null +++ b/data/templates/chrony/override.conf.j2 @@ -0,0 +1,17 @@ +{% set vrf_command = 'ip vrf exec ' ~ vrf ~ ' ' if vrf is vyos_defined else '' %} +[Unit] +StartLimitIntervalSec=0 +ConditionPathExists={{ config_file }} +After=vyos-router.service + +[Service] +EnvironmentFile= +ExecStart= +ExecStart={{ vrf_command }}/usr/sbin/chronyd -F 1 -f {{ config_file }} +PIDFile= +PIDFile={{ config_file | replace('.conf', '.pid') }} +Restart=always +RestartSec=10 +# Required for VRF support +ProtectControlGroups=No + diff --git a/data/templates/ntp/ntpd.conf.j2 b/data/templates/ntp/ntpd.conf.j2 deleted file mode 100644 index 8921826fa..000000000 --- a/data/templates/ntp/ntpd.conf.j2 +++ /dev/null @@ -1,49 +0,0 @@ -### Autogenerated by ntp.py ### - -# -# Non-configurable defaults -# -driftfile /var/lib/ntp/ntp.drift -# By default, only allow ntpd to query time sources, ignore any incoming requests -restrict default noquery nopeer notrap nomodify -# Allow pool associations -restrict source nomodify notrap noquery -# Local users have unrestricted access, allowing reconfiguration via ntpdc -restrict 127.0.0.1 -restrict -6 ::1 - -# -# Configurable section -# -{% if server is vyos_defined %} -{% for server, config in server.items() %} -{% set association = 'server' %} -{% if config.pool is vyos_defined %} -{% set association = 'pool' %} -{% endif %} -{{ association }} {{ server | replace('_', '-') }} iburst {{ 'noselect' if config.noselect is vyos_defined }} {{ 'preempt' if config.preempt is vyos_defined }} {{ 'prefer' if config.prefer is vyos_defined }} -{% endfor %} -{% endif %} - -{% if allow_clients.address is vyos_defined %} -# Allowed clients configuration -restrict default ignore -{% for address in allow_clients.address %} -restrict {{ address | address_from_cidr }} mask {{ address | netmask_from_cidr }} nomodify notrap nopeer -{% endfor %} -{% endif %} - -{% if listen_address is vyos_defined or interface is vyos_defined %} -# NTP should listen on configured addresses only -interface ignore wildcard -{% if listen_address is vyos_defined %} -{% for address in listen_address %} -interface listen {{ address }} -{% endfor %} -{% endif %} -{% if interface is vyos_defined %} -{% for ifname in interface %} -interface listen {{ ifname }} -{% endfor %} -{% endif %} -{% endif %} diff --git a/data/templates/ntp/override.conf.j2 b/data/templates/ntp/override.conf.j2 deleted file mode 100644 index 6fed9d7d2..000000000 --- a/data/templates/ntp/override.conf.j2 +++ /dev/null @@ -1,14 +0,0 @@ -{% set vrf_command = 'ip vrf exec ' ~ vrf ~ ' ' if vrf is vyos_defined else '' %} -[Unit] -StartLimitIntervalSec=0 -ConditionPathExists={{ config_file }} -After=vyos-router.service - -[Service] -ExecStart= -ExecStart={{ vrf_command }}/usr/sbin/ntpd -g -p {{ config_file | replace('.conf', '.pid') }} -c {{ config_file }} -u ntp:ntp -PIDFile= -PIDFile={{ config_file | replace('.conf', '.pid') }} -Restart=always -RestartSec=10 - diff --git a/data/templates/telegraf/telegraf.j2 b/data/templates/telegraf/telegraf.j2 index 36571ce98..c9f402281 100644 --- a/data/templates/telegraf/telegraf.j2 +++ b/data/templates/telegraf/telegraf.j2 @@ -102,7 +102,7 @@ dirs = ["/proc/sys/net/ipv4/netfilter","/proc/sys/net/netfilter"] [[inputs.ethtool]] interface_include = {{ interfaces_ethernet }} -[[inputs.ntpq]] +[[inputs.chrony]] dns_lookup = true [[inputs.internal]] [[inputs.nstat]] diff --git a/debian/control b/debian/control index a477bffec..1e593d378 100644 --- a/debian/control +++ b/debian/control @@ -101,8 +101,7 @@ Depends: nfct, nftables (>= 0.9.3), nginx-light, - ntp, - ntpdate, + chrony, nvme-cli, ocserv, opennhrp, diff --git a/interface-definitions/include/version/ntp-version.xml.i b/interface-definitions/include/version/ntp-version.xml.i index cc4ff9a1c..9eafbf7f0 100644 --- a/interface-definitions/include/version/ntp-version.xml.i +++ b/interface-definitions/include/version/ntp-version.xml.i @@ -1,3 +1,3 @@ - + diff --git a/interface-definitions/ntp.xml.in b/interface-definitions/ntp.xml.in index 85636a50f..65e40ee32 100644 --- a/interface-definitions/ntp.xml.in +++ b/interface-definitions/ntp.xml.in @@ -1,7 +1,7 @@ - + @@ -43,12 +43,6 @@ - - - Specifies the association as preemptable rather than the default persistent - - - Marks the server as preferred @@ -57,24 +51,33 @@ - + - Network Time Protocol (NTP) server options + Specify NTP clients allowed to access the server IP address + + ipv4 + Allowed IPv4 address + ipv4net - IP address and prefix length + Allowed IPv4 prefix + + + ipv6 + Allowed IPv6 address ipv6net - IPv6 address and prefix length + Allowed IPv6 prefix + diff --git a/op-mode-definitions/date.xml.in b/op-mode-definitions/date.xml.in index 15a69dbd9..6d8586025 100644 --- a/op-mode-definitions/date.xml.in +++ b/op-mode-definitions/date.xml.in @@ -37,28 +37,6 @@ /bin/date "$3" - - - Set system date and time - - - - - Set system date and time from NTP server (default: 0.pool.ntp.org) - - /usr/sbin/ntpdate -u 0.pool.ntp.org - - - - Set system date and time from NTP server - - - - - /usr/sbin/ntpdate -u "$4" - - - diff --git a/op-mode-definitions/monitor-log.xml.in b/op-mode-definitions/monitor-log.xml.in index 95d5ecf96..d616bfc08 100644 --- a/op-mode-definitions/monitor-log.xml.in +++ b/op-mode-definitions/monitor-log.xml.in @@ -105,6 +105,12 @@ journalctl --no-hostname --boot --follow --unit opennhrp.service + + + Monitor last lines of Network Time Protocol (NTP) log + + journalctl --no-hostname --boot --follow --unit chrony.service + Monitor last lines of PPPoE log diff --git a/op-mode-definitions/show-log.xml.in b/op-mode-definitions/show-log.xml.in index 2984c467c..6608ea0d8 100644 --- a/op-mode-definitions/show-log.xml.in +++ b/op-mode-definitions/show-log.xml.in @@ -220,6 +220,12 @@ journalctl --no-hostname --boot --unit opennhrp.service + + + Show log for Network Time Protocol (NTP) + + journalctl --no-hostname --boot --unit chrony.service + Show log for MACsec diff --git a/op-mode-definitions/show-ntp.xml.in b/op-mode-definitions/show-ntp.xml.in index 01f4477d8..0907722af 100644 --- a/op-mode-definitions/show-ntp.xml.in +++ b/op-mode-definitions/show-ntp.xml.in @@ -6,22 +6,13 @@ Show peer status of NTP daemon - ${vyos_op_scripts_dir}/show_ntp.sh --basic + ${vyos_op_scripts_dir}/show_ntp.sh --sourcestats - + - Show date and time of specified NTP server - - - + Show parameters about the system clock performance - ${vyos_op_scripts_dir}/show_ntp.sh --server "$4" - - - - Show NTP operational summary - - ${vyos_op_scripts_dir}/show_ntp.sh --info + ${vyos_op_scripts_dir}/show_ntp.sh --tracking diff --git a/smoketest/scripts/cli/test_service_ntp.py b/smoketest/scripts/cli/test_service_ntp.py new file mode 100755 index 000000000..d4793adb6 --- /dev/null +++ b/smoketest/scripts/cli/test_service_ntp.py @@ -0,0 +1,141 @@ +#!/usr/bin/env python3 +# +# Copyright (C) 2019-2023 VyOS maintainers and contributors +# +# This program is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License version 2 or later as +# published by the Free Software Foundation. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program. If not, see . + +import unittest + +from base_vyostest_shim import VyOSUnitTestSHIM + +from vyos.configsession import ConfigSessionError +from vyos.util import cmd +from vyos.util import process_named_running + +PROCESS_NAME = 'chronyd' +NTP_CONF = '/run/chrony/chrony.conf' +base_path = ['service', 'ntp'] + +class TestSystemNTP(VyOSUnitTestSHIM.TestCase): + @classmethod + def setUpClass(cls): + super(TestSystemNTP, cls).setUpClass() + + # ensure we can also run this test on a live system - so lets clean + # out the current configuration :) + cls.cli_delete(cls, base_path) + + def tearDown(self): + self.assertTrue(process_named_running(PROCESS_NAME)) + + self.cli_delete(base_path) + self.cli_commit() + + self.assertFalse(process_named_running(PROCESS_NAME)) + + def test_01_ntp_options(self): + # Test basic NTP support with multiple servers and their options + servers = ['192.0.2.1', '192.0.2.2'] + options = ['noselect', 'prefer'] + pools = ['pool.vyos.io'] + + for server in servers: + for option in options: + self.cli_set(base_path + ['server', server, option]) + + # Test NTP pool + for pool in pools: + self.cli_set(base_path + ['server', pool, 'pool']) + + # commit changes + self.cli_commit() + + # Check generated configuration + # this file must be read with higher permissions + config = cmd(f'sudo cat {NTP_CONF}') + self.assertIn('driftfile /run/chrony/drift', config) + self.assertIn('dumpdir /run/chrony', config) + self.assertIn('clientloglimit 1048576', config) + self.assertIn('rtcsync', config) + self.assertIn('makestep 1.0 3', config) + self.assertIn('leapsectz right/UTC', config) + + for server in servers: + self.assertIn(f'server {server} iburst ' + ' '.join(options), config) + + for pool in pools: + self.assertIn(f'pool {pool} iburst', config) + + def test_02_ntp_clients(self): + # Test the allowed-networks statement + listen_address = ['127.0.0.1', '::1'] + for listen in listen_address: + self.cli_set(base_path + ['listen-address', listen]) + + networks = ['192.0.2.0/24', '2001:db8:1000::/64', '100.64.0.0', '2001:db8::ffff'] + for network in networks: + self.cli_set(base_path + ['allow-client', 'address', network]) + + # Verify "NTP server not configured" verify() statement + with self.assertRaises(ConfigSessionError): + self.cli_commit() + + servers = ['192.0.2.1', '192.0.2.2'] + for server in servers: + self.cli_set(base_path + ['server', server]) + + self.cli_commit() + + # Check generated client address configuration + # this file must be read with higher permissions + config = cmd(f'sudo cat {NTP_CONF}') + for network in networks: + self.assertIn(f'allow {network}', config) + + # Check listen address + for listen in listen_address: + self.assertIn(f'bindaddress {listen}', config) + + def test_03_ntp_interface(self): + interfaces = ['eth0', 'eth1'] + for interface in interfaces: + self.cli_set(base_path + ['interface', interface]) + + servers = ['time1.vyos.net', 'time2.vyos.net'] + for server in servers: + self.cli_set(base_path + ['server', server]) + + self.cli_commit() + + # Check generated client address configuration + # this file must be read with higher permissions + config = cmd(f'sudo cat {NTP_CONF}') + for interface in interfaces: + self.assertIn(f'binddevice {interface}', config) + + def test_04_ntp_vrf(self): + vrf_name = 'vyos-mgmt' + + self.cli_set(['vrf', 'name', vrf_name, 'table', '12345']) + self.cli_set(base_path + ['vrf', vrf_name]) + + servers = ['time1.vyos.net', 'time2.vyos.net'] + for server in servers: + self.cli_set(base_path + ['server', server]) + + self.cli_commit() + + self.cli_delete(['vrf', 'name', vrf_name]) + +if __name__ == '__main__': + unittest.main(verbosity=2) diff --git a/smoketest/scripts/cli/test_system_ntp.py b/smoketest/scripts/cli/test_system_ntp.py deleted file mode 100755 index a0806acf0..000000000 --- a/smoketest/scripts/cli/test_system_ntp.py +++ /dev/null @@ -1,129 +0,0 @@ -#!/usr/bin/env python3 -# -# Copyright (C) 2019-2022 VyOS maintainers and contributors -# -# This program is free software; you can redistribute it and/or modify -# it under the terms of the GNU General Public License version 2 or later as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it will be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program. If not, see . - -import unittest - -from base_vyostest_shim import VyOSUnitTestSHIM - -from vyos.configsession import ConfigSessionError -from vyos.template import address_from_cidr -from vyos.template import netmask_from_cidr -from vyos.util import read_file -from vyos.util import process_named_running - -PROCESS_NAME = 'ntpd' -NTP_CONF = '/run/ntpd/ntpd.conf' -base_path = ['system', 'ntp'] - -class TestSystemNTP(VyOSUnitTestSHIM.TestCase): - @classmethod - def setUpClass(cls): - super(TestSystemNTP, cls).setUpClass() - - # ensure we can also run this test on a live system - so lets clean - # out the current configuration :) - cls.cli_delete(cls, base_path) - - def tearDown(self): - self.cli_delete(base_path) - self.cli_commit() - - self.assertFalse(process_named_running(PROCESS_NAME)) - - def test_01_ntp_options(self): - # Test basic NTP support with multiple servers and their options - servers = ['192.0.2.1', '192.0.2.2'] - options = ['noselect', 'preempt', 'prefer'] - pools = ['pool.vyos.io'] - - for server in servers: - for option in options: - self.cli_set(base_path + ['server', server, option]) - - # Test NTP pool - for pool in pools: - self.cli_set(base_path + ['server', pool, 'pool']) - - # commit changes - self.cli_commit() - - # Check generated configuration - config = read_file(NTP_CONF) - self.assertIn('driftfile /var/lib/ntp/ntp.drift', config) - self.assertIn('restrict default noquery nopeer notrap nomodify', config) - self.assertIn('restrict source nomodify notrap noquery', config) - self.assertIn('restrict 127.0.0.1', config) - self.assertIn('restrict -6 ::1', config) - - for server in servers: - self.assertIn(f'server {server} iburst ' + ' '.join(options), config) - - for pool in pools: - self.assertIn(f'pool {pool} iburst', config) - - def test_02_ntp_clients(self): - # Test the allowed-networks statement - listen_address = ['127.0.0.1', '::1'] - for listen in listen_address: - self.cli_set(base_path + ['listen-address', listen]) - - networks = ['192.0.2.0/24', '2001:db8:1000::/64'] - for network in networks: - self.cli_set(base_path + ['allow-clients', 'address', network]) - - # Verify "NTP server not configured" verify() statement - with self.assertRaises(ConfigSessionError): - self.cli_commit() - - servers = ['192.0.2.1', '192.0.2.2'] - for server in servers: - self.cli_set(base_path + ['server', server]) - - self.cli_commit() - - # Check generated client address configuration - config = read_file(NTP_CONF) - self.assertIn('restrict default ignore', config) - - for network in networks: - network_address = address_from_cidr(network) - network_netmask = netmask_from_cidr(network) - self.assertIn(f'restrict {network_address} mask {network_netmask} nomodify notrap nopeer', config) - - # Check listen address - self.assertIn('interface ignore wildcard', config) - for listen in listen_address: - self.assertIn(f'interface listen {listen}', config) - - def test_03_ntp_interface(self): - interfaces = ['eth0', 'eth1'] - for interface in interfaces: - self.cli_set(base_path + ['interface', interface]) - - servers = ['time1.vyos.net', 'time2.vyos.net'] - for server in servers: - self.cli_set(base_path + ['server', server]) - - self.cli_commit() - - # Check generated client address configuration - config = read_file(NTP_CONF) - self.assertIn('interface ignore wildcard', config) - for interface in interfaces: - self.assertIn(f'interface listen {interface}', config) - -if __name__ == '__main__': - unittest.main(verbosity=2) diff --git a/src/conf_mode/ntp.py b/src/conf_mode/ntp.py index 0ecb4d736..92cb73aab 100755 --- a/src/conf_mode/ntp.py +++ b/src/conf_mode/ntp.py @@ -1,6 +1,6 @@ #!/usr/bin/env python3 # -# Copyright (C) 2018-2022 VyOS maintainers and contributors +# Copyright (C) 2018-2023 VyOS maintainers and contributors # # This program is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License version 2 or later as @@ -21,26 +21,29 @@ from vyos.configdict import is_node_changed from vyos.configverify import verify_vrf from vyos.configverify import verify_interface_exists from vyos.util import call +from vyos.util import chmod_750 from vyos.util import get_interface_config from vyos.template import render from vyos import ConfigError from vyos import airbag airbag.enable() -config_file = r'/run/ntpd/ntpd.conf' -systemd_override = r'/etc/systemd/system/ntp.service.d/override.conf' +config_file = r'/run/chrony/chrony.conf' +systemd_override = r'/run/systemd/system/chrony.service.d/override.conf' +user_group = '_chrony' def get_config(config=None): if config: conf = config else: conf = Config() - base = ['system', 'ntp'] + base = ['service', 'ntp'] if not conf.exists(base): return None ntp = conf.get_config_dict(base, key_mangling=('-', '_'), get_first_key=True) ntp['config_file'] = config_file + ntp['user'] = user_group tmp = is_node_changed(conf, base + ['vrf']) if tmp: ntp.update({'restart_required': {}}) @@ -52,7 +55,7 @@ def verify(ntp): if not ntp: return None - if 'allow_clients' in ntp and 'server' not in ntp: + if 'server' not in ntp: raise ConfigError('NTP server not configured') verify_vrf(ntp) @@ -77,13 +80,17 @@ def generate(ntp): if not ntp: return None - render(config_file, 'ntp/ntpd.conf.j2', ntp) - render(systemd_override, 'ntp/override.conf.j2', ntp) + render(config_file, 'chrony/chrony.conf.j2', ntp, user=user_group, group=user_group) + render(systemd_override, 'chrony/override.conf.j2', ntp, user=user_group, group=user_group) + + # Ensure proper permission for chrony command socket + config_dir = os.path.dirname(config_file) + chmod_750(config_dir) return None def apply(ntp): - systemd_service = 'ntp.service' + systemd_service = 'chrony.service' # Reload systemd manager configuration call('systemctl daemon-reload') diff --git a/src/migration-scripts/ntp/1-to-2 b/src/migration-scripts/ntp/1-to-2 new file mode 100755 index 000000000..1faf0b0e6 --- /dev/null +++ b/src/migration-scripts/ntp/1-to-2 @@ -0,0 +1,67 @@ +#!/usr/bin/env python3 + +# Copyright (C) 2023 VyOS maintainers and contributors +# +# This program is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License version 2 or later as +# published by the Free Software Foundation. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program. If not, see . + +# T3008: move from ntpd to chrony and migrate "system ntp" to "service ntp" + +import sys + +from vyos.configtree import ConfigTree + +if (len(sys.argv) < 1): + print("Must specify file name!") + sys.exit(1) + +file_name = sys.argv[1] + +with open(file_name, 'r') as f: + config_file = f.read() + +config = ConfigTree(config_file) + +base_path = ['system', 'ntp'] +new_base_path = ['service', 'ntp'] +if not config.exists(base_path): + # Nothing to do + sys.exit(0) + +# copy "system ntp" to "service ntp" +config.copy(base_path, new_base_path) +config.delete(base_path) + +# chrony does not support the preempt option, drop it +for server in config.list_nodes(new_base_path + ['server']): + server_base = new_base_path + ['server', server] + if config.exists(server_base + ['preempt']): + config.delete(server_base + ['preempt']) + +# Rename "allow-clients" -> "allow-client" +if config.exists(new_base_path + ['allow-clients']): + config.rename(new_base_path + ['allow-client']) + +# By default VyOS 1.3 allowed NTP queries for all networks - in chrony we +# explicitly disable this behavior and clients need to be specified using the +# allow-client CLI option. In order to be fully backwards compatible, we specify +# 0.0.0.0/0 and ::/0 as allow networks if not specified otherwise explicitly. +if not config.exists(new_base_path + ['allow-client']): + config.set(new_base_path + ['allow-client', 'address'], value='0.0.0.0/0', replace=False) + config.set(new_base_path + ['allow-client', 'address'], value='::/0', replace=False) + +try: + with open(file_name, 'w') as f: + f.write(config.to_string()) +except OSError as e: + print("Failed to save the modified config: {}".format(e)) + sys.exit(1) diff --git a/src/op_mode/show_ntp.sh b/src/op_mode/show_ntp.sh index e9dd6c5c9..85f8eda15 100755 --- a/src/op_mode/show_ntp.sh +++ b/src/op_mode/show_ntp.sh @@ -1,39 +1,34 @@ #!/bin/sh -basic=0 -info=0 +sourcestats=0 +tracking=0 while [[ "$#" -gt 0 ]]; do case $1 in - --info) info=1 ;; - --basic) basic=1 ;; - --server) server=$2; shift ;; + --sourcestats) sourcestats=1 ;; + --tracking) tracking=1 ;; *) echo "Unknown parameter passed: $1" ;; esac shift done -if ! ps -C ntpd &>/dev/null; then +if ! ps -C chronyd &>/dev/null; then echo NTP daemon disabled exit 1 fi -PID=$(pgrep ntpd) -VRF_NAME=$(ip vrf identify ${PID}) +PID=$(pgrep chronyd | head -n1) +VRF_NAME=$(ip vrf identify ) if [ ! -z ${VRF_NAME} ]; then VRF_CMD="sudo ip vrf exec ${VRF_NAME}" fi -if [ $basic -eq 1 ]; then - $VRF_CMD ntpq -n -c peers -elif [ $info -eq 1 ]; then - echo "=== sysingo ===" - $VRF_CMD ntpq -n -c sysinfo - echo - echo "=== kerninfo ===" - $VRF_CMD ntpq -n -c kerninfo -elif [ ! -z $server ]; then - $VRF_CMD /usr/sbin/ntpdate -q $server +if [ $sourcestats -eq 1 ]; then + $VRF_CMD chronyc sourcestats -v +elif [ $tracking -eq 1 ]; then + $VRF_CMD chronyc tracking -v +else + echo "Unknown option" fi -- cgit v1.2.3