How to Configure ntp.toml for ntpd-rs with NTS Servers
To configure ntp.toml for ntpd-rs with NTS servers, populate [[source]] tables with mode = "nts" and the server address, then point ntpd-rs to the file via --config or the NTPD_RS_CONFIG environment variable.
The jauderho/nts-servers repository maintains a curated, auto-generated ntp.toml file specifically for ntpd-rs, a modern Rust-based NTP daemon. This configuration enables secure time synchronization using Network Time Security (NTS), eliminating the need to manually compile server lists or risk configuration drift.
Understanding the ntp.toml Configuration Structure
The ntp.toml file uses TOML format with a series of [[source]] tables. Each table represents a single NTS-enabled time server that ntpd-rs will contact.
A minimal entry requires two fields:
[[source]]
mode = "nts"
address = "time.cloudflare.com"
The mode = "nts" parameter instructs ntpd-rs to perform an NTS-KE (Key Establishment) handshake and use authenticated NTP packets. The address field accepts any NTS-enabled hostname. According to the repository's generate_ntp_toml function in scripts/ntpServerConverter.py (lines 86-104), each server from the master data file is emitted as a separate [[source]] block in this exact format.
Generating ntp.toml from the nts-servers Repository
Rather than maintaining ntp.toml manually, the repository provides an automated pipeline that generates the configuration from a canonical data source.
The nts-sources.yml Data Source
The authoritative list of servers resides in nts-sources.yml at the repository root. This YAML file contains metadata for each server including hostname, stratum, location, owner, and a vm flag indicating virtualized infrastructure. When servers are added or updated here, the downstream configuration files automatically reflect those changes.
The ntpServerConverter.py Script
The Python script scripts/ntpServerConverter.py reads nts-sources.yml and produces three artifacts: a Markdown server list, a chrony.conf, and the ntp.toml file. The generation logic specifically filters for NTS-capable entries and formats them into the required TOML structure.
To regenerate the configuration:
# From the repository root
./scripts/ntpServerConverter.py nts-sources.yml
This command outputs:
README.md(updated server table)chrony.conf(for Chrony users)ntp.toml(for ntpd-rs users)
Always run git diff after regeneration to verify that only the intended files changed, as recommended in the repository documentation.
Configuring ntpd-rs to Use Your ntp.toml
Once you have generated or manually created ntp.toml, you must ensure ntpd-rs can locate and parse it at startup.
File Placement
The standard system location for ntpd-rs configuration is /etc/ntpd-rs/ntp.toml. Copy the generated file there:
sudo cp ntp.toml /etc/ntpd-rs/ntp.toml
sudo chmod 644 /etc/ntpd-rs/ntp.toml
Command-Line and Environment Options
If you prefer to keep the configuration in a custom location, ntpd-rs accepts the --config flag:
ntpd-rs --config /path/to/ntp.toml
Alternatively, set the NTPD_RS_CONFIG environment variable:
export NTPD_RS_CONFIG=/path/to/ntp.toml
ntpd-rs
Starting the Daemon
For production use, enable and start the systemd service:
sudo systemctl enable --now ntpd-rs
For testing or debugging, run the daemon manually in the foreground to verify it parses the configuration correctly:
ntpd-rs --config ntp.toml
Best Practices for NTS Server Selection
The jauderho/nts-servers repository enforces specific constraints to ensure reliable and secure time synchronization.
Server Quantity Limits
Configure at least 4 and no more than 10 distinct NTS servers. This range provides sufficient redundancy for Byzantine fault tolerance while avoiding excessive network load and NTS-KE handshake overhead.
Avoid Mixed Modes
Do not mix classic NTP (mode = "client") with NTS entries in the same ntp.toml file. The repository specifically generates NTS-only configurations, and ntpd-rs handles authentication parameters differently for each mode.
Virtualized Host Considerations
Entries marked with vm: true in nts-sources.yml indicate virtualized infrastructure. These servers may exhibit higher jitter due to hypervisor scheduling and are grouped separately in the generated TOML. Use them as supplementary sources rather than primary timekeepers.
Anycast Limitations
Many public NTS servers use Anycast routing (e.g., Cloudflare). While this improves availability, refer to RFC 8633 section 4.3 for potential limitations regarding path asymmetry and certificate validation in Anycast deployments.
Verifying NTS Authentication
After starting ntpd-rs with your ntp.toml, confirm that NTS handshakes are succeeding.
Use the ntpq utility to inspect peer status:
ntpq -p -c "ntp server"
Look for the N flag in the remote column, which indicates successful NTS authentication. If the flag is absent, verify that the server supports NTS and that your firewall allows TCP port 4460 (NTS-KE) and UDP port 123 (NTP).
Summary
- The
ntp.tomlfile uses[[source]]tables withmode = "nts"and anaddressfield to define NTS servers for ntpd-rs. - The
jauderho/nts-serversrepository auto-generates this file fromnts-sources.ymlusingscripts/ntpServerConverter.py(specifically thegenerate_ntp_tomlfunction at lines 86-104). - Deploy the configuration to
/etc/ntpd-rs/ntp.toml, or specify a custom path via--configor theNTPD_RS_CONFIGenvironment variable. - Maintain 4 to 10 NTS sources for optimal security and reliability, avoiding mixed-mode configurations.
- Verify NTS operation using
ntpqand look for theNauthentication flag.
Frequently Asked Questions
How do I add a new NTS server to my ntp.toml configuration?
Edit the nts-sources.yml file in the repository root to include the new server details (hostname, stratum, location, owner), then run ./scripts/ntpServerConverter.py nts-sources.yml to regenerate ntp.toml. This ensures the new server appears with the correct mode = "nts" syntax and maintains consistency across all generated configuration files.
Can I mix NTS servers with standard NTP servers in the same ntp.toml file?
No, you should not mix mode = "nts" entries with mode = "client" (standard NTP) in the same configuration. The jauderho/nts-servers repository generates NTS-only configurations, and ntpd-rs handles authentication and certificate validation specifically for NTS mode. Mixing modes may cause configuration parsing errors or unexpected security behavior.
What is the recommended number of NTS servers to configure in ntp.toml?
Configure between 4 and 10 NTS servers. The repository documentation specifies a minimum of 4 servers to provide adequate redundancy and protection against Byzantine faults, while limiting the maximum to 10 prevents excessive network overhead from NTS-KE handshakes and certificate exchanges. This range balances reliability with performance.
How do I verify that ntpd-rs is actually using NTS authentication?
Use the ntpq utility with the command ntpq -p -c "ntp server" and examine the output for the N flag in the remote column. This flag indicates that the server connection is using NTS authentication. If the flag is missing, verify that the server supports NTS, that your firewall allows TCP port 4460 (for NTS-KE), and that the mode = "nts" setting is correctly specified in your ntp.toml file.
Have a question about this repo?
These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:
curl -s "https://instagit.com/install.md" Maintain an open-source project? Get it listed too →