at 24.11-pre 3.7 kB view raw
1{ config, lib, pkgs, ... }: 2 3with lib; 4 5let 6 7 inherit (pkgs) ntp; 8 9 cfg = config.services.ntp; 10 11 stateDir = "/var/lib/ntp"; 12 13 configFile = pkgs.writeText "ntp.conf" '' 14 driftfile ${stateDir}/ntp.drift 15 16 restrict default ${toString cfg.restrictDefault} 17 restrict -6 default ${toString cfg.restrictDefault} 18 restrict source ${toString cfg.restrictSource} 19 20 restrict 127.0.0.1 21 restrict -6 ::1 22 23 ${toString (map (server: "server " + server + " iburst\n") cfg.servers)} 24 25 ${cfg.extraConfig} 26 ''; 27 28 ntpFlags = [ "-c" "${configFile}" "-u" "ntp:ntp" ] ++ cfg.extraFlags; 29 30in 31 32{ 33 34 ###### interface 35 36 options = { 37 38 services.ntp = { 39 40 enable = mkOption { 41 type = types.bool; 42 default = false; 43 description = '' 44 Whether to synchronise your machine's time using ntpd, as a peer in 45 the NTP network. 46 47 Disables `systemd.timesyncd` if enabled. 48 ''; 49 }; 50 51 restrictDefault = mkOption { 52 type = types.listOf types.str; 53 description = '' 54 The restriction flags to be set by default. 55 56 The default flags prevent external hosts from using ntpd as a DDoS 57 reflector, setting system time, and querying OS/ntpd version. As 58 recommended in section 6.5.1.1.3, answer "No" of 59 https://support.ntp.org/Support/AccessRestrictions 60 ''; 61 default = [ "limited" "kod" "nomodify" "notrap" "noquery" "nopeer" ]; 62 }; 63 64 restrictSource = mkOption { 65 type = types.listOf types.str; 66 description = '' 67 The restriction flags to be set on source. 68 69 The default flags allow peers to be added by ntpd from configured 70 pool(s), but not by other means. 71 ''; 72 default = [ "limited" "kod" "nomodify" "notrap" "noquery" ]; 73 }; 74 75 servers = mkOption { 76 default = config.networking.timeServers; 77 defaultText = literalExpression "config.networking.timeServers"; 78 type = types.listOf types.str; 79 description = '' 80 The set of NTP servers from which to synchronise. 81 ''; 82 }; 83 84 extraConfig = mkOption { 85 type = types.lines; 86 default = ""; 87 example = '' 88 fudge 127.127.1.0 stratum 10 89 ''; 90 description = '' 91 Additional text appended to {file}`ntp.conf`. 92 ''; 93 }; 94 95 extraFlags = mkOption { 96 type = types.listOf types.str; 97 description = "Extra flags passed to the ntpd command."; 98 example = literalExpression ''[ "--interface=eth0" ]''; 99 default = []; 100 }; 101 102 }; 103 104 }; 105 106 107 ###### implementation 108 109 config = mkIf config.services.ntp.enable { 110 meta.maintainers = with lib.maintainers; [ thoughtpolice ]; 111 112 # Make tools such as ntpq available in the system path. 113 environment.systemPackages = [ pkgs.ntp ]; 114 services.timesyncd.enable = mkForce false; 115 116 systemd.services.systemd-timedated.environment = { SYSTEMD_TIMEDATED_NTP_SERVICES = "ntpd.service"; }; 117 118 users.users.ntp = 119 { isSystemUser = true; 120 group = "ntp"; 121 description = "NTP daemon user"; 122 home = stateDir; 123 }; 124 users.groups.ntp = {}; 125 126 systemd.services.ntpd = 127 { description = "NTP Daemon"; 128 129 wantedBy = [ "multi-user.target" ]; 130 wants = [ "time-sync.target" ]; 131 before = [ "time-sync.target" ]; 132 133 preStart = 134 '' 135 mkdir -m 0755 -p ${stateDir} 136 chown ntp ${stateDir} 137 ''; 138 139 serviceConfig = { 140 ExecStart = "@${ntp}/bin/ntpd ntpd -g ${builtins.toString ntpFlags}"; 141 Type = "forking"; 142 }; 143 }; 144 145 }; 146 147}