Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/netbsd-1-6]: src/dist/bind/lib/resolv Pull up revision 1.4 (requested by...



details:   https://anonhg.NetBSD.org/src/rev/504954fe854a
branches:  netbsd-1-6
changeset: 528237:504954fe854a
user:      lukem <lukem%NetBSD.org@localhost>
date:      Fri Jun 28 11:57:45 2002 +0000

description:
Pull up revision 1.4 (requested by itojun in ticket #387):
Update to BIND 8.3.3.  Fixes buffer overrun in resolver code.

diffstat:

 dist/bind/lib/resolv/res_findzonecut.c |  171 ++++++++++++++++-----
 dist/bind/lib/resolv/res_init.c        |  251 ++++++++++++++++++++++++++++++--
 2 files changed, 363 insertions(+), 59 deletions(-)

diffs (truncated from 738 to 300 lines):

diff -r 0a7c15e3b2f6 -r 504954fe854a dist/bind/lib/resolv/res_findzonecut.c
--- a/dist/bind/lib/resolv/res_findzonecut.c    Fri Jun 28 11:57:37 2002 +0000
+++ b/dist/bind/lib/resolv/res_findzonecut.c    Fri Jun 28 11:57:45 2002 +0000
@@ -1,7 +1,7 @@
-/*     $NetBSD: res_findzonecut.c,v 1.3 2001/01/27 07:22:05 itojun Exp $       */
+/*     $NetBSD: res_findzonecut.c,v 1.3.2.1 2002/06/28 11:57:45 lukem Exp $    */
 
 #if !defined(lint) && !defined(SABER)
-static const char rcsid[] = "Id: res_findzonecut.c,v 8.12 2000/11/22 01:20:44 marka Exp";
+static const char rcsid[] = "Id: res_findzonecut.c,v 8.16 2002/04/12 06:27:46 marka Exp";
 #endif /* not lint */
 
 /*
@@ -36,7 +36,6 @@
 #include <errno.h>
 #include <limits.h>
 #include <netdb.h>
-#include <resolv.h>
 #include <stdarg.h>
 #include <stdio.h>
 #include <stdlib.h>
@@ -46,48 +45,52 @@
 
 #include "port_after.h"
 
+#include <resolv.h>
+
 /* Data structures. */
 
 typedef struct rr_a {
        LINK(struct rr_a)       link;
-       struct in_addr          addr;
+       union res_sockaddr_union                addr;
 } rr_a;
 typedef LIST(rr_a) rrset_a;
 
 typedef struct rr_ns {
        LINK(struct rr_ns)      link;
        const char *            name;
+       int                     have_v4;
+       int                     have_v6;
        rrset_a                 addrs;
 } rr_ns;
 typedef LIST(rr_ns) rrset_ns;
 
 /* Forward. */
 
-static int     satisfy(res_state,
-                       const char *, rrset_ns *, struct in_addr *, int);
-static int     add_addrs(res_state, rr_ns *, struct in_addr *, int);
-static int     get_soa(res_state, const char *, ns_class,
+static int     satisfy(res_state, const char *, rrset_ns *,
+                       union res_sockaddr_union *, int);
+static int     add_addrs(res_state, rr_ns *,
+                         union res_sockaddr_union *, int);
+static int     get_soa(res_state, const char *, ns_class, int,
                        char *, size_t, char *, size_t,
                        rrset_ns *);
-static int     get_ns(res_state, const char *, ns_class, rrset_ns *);
-static int     get_glue(res_state, ns_class, rrset_ns *);
+static int     get_ns(res_state, const char *, ns_class, int, rrset_ns *);
+static int     get_glue(res_state, ns_class, int, rrset_ns *);
 static int     save_ns(res_state, ns_msg *, ns_sect,
-                       const char *, ns_class, rrset_ns *);
+                       const char *, ns_class, int, rrset_ns *);
 static int     save_a(res_state, ns_msg *, ns_sect,
-                      const char *, ns_class, rrset_a *);
+                      const char *, ns_class, int, rr_ns *);
 static void    free_nsrrset(rrset_ns *);
 static void    free_nsrr(rrset_ns *, rr_ns *);
 static rr_ns * find_ns(rrset_ns *, const char *);
 static int     do_query(res_state, const char *, ns_class, ns_type,
                         u_char *, ns_msg *);
-static void    dprintf(const char *, ...) 
-     __attribute__((__format__(__printf__, 1, 2)));
+static void    res_dprintf(const char *, ...) ISC_FORMAT_PRINTF(1, 2);
 
 /* Macros. */
 
 #define DPRINTF(x) do {\
                int save_errno = errno; \
-               if ((statp->options & RES_DEBUG) != 0) dprintf x; \
+               if ((statp->options & RES_DEBUG) != 0) res_dprintf x; \
                errno = save_errno; \
        } while (0)
 
@@ -148,7 +151,32 @@
 
 int
 res_findzonecut(res_state statp, const char *dname, ns_class class, int opts,
-               char *zname, size_t zsize, struct in_addr *addrs, int naddrs)
+               char *zname, size_t zsize, struct in_addr *addrs, int naddrs) {
+       int result, i;
+       union res_sockaddr_union *u;
+
+       
+       opts |= RES_IPV4ONLY;
+       opts &= ~RES_IPV6ONLY;
+
+       u = calloc(naddrs, sizeof(*u));
+       if (u == NULL)
+               return(-1);
+
+       result = res_findzonecut2(statp, dname, class, opts, zname, zsize,
+                                 u, naddrs);
+
+       for (i = 0; i < result; i++) {
+               addrs[i] = u[i].sin.sin_addr;
+       }
+       free(u);
+       return (result);
+}
+
+int
+res_findzonecut2(res_state statp, const char *dname, ns_class class, int opts,
+                char *zname, size_t zsize, union res_sockaddr_union *addrs,
+                int naddrs)
 {
        char mname[NS_MAXDNAME];
        u_long save_pfcode;
@@ -164,20 +192,20 @@
        INIT_LIST(nsrrs);
 
        DPRINTF(("get the soa, and see if it has enough glue"));
-       if ((n = get_soa(statp, dname, class, zname, zsize,
+       if ((n = get_soa(statp, dname, class, opts, zname, zsize,
                         mname, sizeof mname, &nsrrs)) < 0 ||
            ((opts & RES_EXHAUSTIVE) == 0 &&
             (n = satisfy(statp, mname, &nsrrs, addrs, naddrs)) > 0))
                goto done;
 
        DPRINTF(("get the ns rrset and see if it has enough glue"));
-       if ((n = get_ns(statp, zname, class, &nsrrs)) < 0 ||
+       if ((n = get_ns(statp, zname, class, opts, &nsrrs)) < 0 ||
            ((opts & RES_EXHAUSTIVE) == 0 &&
             (n = satisfy(statp, mname, &nsrrs, addrs, naddrs)) > 0))
                goto done;
 
        DPRINTF(("get the missing glue and see if it's finally enough"));
-       if ((n = get_glue(statp, class, &nsrrs)) >= 0)
+       if ((n = get_glue(statp, class, opts, &nsrrs)) >= 0)
                n = satisfy(statp, mname, &nsrrs, addrs, naddrs);
 
  done:
@@ -190,8 +218,8 @@
 /* Private. */
 
 static int
-satisfy(res_state statp,
-       const char *mname, rrset_ns *nsrrsp, struct in_addr *addrs, int naddrs)
+satisfy(res_state statp, const char *mname, rrset_ns *nsrrsp,
+       union res_sockaddr_union *addrs, int naddrs)
 {
        rr_ns *nsrr;
        int n, x;
@@ -218,7 +246,9 @@
 }
 
 static int
-add_addrs(res_state statp, rr_ns *nsrr, struct in_addr *addrs, int naddrs) {
+add_addrs(res_state statp, rr_ns *nsrr,
+         union res_sockaddr_union *addrs, int naddrs)
+{
        rr_a *arr;
        int n = 0;
 
@@ -234,7 +264,7 @@
 }
 
 static int
-get_soa(res_state statp, const char *dname, ns_class class,
+get_soa(res_state statp, const char *dname, ns_class class, int opts,
        char *zname, size_t zsize, char *mname, size_t msize,
        rrset_ns *nsrrsp)
 {
@@ -335,7 +365,7 @@
                                return (-1);
                        }
                        if (save_ns(statp, &msg, ns_s_ns,
-                                   zname, class, nsrrsp) < 0) {
+                                   zname, class, opts, nsrrsp) < 0) {
                                DPRINTF(("get_soa: save_ns failed"));
                                return (-1);
                        }
@@ -362,7 +392,9 @@
 }
 
 static int
-get_ns(res_state statp, const char *zname, ns_class class, rrset_ns *nsrrsp) {
+get_ns(res_state statp, const char *zname, ns_class class, int opts,
+      rrset_ns *nsrrsp)
+{
        u_char resp[NS_PACKETSZ];
        ns_msg msg;
        int n;
@@ -376,7 +408,7 @@
        }
 
        /* Remember the NS RRs and associated A RRs that came back. */
-       if (save_ns(statp, &msg, ns_s_an, zname, class, nsrrsp) < 0) {
+       if (save_ns(statp, &msg, ns_s_an, zname, class, opts, nsrrsp) < 0) {
                DPRINTF(("get_ns save_ns('%s', %s) failed",
                         zname, p_class(class)));
                return (-1);
@@ -386,7 +418,7 @@
 }
 
 static int
-get_glue(res_state statp, ns_class class, rrset_ns *nsrrsp) {
+get_glue(res_state statp, ns_class class, int opts, rrset_ns *nsrrsp) {
        rr_ns *nsrr, *nsrr_n;
 
        /* Go and get the A RRs for each empty NS RR on our list. */
@@ -397,7 +429,7 @@
 
                nsrr_n = NEXT(nsrr, link);
 
-               if (EMPTY(nsrr->addrs)) {
+               if (!nsrr->have_v4) {
                        n = do_query(statp, nsrr->name, class, ns_t_a,
                                     resp, &msg);
                        if (n < 0) {
@@ -411,17 +443,39 @@
                                         nsrr->name, p_class(class)));
                        }
                        if (save_a(statp, &msg, ns_s_an, nsrr->name, class,
-                                  &nsrr->addrs) < 0) {
+                                  opts, nsrr) < 0) {
                                DPRINTF(("get_glue: save_r('%s', %s) failed",
                                         nsrr->name, p_class(class)));
                                return (-1);
                        }
-                       /* If it's still empty, it's just chaff. */
-                       if (EMPTY(nsrr->addrs)) {
-                               DPRINTF(("get_glue: removing empty '%s' NS",
-                                        nsrr->name));
-                               free_nsrr(nsrrsp, nsrr);
+               }
+
+               if (!nsrr->have_v6) {
+                       n = do_query(statp, nsrr->name, class, ns_t_aaaa,
+                                    resp, &msg);
+                       if (n < 0) {
+                               DPRINTF(("get_glue: do_query('%s', %s') failed",
+                                        nsrr->name, p_class(class)));
+                               return (-1);
                        }
+                       if (n > 0) {
+                               DPRINTF((
+                       "get_glue: do_query('%s', %s') CNAME or DNAME found",
+                                        nsrr->name, p_class(class)));
+                       }
+                       if (save_a(statp, &msg, ns_s_an, nsrr->name, class,
+                                  opts, nsrr) < 0) {
+                               DPRINTF(("get_glue: save_r('%s', %s) failed",
+                                        nsrr->name, p_class(class)));
+                               return (-1);
+                       }
+               }
+
+               /* If it's still empty, it's just chaff. */
+               if (EMPTY(nsrr->addrs)) {
+                       DPRINTF(("get_glue: removing empty '%s' NS",
+                                nsrr->name));
+                       free_nsrr(nsrrsp, nsrr);
                }
        }
        return (0);
@@ -429,7 +483,7 @@
 
 static int
 save_ns(res_state statp, ns_msg *msg, ns_sect sect,
-       const char *owner, ns_class class,
+       const char *owner, ns_class class, int opts,
        rrset_ns *nsrrsp)
 {
        int i;
@@ -474,10 +528,12 @@
                        }
                        INIT_LINK(nsrr, link);
                        INIT_LIST(nsrr->addrs);
+                       nsrr->have_v4 = 0;
+                       nsrr->have_v6 = 0;
                        APPEND(*nsrrsp, nsrr, link);
                }
                if (save_a(statp, msg, ns_s_ar,
-                          nsrr->name, class, &nsrr->addrs) < 0) {
+                          nsrr->name, class, opts, nsrr) < 0) {
                        DPRINTF(("save_ns: save_r('%s', %s) failed",
                                 nsrr->name, p_class(class)));
                        return (-1);
@@ -488,8 +544,8 @@
 
 static int
 save_a(res_state statp, ns_msg *msg, ns_sect sect,
-       const char *owner, ns_class class,
-       rrset_a *arrsp)
+       const char *owner, ns_class class, int opts,
+       rr_ns *nsrr)
 {



Home | Main Index | Thread Index | Old Index