diff options
author | Todd C. Miller <millert@cvs.openbsd.org> | 2002-11-14 02:54:23 +0000 |
---|---|---|
committer | Todd C. Miller <millert@cvs.openbsd.org> | 2002-11-14 02:54:23 +0000 |
commit | 8c40cc2c58bce394e853e8cfab1dde400d093b18 (patch) | |
tree | cc612ff5f9dfc9e6f48846269c52e4670ce930e3 | |
parent | 0804bd02c2292c096d688f566129de14c9141b3a (diff) |
Sync with bind-4.9.11-REL; fixes the problems listed in:
http://www.isc.org/products/BIND/bind-security.html
including a buffer overflow that could lead to remote code execution.
-rw-r--r-- | usr.sbin/named/Makefile | 4 | ||||
-rw-r--r-- | usr.sbin/named/libresolv/getnetnamadr.c | 70 | ||||
-rw-r--r-- | usr.sbin/named/named/db_defs.h | 4 | ||||
-rw-r--r-- | usr.sbin/named/named/ns_ncache.c | 17 | ||||
-rw-r--r-- | usr.sbin/named/named/ns_req.c | 6 | ||||
-rw-r--r-- | usr.sbin/named/named/ns_resp.c | 22 |
6 files changed, 74 insertions, 49 deletions
diff --git a/usr.sbin/named/Makefile b/usr.sbin/named/Makefile index 140d0c1ff99..f68f8346b49 100644 --- a/usr.sbin/named/Makefile +++ b/usr.sbin/named/Makefile @@ -1,4 +1,4 @@ -# $OpenBSD: Makefile,v 1.12 2002/11/02 02:13:18 millert Exp $ +# $OpenBSD: Makefile,v 1.13 2002/11/14 02:54:22 millert Exp $ SUBDIR= named named-xfer ndc reload restart dig nslookup \ host dnsquery @@ -6,6 +6,6 @@ SUBDIR= named named-xfer ndc reload restart dig nslookup \ SUBDIR+= doc/bog .endif -VER= 4.9.9-REL +VER= 4.9.11-REL .include <bsd.subdir.mk> diff --git a/usr.sbin/named/libresolv/getnetnamadr.c b/usr.sbin/named/libresolv/getnetnamadr.c index 11049055890..747297aa95b 100644 --- a/usr.sbin/named/libresolv/getnetnamadr.c +++ b/usr.sbin/named/libresolv/getnetnamadr.c @@ -1,4 +1,4 @@ -/* $OpenBSD: getnetnamadr.c,v 1.4 2002/06/26 06:08:17 itojun Exp $ */ +/* $OpenBSD: getnetnamadr.c,v 1.5 2002/11/14 02:54:22 millert Exp $ */ /* Copyright (c) 1993 Carlos Leandro and Rui Salgueiro * Dep. Matematica Universidade de Coimbra, Portugal, Europe @@ -46,7 +46,7 @@ static char sccsid[] = "@(#)getnetbyaddr.c 8.1 (Berkeley) 6/4/93"; static char sccsid_[] = "from getnetnamadr.c 1.4 (Coimbra) 93/06/03"; static char rcsid[] = "$From: getnetnamadr.c,v 8.8 1997/06/01 20:34:37 vixie Exp $"; #else -static char rcsid[] = "$OpenBSD: getnetnamadr.c,v 1.4 2002/06/26 06:08:17 itojun Exp $"; +static char rcsid[] = "$OpenBSD: getnetnamadr.c,v 1.5 2002/11/14 02:54:22 millert Exp $"; #endif #endif /* LIBC_SCCS and not lint */ @@ -105,10 +105,11 @@ getnetanswer(answer, anslen, net_i) register int n; u_char *eom; int type, class, ancount, qdcount, haveanswer, i, nchar; - char aux1[30], aux2[30], ans[30], *in, *st, *pauxt, *bp, **ap, - *paux1 = &aux1[0], *paux2 = &aux2[0], flag = 0, *ep; -static struct netent net_entry; -static char *net_aliases[MAXALIASES], netbuf[PACKETSZ]; + char aux1[30], aux2[30], *in, *st, *pauxt, *bp, **ap, + *paux1 = &aux1[0], *paux2 = &aux2[0], *ep; + static struct netent net_entry; + static char *net_aliases[MAXALIASES], netbuf[PACKETSZ]; + static char ans[MAXDNAME]; /* * find first satisfactory answer @@ -138,8 +139,14 @@ static char *net_aliases[MAXALIASES], netbuf[PACKETSZ]; h_errno = TRY_AGAIN; return (NULL); } - while (qdcount-- > 0) - cp += __dn_skipname(cp, eom) + QFIXEDSZ; + while (qdcount-- > 0) { + n = __dn_skipname(cp, eom); + if (n < 0 || (cp + n + QFIXEDSZ) > eom) { + h_errno = NO_RECOVERY; + return(NULL); + } + cp += n + QFIXEDSZ; + } ap = net_aliases; *ap = NULL; net_entry.n_aliases = net_aliases; @@ -150,7 +157,7 @@ static char *net_aliases[MAXALIASES], netbuf[PACKETSZ]; break; cp += n; ans[0] = '\0'; - (void)strcpy(&ans[0], bp); + (void)strcpy(ans, bp); GETSHORT(type, cp); GETSHORT(class, cp); cp += INT32SZ; /* TTL */ @@ -162,11 +169,13 @@ static char *net_aliases[MAXALIASES], netbuf[PACKETSZ]; return (NULL); } cp += n; - *ap++ = bp; - bp += strlen(bp) + 1; - net_entry.n_addrtype = - (class == C_IN) ? AF_INET : AF_UNSPEC; - haveanswer++; + if ((ap + 2) < &net_aliases[MAXALIASES]) { + *ap++ = bp; + bp += strlen(bp) + 1; + net_entry.n_addrtype = + (class == C_IN) ? AF_INET : AF_UNSPEC; + haveanswer++; + } } } if (haveanswer) { @@ -177,26 +186,33 @@ static char *net_aliases[MAXALIASES], netbuf[PACKETSZ]; net_entry.n_net = 0L; break; case BYNAME: - in = *net_entry.n_aliases; - net_entry.n_name = &ans[0]; + ap = net_entry.n_aliases; + next_alias: + in = *ap++; + if (in == NULL) { + h_errno = HOST_NOT_FOUND; + return (NULL); + } + net_entry.n_name = ans; aux2[0] = '\0'; for (i = 0; i < 4; i++) { for (st = in, nchar = 0; - *st != '.'; + isdigit((unsigned char)*st); st++, nchar++) ; - if (nchar != 1 || *in != '0' || flag) { - flag = 1; - (void)strncpy(paux1, - (i==0) ? in : in-1, - (i==0) ?nchar : nchar+1); - paux1[(i==0) ? nchar : nchar+1] = '\0'; - pauxt = paux2; - paux2 = strcat(paux1, paux2); - paux1 = pauxt; - } + if (*st != '.' || nchar == 0 || nchar > 3) + goto next_alias; + if (i != 0) + nchar++; + (void)strncpy(paux1, in, nchar); + paux1[nchar] = '\0'; + pauxt = paux2; + paux2 = strcat(paux1, paux2); + paux1 = pauxt; in = ++st; } + if (strcasecmp(in, "IN-ADDR.ARPA") != 0) + goto next_alias; net_entry.n_net = inet_network(paux2); break; } diff --git a/usr.sbin/named/named/db_defs.h b/usr.sbin/named/named/db_defs.h index 50a7568c959..ddd497d75ba 100644 --- a/usr.sbin/named/named/db_defs.h +++ b/usr.sbin/named/named/db_defs.h @@ -1,4 +1,4 @@ -/* $OpenBSD: db_defs.h,v 1.3 1998/05/22 00:47:31 millert Exp $ */ +/* $OpenBSD: db_defs.h,v 1.4 2002/11/14 02:54:22 millert Exp $ */ /* * from db.h 4.16 (Berkeley) 6/1/90 @@ -68,7 +68,7 @@ #define INVHASHSZ 919 /* size of inverse hash table */ /* max length of data in RR data field */ -#define MAXDATA 2048 +#define MAXDATA (3*MAXDNAME + 5*INT32SZ) #define DB_ROOT_TIMBUF 3600 #define TIMBUF 300 diff --git a/usr.sbin/named/named/ns_ncache.c b/usr.sbin/named/named/ns_ncache.c index 04da6fe784a..3fa70433f16 100644 --- a/usr.sbin/named/named/ns_ncache.c +++ b/usr.sbin/named/named/ns_ncache.c @@ -1,4 +1,4 @@ -/* $OpenBSD: ns_ncache.c,v 1.4 1998/05/22 07:09:17 millert Exp $ */ +/* $OpenBSD: ns_ncache.c,v 1.5 2002/11/14 02:54:22 millert Exp $ */ /************************************************************************** * ns_ncache.c @@ -81,8 +81,8 @@ cache_n_resp(msg, msglen) u_int16_t atype; u_char *tp = cp; u_char *cp1; - u_char data[MAXDNAME*2 + INT32SZ*5]; - size_t len = sizeof data; + u_char data[MAXDATA]; + u_char *eod = data + sizeof(data); /* we store NXDOMAIN as T_SOA regardless of the query type */ if (hp->rcode == NXDOMAIN) @@ -109,7 +109,7 @@ cache_n_resp(msg, msglen) rdatap = tp; /* origin */ - n = dn_expand(msg, eom, tp, (char*)data, len); + n = dn_expand(msg, eom, tp, (char*)data, eod - data); if (n < 0) { dprintf(3, (ddt, "ncache: form error 2\n")); return; @@ -117,9 +117,8 @@ cache_n_resp(msg, msglen) tp += n; n = strlen((char*)data) + 1; cp1 = data + n; - len -= n; /* mail */ - n = dn_expand(msg, msg + msglen, tp, (char*)cp1, len); + n = dn_expand(msg, msg + msglen, tp, (char*)cp1, eod - cp1); if (n < 0) { dprintf(3, (ddt, "ncache: form error 2\n")); return; @@ -127,20 +126,20 @@ cache_n_resp(msg, msglen) tp += n; n = strlen((char*)cp1) + 1; cp1 += n; - len -= n; n = 5 * INT32SZ; + if (n > (eod - cp1)) /* Can't happen. See MAXDATA. */ + return; BOUNDS_CHECK(tp, n); bcopy(tp, cp1, n); /* serial, refresh, retry, expire, min */ cp1 += n; - len -= n; tp += n; if (tp != rdatap + dlen) { dprintf(3, (ddt, "ncache: form error 2\n")); return; } /* store the zone of the soa record */ - n = dn_expand(msg, msg + msglen, cp, (char*)cp1, len); + n = dn_expand(msg, msg + msglen, cp, (char*)cp1, eod - cp1); if (n < 0) { dprintf(3, (ddt, "ncache: form error 2\n")); return; diff --git a/usr.sbin/named/named/ns_req.c b/usr.sbin/named/named/ns_req.c index 8d3501ea85b..f3806400e14 100644 --- a/usr.sbin/named/named/ns_req.c +++ b/usr.sbin/named/named/ns_req.c @@ -1,11 +1,11 @@ -/* $OpenBSD: ns_req.c,v 1.10 2002/05/28 01:23:13 deraadt Exp $ */ +/* $OpenBSD: ns_req.c,v 1.11 2002/11/14 02:54:22 millert Exp $ */ #if !defined(lint) && !defined(SABER) #if 0 static char sccsid[] = "@(#)ns_req.c 4.47 (Berkeley) 7/1/91"; static char rcsid[] = "$From: ns_req.c,v 8.30 1998/05/11 04:19:45 vixie Exp $"; #else -static char rcsid[] = "$OpenBSD: ns_req.c,v 1.10 2002/05/28 01:23:13 deraadt Exp $"; +static char rcsid[] = "$OpenBSD: ns_req.c,v 1.11 2002/11/14 02:54:22 millert Exp $"; #endif #endif /* not lint */ @@ -1526,7 +1526,7 @@ make_rr(name, dp, buf, buflen, doadd) /* first just copy over the type_covered, algorithm, */ /* labels, orig ttl, two timestamps, and the footprint */ - if ((dp->d_size - 18) > buflen) + if (buflen < 18) goto cleanup; bcopy( cp1, cp, 18 ); cp += 18; diff --git a/usr.sbin/named/named/ns_resp.c b/usr.sbin/named/named/ns_resp.c index ff184f50fd1..650e2963292 100644 --- a/usr.sbin/named/named/ns_resp.c +++ b/usr.sbin/named/named/ns_resp.c @@ -1,11 +1,11 @@ -/* $OpenBSD: ns_resp.c,v 1.8 2002/06/09 01:27:29 kjell Exp $ */ +/* $OpenBSD: ns_resp.c,v 1.9 2002/11/14 02:54:22 millert Exp $ */ #if !defined(lint) && !defined(SABER) #if 0 static char sccsid[] = "@(#)ns_resp.c 4.65 (Berkeley) 3/3/91"; static char rcsid[] = "$From: ns_resp.c,v 8.41 1998/04/07 04:59:45 vixie Exp $"; #else -static char rcsid[] = "$OpenBSD: ns_resp.c,v 1.8 2002/06/09 01:27:29 kjell Exp $"; +static char rcsid[] = "$OpenBSD: ns_resp.c,v 1.9 2002/11/14 02:54:22 millert Exp $"; #endif #endif /* not lint */ @@ -1676,7 +1676,7 @@ rrextract(msg, msglen, rrp, dpp, dname, namelen, tnamep) * to BOUNDS_CHECK() here. */ cp1 += (n = strlen((char *)cp1) + 1); - n1 = sizeof(data) - n; + n1 = sizeof(data) - n - INT16SZ; n = dn_expand(msg, eom, cp, (char *)cp1, n1); if (n < 0) { hp->rcode = FORMERR; @@ -1694,7 +1694,7 @@ rrextract(msg, msglen, rrp, dpp, dname, namelen, tnamep) break; case T_SIG: { - u_long origTTL, exptime, signtime, timetilexp, now; + u_int32_t origTTL, exptime, signtime, timetilexp, now; /* Check signature time, expiration, and adjust TTL. */ /* This code is similar to that in db_load.c. */ @@ -1715,8 +1715,18 @@ rrextract(msg, msglen, rrp, dpp, dname, namelen, tnamep) ttl = origTTL; } + /* + * Check that expire and signature times are internally + * consistant. + */ + if (!SEQ_GT(exptime, signtime) && exptime != signtime) { + dprintf(3, (ddt, + "ignoring SIG: signature expires before it was signed")); + return ((cp - rrp) + dlen); + } + /* Don't let bogus signers "sign" in the future. */ - if (signtime > now) { + if (SEQ_GT(signtime, now)) { dprintf(3, (ddt, "ignoring SIG: signature date %s is in the future\n", p_secstodate (signtime))); @@ -1724,7 +1734,7 @@ rrextract(msg, msglen, rrp, dpp, dname, namelen, tnamep) } /* Ignore received SIG RR's that are already expired. */ - if (exptime <= now) { + if (SEQ_GT(exptime, now)) { dprintf(3, (ddt, "ignoring SIG: expiration %s is in the past\n", p_secstodate (exptime))); |