On Wed, Nov 29, 2023 at 11:57:15AM +0100, Otto Moerbeek wrote: > On Wed, Nov 29, 2023 at 08:49:55AM +0100, Otto Moerbeek wrote: > > > On Tue, Nov 28, 2023 at 04:19:07PM +0100, Paul de Weerd wrote: > > > > > Hi all, > > > > > > I have a few APU's I'm using to experiment with some stuff. I found all > > > of them unable to sync with NTP because they don't have IPv4 > > > connectivity to the outside world. > > > > > > Digging a bit deeper, it turns out that v6 is only configured after > > > ntpd is started. This means the constraints cannot be reached (ntpd > > > logs "constraints configured but none available"). Even if v6 becomes > > > available (shortly after) ntpd is started, ntpd still refuses to try > > > to connect to the constraints over IPv6. > > > > > > Simply restarting ntpd when an IPv6 address is configured makes > > > everything go again: the constraint servers can be reached, so those > > > are checked, and then the regular NTP servers also work fine. > > > > > > Address configuration is dynamic: > > > > > > --- cat /etc/hostname.em0 -------------------------------------------- > > > up > > > inet autoconf > > > inet6 autoconf > > > ---------------------------------------------------------------------- > > > > > > I have confirmed the behaviour by removing all config from the > > > interface, stopping ntpd and then bringing up a v4 address (ifconfig > > > em0 inet autoconf), starting ntpd and bringing up a v6 address > > > (ifconfig em0 inet6 autoconf). ntpd never connects to the constraint > > > servers, despite having a v6 address (and the constraint servers have > > > AAAA records, obviously). Again, restarting ntpd when a v6 address is > > > configured gets things going: constraint servers are reached just > > > fine, and time is adjusted according to NTP. > > > > > > Paul 'WEiRD' de Weerd > > > > I'll see if I can find the root cuase of this. > > > > -Otto > > > > > So I tried a couple of configs--all with a v6 address coming up late-- > with both no v4 at all and v4 but not working, but in all cases > (though it may take a while) the contrainst *did* use v6 addresses, > both for the hardcoded case and retrieved via DNS case. > > So I like to see your config and also -vv log files to figure out > what's different in your setup. > > -Otto >
With your config detail i managed to reproduce. What is happening is that the initial constraint DNS info which does not include v6 info gets re-used. The diff below resets the constraint DNS info immediately after first use and then periodically (but only after all constraint queries have been done). For constraints we do no want to stick to a DNS resolve result too long anyway. For NTP peers it worked already, since they redo DNS after they cycled though the list of available addresses. I'm doing some more tests, but here's the diff I'm using. -Otto Index: ntp.c =================================================================== RCS file: /home/cvs/src/usr.sbin/ntpd/ntp.c,v diff -u -p -r1.170 ntp.c --- ntp.c 27 Nov 2022 13:19:00 -0000 1.170 +++ ntp.c 29 Nov 2023 18:31:23 -0000 @@ -75,6 +75,7 @@ ntp_main(struct ntpd_conf *nconf, struct int nullfd, pipe_dns[2], idx_clients; int ctls; int fd_ctl; + int clear_cdns; u_int pfd_elms = 0, idx2peer_elms = 0; u_int listener_cnt, new_cnt, sent_cnt, trial_cnt; u_int ctl_cnt; @@ -89,7 +90,7 @@ ntp_main(struct ntpd_conf *nconf, struct struct stat stb; struct ctl_conn *cc; time_t nextaction, last_sensor_scan = 0, now; - time_t last_action = 0, interval; + time_t last_action = 0, interval, last_cdns_reset = 0; void *newp; if (socketpair(AF_UNIX, SOCK_STREAM | SOCK_CLOEXEC, PF_UNSPEC, @@ -326,9 +327,11 @@ ntp_main(struct ntpd_conf *nconf, struct (peer_cnt == 0 && sensors_cnt == 0))) priv_settime(0, "no valid peers configured"); + clear_cdns = 1; TAILQ_FOREACH(cstr, &conf->constraints, entry) { - if (constraint_query(cstr, conf->status.synced) == -1) - continue; + constraint_query(cstr, conf->status.synced); + if (cstr->state <= STATE_QUERY_SENT) + clear_cdns = 0; } if (ibuf_main->w.queued > 0) @@ -346,6 +349,12 @@ ntp_main(struct ntpd_conf *nconf, struct ctls = i; now = getmonotime(); + if (clear_cdns && now - last_cdns_reset > CONSTRAINT_SCAN_INTERVAL) { + log_debug("Reset constraint info"); + constraint_reset(); + last_cdns_reset = now; + nextaction = now + CONSTRAINT_RETRY_INTERVAL; + } timeout = nextaction - now; if (timeout < 0) timeout = 0;