Currently, after 4 failed constraint checks, we suspect the constraint
authorreyk <reyk@openbsd.org>
Mon, 18 May 2015 14:19:23 +0000 (14:19 +0000)
committerreyk <reyk@openbsd.org>
Mon, 18 May 2015 14:19:23 +0000 (14:19 +0000)
of being wrong, not the NTP responses, reset it and query it from all
the constraint servers all over again.  This is turned out to be a bit
aggressive because it could get triggered with just a few bad NTP
peers in a larger pool.  To avoid constant reconnections, scale the
error margin with the number of resolved NTP peers using peer_cnt * 4.
This way a single or a few outliers in a NTP pool cannot trigger
reconnecting to the constraint servers immediately.  More NTP peers,
less reason to mistrust the constraint.

Found by dtucker@
OK deraadt@

usr.sbin/ntpd/constraint.c

index fe9dc00..25a4fa7 100644 (file)
@@ -1,4 +1,4 @@
-/*     $OpenBSD: constraint.c,v 1.9 2015/05/17 18:31:32 reyk Exp $     */
+/*     $OpenBSD: constraint.c,v 1.10 2015/05/18 14:19:23 reyk Exp $    */
 
 /*
  * Copyright (c) 2015 Reyk Floeter <reyk@openbsd.org>
@@ -66,6 +66,7 @@ void  *httpsdate_query(const char *, const char *, const char *,
 char   *tls_readline(struct tls *, size_t *, size_t *, struct timeval *);
 
 extern u_int constraint_cnt;
+extern u_int peer_cnt;
 
 struct httpsdate {
        char                    *tls_host;
@@ -560,7 +561,8 @@ constraint_check(double val)
        if (((val - constraint) > CONSTRAINT_MARGIN) ||
            ((constraint - val) > CONSTRAINT_MARGIN)) {
                /* XXX get new constraint if too many errors happened */
-               if (conf->constraint_errors++ > CONSTRAINT_ERROR_MARGIN) {
+               if (conf->constraint_errors++ >
+                   (CONSTRAINT_ERROR_MARGIN * peer_cnt)) {
                        constraint_reset();
                }