From ec351717c5906caa7070bea4a697526247e8146f Mon Sep 17 00:00:00 2001 From: jsing <> Date: Mon, 21 Jan 2019 08:38:22 +0000 Subject: [PATCH] Perform manual validity checking of the X.509 certificate for constraints. Given that we're getting a constraint so that we can validate time, if our own time is out we can fail the automatic validity checking since it is based on the wallclock. Instead, disable the automatic validity checking and perform manual checks based on the time reported from the server via the HTTP header. Discussed at length with and ok deraadt@ --- src/usr.sbin/ntpd/constraint.c | 23 ++++++++++++++++++++++- 1 file changed, 22 insertions(+), 1 deletion(-) diff --git a/src/usr.sbin/ntpd/constraint.c b/src/usr.sbin/ntpd/constraint.c index 3c48c6c9..4434a938 100644 --- a/src/usr.sbin/ntpd/constraint.c +++ b/src/usr.sbin/ntpd/constraint.c @@ -1,4 +1,4 @@ -/* $OpenBSD: constraint.c,v 1.39 2019/01/20 16:40:42 otto Exp $ */ +/* $OpenBSD: constraint.c,v 1.40 2019/01/21 08:38:22 jsing Exp $ */ /* * Copyright (c) 2015 Reyk Floeter @@ -874,6 +874,13 @@ httpsdate_init(const char *addr, const char *port, const char *hostname, if (tls_config_set_ca_mem(httpsdate->tls_config, ca, ca_len) == -1) goto fail; + /* + * Due to the fact that we're trying to determine a constraint for time + * we do our own certificate validity checking, since the automatic + * version is based on our wallclock, which may well be inaccurate... + */ + tls_config_insecure_noverifytime(httpsdate->tls_config); + return (httpsdate); fail: @@ -904,6 +911,7 @@ httpsdate_request(struct httpsdate *httpsdate, struct timeval *when) { size_t outlen = 0, maxlength = CONSTRAINT_MAXHEADERLENGTH, len; char *line, *p, *buf; + time_t httptime; ssize_t ret; if ((httpsdate->tls_ctx = tls_client()) == NULL) @@ -972,6 +980,19 @@ httpsdate_request(struct httpsdate *httpsdate, struct timeval *when) free(line); } + /* + * Now manually check the validity of the certificate presented in the + * TLS handshake, based on the time specified by the server's HTTP Date: + * header. + */ + httptime = timegm(&httpsdate->tls_tm); + if (httptime <= tls_peer_cert_notbefore(httpsdate->tls_ctx) || + httptime >= tls_peer_cert_notafter(httpsdate->tls_ctx)) { + log_warnx("tls certificate invalid: %s (%s):", + httpsdate->tls_addr, httpsdate->tls_hostname); + goto fail; + } + return (0); fail: