bin/134787: [patch] ntpd: fix CVE-2009-1252, remote code execution when autokey is enabled

Eygene Ryabinkin rea-fbsd at codelabs.ru
Thu May 21 15:20:03 UTC 2009


>Number:         134787
>Category:       bin
>Synopsis:       [patch] ntpd: fix CVE-2009-1252, remote code execution when autokey is enabled
>Confidential:   no
>Severity:       serious
>Priority:       high
>Responsible:    freebsd-bugs
>State:          open
>Quarter:        
>Keywords:       
>Date-Required:
>Class:          sw-bug
>Submitter-Id:   current-users
>Arrival-Date:   Thu May 21 15:20:02 UTC 2009
>Closed-Date:
>Last-Modified:
>Originator:     Eygene Ryabinkin
>Release:        FreeBSD 7.2-STABLE amd64
>Organization:
Code Labs
>Environment:

System: FreeBSD 7.2-STABLE amd64

>Description:

There is remotely exploitable flaw in ntpd when autokey is enabled
(crypto=autokey): [1], [2], [3].

Please, note that there are ports/134756 and ports/134755 that also
contain this fix (and CVE-2009-0159 that was fixed in vendor branch
(r191298) and HEAD (r191302).

>How-To-Repeat:

[1] http://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2009-1252
[2] http://ntp.bkbits.net:8080/ntp-stable/?PAGE=cset&REV=4a1106a4LBCELdfOC7k6lCfqAJcYIA
[3] https://support.ntp.org/bugs/show_bug.cgi?id=1151

>Fix:

The following patch fixes the issue.  It should be applied (at least)
to 7-STABLE and 8-CURRENT.  I had tested the patch -- applies well and
resulting ntpd works fine for me.
--- ntp-cve-2009-1252.diff begins here ---
>From f5e16149ea224cd3acdc4a62516de5b34d38398d Mon Sep 17 00:00:00 2001
From: Eygene Ryabinkin <rea-fbsd at codelabs.ru>
Date: Thu, 21 May 2009 18:56:42 +0400

Patch is taken from
  http://ntp.bkbits.net:8080/ntp-stable/ntpd/ntp_crypto.c?PAGE=diffs&REV=4a110696OZQ8z91qAl4XAZ1367Ynlg
but "applied" with sed (changes are straightforward,
"s/sprintf(statstr,/ snprintf(statstr, NTP_MAXSTRLEN,/"),
since I have no BitKeeper client at hand.

Signed-off-by: Eygene Ryabinkin <rea-fbsd at codelabs.ru>
---
 contrib/ntp/ntpd/ntp_crypto.c |   32 ++++++++++++++++----------------
 1 files changed, 16 insertions(+), 16 deletions(-)

diff --git a/contrib/ntp/ntpd/ntp_crypto.c b/contrib/ntp/ntpd/ntp_crypto.c
index 82afe69..b378b57 100644
--- a/contrib/ntp/ntpd/ntp_crypto.c
+++ b/contrib/ntp/ntpd/ntp_crypto.c
@@ -570,7 +570,7 @@ crypto_recv(
 			peer->issuer = emalloc(vallen + 1);
 			strcpy(peer->issuer, peer->subject);
 			temp32 = (fstamp >> 16) & 0xffff;
-			sprintf(statstr,
+			snprintf(statstr, NTP_MAXSTRLEN,
 			    "flags 0x%x host %s signature %s", fstamp,
 			    peer->subject, OBJ_nid2ln(temp32));
 			record_crypto_stats(&peer->srcadr, statstr);
@@ -636,7 +636,7 @@ crypto_recv(
 			}
 			peer->flash &= ~TEST8;
 			temp32 = cinfo->nid;
-			sprintf(statstr, "cert %s 0x%x %s (%u) fs %u",
+			snprintf(statstr, NTP_MAXSTRLEN, "cert %s 0x%x %s (%u) fs %u",
 			    cinfo->subject, cinfo->flags,
 			    OBJ_nid2ln(temp32), temp32,
 			    ntohl(ep->fstamp));
@@ -685,7 +685,7 @@ crypto_recv(
 			peer->crypto |= CRYPTO_FLAG_VRFY |
 			    CRYPTO_FLAG_PROV;
 			peer->flash &= ~TEST8;
-			sprintf(statstr, "iff fs %u",
+			snprintf(statstr, NTP_MAXSTRLEN, "iff fs %u",
 			    ntohl(ep->fstamp));
 			record_crypto_stats(&peer->srcadr, statstr);
 #ifdef DEBUG
@@ -733,7 +733,7 @@ crypto_recv(
 			peer->crypto |= CRYPTO_FLAG_VRFY |
 			    CRYPTO_FLAG_PROV;
 			peer->flash &= ~TEST8;
-			sprintf(statstr, "gq fs %u",
+			snprintf(statstr, NTP_MAXSTRLEN, "gq fs %u",
 			    ntohl(ep->fstamp));
 			record_crypto_stats(&peer->srcadr, statstr);
 #ifdef DEBUG
@@ -774,7 +774,7 @@ crypto_recv(
 			peer->crypto |= CRYPTO_FLAG_VRFY |
 			    CRYPTO_FLAG_PROV;
 			peer->flash &= ~TEST8;
-			sprintf(statstr, "mv fs %u",
+			snprintf(statstr, NTP_MAXSTRLEN, "mv fs %u",
 			    ntohl(ep->fstamp));
 			record_crypto_stats(&peer->srcadr, statstr);
 #ifdef DEBUG
@@ -828,7 +828,7 @@ crypto_recv(
 			peer->crypto &= ~CRYPTO_FLAG_AUTO;
 			peer->crypto |= CRYPTO_FLAG_AGREE;
 			peer->flash &= ~TEST8;
-			sprintf(statstr, "cook %x ts %u fs %u",
+			snprintf(statstr, NTP_MAXSTRLEN, "cook %x ts %u fs %u",
 			    peer->pcookie, ntohl(ep->tstamp),
 			    ntohl(ep->fstamp));
 			record_crypto_stats(&peer->srcadr, statstr);
@@ -893,7 +893,7 @@ crypto_recv(
 				peer->crypto &= ~CRYPTO_FLAG_AUTO;
 			peer->crypto |= CRYPTO_FLAG_AGREE;
 			peer->flash &= ~TEST8;
-			sprintf(statstr, "cook %x ts %u fs %u",
+			snprintf(statstr, NTP_MAXSTRLEN, "cook %x ts %u fs %u",
 			    peer->pcookie, ntohl(ep->tstamp),
 			    ntohl(ep->fstamp));
 			record_crypto_stats(&peer->srcadr, statstr);
@@ -944,7 +944,7 @@ crypto_recv(
 			peer->pkeyid = bp->key;
 			peer->crypto |= CRYPTO_FLAG_AUTO;
 			peer->flash &= ~TEST8;
-			sprintf(statstr,
+			snprintf(statstr, NTP_MAXSTRLEN,
 			    "auto seq %d key %x ts %u fs %u", bp->seq,
 			    bp->key, ntohl(ep->tstamp),
 			    ntohl(ep->fstamp));
@@ -987,7 +987,7 @@ crypto_recv(
 			peer->crypto |= CRYPTO_FLAG_SIGN;
 			peer->flash &= ~TEST8;
 			temp32 = cinfo->nid;
-			sprintf(statstr, "sign %s 0x%x %s (%u) fs %u",
+			snprintf(statstr, NTP_MAXSTRLEN, "sign %s 0x%x %s (%u) fs %u",
 			    cinfo->issuer, cinfo->flags,
 			    OBJ_nid2ln(temp32), temp32,
 			    ntohl(ep->fstamp));
@@ -1071,7 +1071,7 @@ crypto_recv(
 			crypto_flags |= CRYPTO_FLAG_TAI;
 			peer->crypto |= CRYPTO_FLAG_LEAP;
 			peer->flash &= ~TEST8;
-			sprintf(statstr, "leap %u ts %u fs %u", vallen,
+			snprintf(statstr, NTP_MAXSTRLEN, "leap %u ts %u fs %u", vallen,
 			    ntohl(ep->tstamp), ntohl(ep->fstamp));
 			record_crypto_stats(&peer->srcadr, statstr);
 #ifdef DEBUG
@@ -1127,7 +1127,7 @@ crypto_recv(
 		 * cheerfully ignored, as the message is not sent.
 		 */
 		if (rval > XEVNT_TSP) {
-			sprintf(statstr,
+			snprintf(statstr, NTP_MAXSTRLEN,
 			    "error %x opcode %x ts %u fs %u", rval,
 			    code, tstamp, fstamp);
 			record_crypto_stats(&peer->srcadr, statstr);
@@ -1453,7 +1453,7 @@ crypto_xmit(
 	 */
 	if (rval != XEVNT_OK) {
 		opcode |= CRYPTO_ERROR;
-		sprintf(statstr, "error %x opcode %x", rval, opcode);
+		snprintf(statstr, NTP_MAXSTRLEN, "error %x opcode %x", rval, opcode);
 		record_crypto_stats(srcadr_sin, statstr);
 		report_event(rval, NULL);
 #ifdef DEBUG
@@ -1952,7 +1952,7 @@ crypto_update(void)
 		if (EVP_SignFinal(&ctx, tai_leap.sig, &len, sign_pkey))
 			tai_leap.siglen = htonl(len);
 	}
-	sprintf(statstr, "update ts %u", ntohl(hostval.tstamp)); 
+	snprintf(statstr, NTP_MAXSTRLEN, "update ts %u", ntohl(hostval.tstamp)); 
 	record_crypto_stats(NULL, statstr);
 #ifdef DEBUG
 	if (debug)
@@ -3606,7 +3606,7 @@ crypto_key(
 	 */
 	if ((ptr = strrchr(linkname, '\n')) != NULL)
 		*ptr = '\0'; 
-	sprintf(statstr, "%s mod %d", &linkname[2],
+	snprintf(statstr, NTP_MAXSTRLEN, "%s mod %d", &linkname[2],
 	    EVP_PKEY_size(pkey) * 8);
 	record_crypto_stats(NULL, statstr);
 #ifdef DEBUG
@@ -3715,7 +3715,7 @@ crypto_cert(
 
 	if ((ptr = strrchr(linkname, '\n')) != NULL)
 		*ptr = '\0'; 
-	sprintf(statstr, "%s 0x%x len %lu", &linkname[2], ret->flags,
+	snprintf(statstr, NTP_MAXSTRLEN, "%s 0x%x len %lu", &linkname[2], ret->flags,
 	    len);
 	record_crypto_stats(NULL, statstr);
 #ifdef DEBUG
@@ -3832,7 +3832,7 @@ crypto_tai(
 	for (j = 0; j < i; j++)
 		*ptr++ = htonl(leapsec[j]);
 	crypto_flags |= CRYPTO_FLAG_TAI;
-	sprintf(statstr, "%s fs %u leap %u len %u", cp, fstamp,
+	snprintf(statstr, NTP_MAXSTRLEN, "%s fs %u leap %u len %u", cp, fstamp,
 	   leapsec[--j], len);
 	record_crypto_stats(NULL, statstr);
 #ifdef DEBUG
-- 
1.6.3.1
--- ntp-cve-2009-1252.diff ends here ---
>Release-Note:
>Audit-Trail:
>Unformatted:


More information about the freebsd-bugs mailing list