Update.
authorUlrich Drepper <drepper@redhat.com>
Fri, 31 May 2002 07:54:02 +0000 (07:54 +0000)
committerUlrich Drepper <drepper@redhat.com>
Fri, 31 May 2002 07:54:02 +0000 (07:54 +0000)
2002-05-21  Jakub Jelinek  <jakub@redhat.com>

* resolv/resolv.h (struct __res_state): Remove unused nstimes.
Add nsmap.
* resolv/res_init.c (__res_vinit): Initialize nsmap array.
Remove nstimes setting.
(res_nclose): Check all MAXNS nameservers with non-NULL nsaddrs.
* resolv/res_send.c (res_nsend): Don't close unconditionally if
there is mix of IPv6 and IPv4 nameservers.
Use nsmap array to find free slots and preserve nameserver ordering.
Fix RES_ROTATE.

ChangeLog
resolv/res_init.c
resolv/res_send.c
resolv/resolv.h

index 56b6c17..f6efc19 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,15 @@
+2002-05-21  Jakub Jelinek  <jakub@redhat.com>
+
+       * resolv/resolv.h (struct __res_state): Remove unused nstimes.
+       Add nsmap.
+       * resolv/res_init.c (__res_vinit): Initialize nsmap array.
+       Remove nstimes setting.
+       (res_nclose): Check all MAXNS nameservers with non-NULL nsaddrs.
+       * resolv/res_send.c (res_nsend): Don't close unconditionally if
+       there is mix of IPv6 and IPv4 nameservers.
+       Use nsmap array to find free slots and preserve nameserver ordering.
+       Fix RES_ROTATE.
+
 2002-05-30  Ulrich Drepper  <drepper@redhat.com>
 
        * sysdeps/unix/sysv/linux/sys/sendfile.h: It is now possible to
index bb66b02..f561382 100644 (file)
@@ -182,8 +182,10 @@ __res_vinit(res_state statp, int preinit) {
        statp->_u._ext.nscount = 0;
 #ifdef _LIBC
        statp->_u._ext.nscount6 = 0;
-       for (n = 0; n < MAXNS; n++)
-           statp->_u._ext.nsaddrs[n] = NULL;
+       for (n = 0; n < MAXNS; n++) {
+               statp->_u._ext.nsaddrs[n] = NULL;
+               statp->_u._ext.nsmap[n] = MAXNS;
+       }
 #endif
 
        /* Allow user to override the local domain definition */
@@ -323,8 +325,8 @@ __res_vinit(res_state statp, int preinit) {
                                 sa6->sin6_family = AF_INET6;
                                 sa6->sin6_port = htons(NAMESERVER_PORT);
                                statp->_u._ext.nsaddrs[nservall] = sa6;
-                               statp->_u._ext.nstimes[nservall] = RES_MAXTIME;
                                statp->_u._ext.nssocks[nservall] = -1;
+                               statp->_u._ext.nsmap[nservall] = MAXNS + 1;
                                 nservall++;
                             }
                         }
@@ -537,16 +539,14 @@ res_nclose(res_state statp) {
                statp->_flags &= ~(RES_F_VC | RES_F_CONN);
        }
 #ifdef _LIBC
-       for (ns = 0; ns < statp->_u._ext.nscount + statp->_u._ext.nscount6;
-            ns++)
+       for (ns = 0; ns < MAXNS; ns++)
 #else
        for (ns = 0; ns < statp->_u._ext.nscount; ns++)
 #endif
-       {
-               if (statp->_u._ext.nssocks[ns] != -1) {
+               if (statp->_u._ext.nsaddrs[ns]
+                   && statp->_u._ext.nssocks[ns] != -1) {
                        (void) __close(statp->_u._ext.nssocks[ns]);
                        statp->_u._ext.nssocks[ns] = -1;
                }
-       }
        statp->_u._ext.nsinit = 0;
 }
index 751a550..a163d06 100644 (file)
@@ -400,12 +400,15 @@ res_nsend(res_state statp,
                if (EXT(statp).nscount != statp->nscount)
                        needclose++;
                else
-                       for (ns = 0; ns < statp->nscount; ns++)
 #ifdef _LIBC
-                               if (!sock_eq((struct sockaddr_in6 *)
-                                            &statp->nsaddr_list[ns],
-                                            EXT(statp).nsaddrs[ns]))
+                       for (ns = 0; ns < MAXNS; ns++) {
+                               unsigned int map = EXT(statp).nsmap[ns];
+                               if (map < MAXNS
+                                   && !sock_eq((struct sockaddr_in6 *)
+                                               &statp->nsaddr_list[map],
+                                               EXT(statp).nsaddrs[ns]))
 #else
+                       for (ns = 0; ns < statp->nscount; ns++) {
                                if (!sock_eq(&statp->nsaddr_list[ns],
                                             &EXT(statp).nsaddrs[ns]))
 #endif
@@ -413,6 +416,7 @@ res_nsend(res_state statp,
                                        needclose++;
                                        break;
                                }
+                       }
                if (needclose)
                        res_nclose(statp);
        }
@@ -422,20 +426,34 @@ res_nsend(res_state statp,
         */
        if (EXT(statp).nsinit == 0) {
 #ifdef _LIBC
-               n = 0;
-#endif
-               for (ns = 0; ns < statp->nscount; ns++) {
-#ifdef _LIBC
-                       /* find a hole */
-                       while ((n < MAXNS) &&
-                           (EXT(statp).nsaddrs[n] != NULL) &&
-                           (EXT(statp).nsaddrs[n]->sin6_family == AF_INET6) &&
-                           !IN6_IS_ADDR_V4MAPPED(
-                               &EXT(statp).nsaddrs[n]->sin6_addr))
-                               n++;
-                       if (n == MAXNS)
-                               break;
-
+               unsigned char map[MAXNS];
+
+               memset (map, MAXNS, sizeof (map));
+               for (n = 0; n < MAXNS; n++) {
+                       ns = EXT(statp).nsmap[n];
+                       if (ns < statp->nscount)
+                               map[ns] = n;
+                       else if (ns < MAXNS) {
+                               free(EXT(statp).nsaddrs[n]);
+                               EXT(statp).nsaddrs[n] = NULL;
+                               EXT(statp).nsmap[n] = MAXNS;
+                       }
+               }
+               n = statp->nscount;
+               if (statp->nscount > EXT(statp).nscount)
+                       for (n = EXT(statp).nscount, ns = 0;
+                            n < statp->nscount; n++) {
+                               while (ns < MAXNS
+                                      && EXT(statp).nsmap[ns] != MAXNS)
+                                       ns++;
+                               if (ns == MAXNS)
+                                       break;
+                               EXT(statp).nsmap[ns] = n;
+                               map[n] = ns++;
+                       }
+               EXT(statp).nscount = n;
+               for (ns = 0; ns < EXT(statp).nscount; ns++) {
+                       n = map[ns];
                        if (EXT(statp).nsaddrs[n] == NULL)
                                EXT(statp).nsaddrs[n] =
                                    malloc(sizeof (struct sockaddr_in6));
@@ -443,31 +461,18 @@ res_nsend(res_state statp,
                                memcpy(EXT(statp).nsaddrs[n],
                                       &statp->nsaddr_list[ns],
                                       sizeof (struct sockaddr_in));
-                               EXT(statp).nstimes[n] = RES_MAXTIME;
                                EXT(statp).nssocks[n] = -1;
                                n++;
                        }
+               }
 #else
+               for (ns = 0; ns < statp->nscount; ns++) {
                        EXT(statp).nsaddrs[ns] = statp->nsaddr_list[ns];
-                       EXT(statp).nstimes[ns] = RES_MAXTIME;
                        EXT(statp).nssocks[ns] = -1;
-#endif
-               }
-               EXT(statp).nscount = statp->nscount;
-               EXT(statp).nsinit = 1;
-#ifdef _LIBC
-               /* If holes left, free memory and set to NULL */
-               while (n < MAXNS) {
-                       if ((EXT(statp).nsaddrs[n] != NULL) &&
-                           ((EXT(statp).nsaddrs[n]->sin6_family != AF_INET6)
-                           || IN6_IS_ADDR_V4MAPPED(
-                                  &EXT(statp).nsaddrs[n]->sin6_addr))) {
-                               free(EXT(statp).nsaddrs[n]);
-                               EXT(statp).nsaddrs[n] = NULL;
-                       }
-                       n++;
                }
+               EXT(statp).nscount = ns;
 #endif
+               EXT(statp).nsinit = 1;
        }
 
        /*
@@ -478,12 +483,28 @@ res_nsend(res_state statp,
            (statp->options & RES_BLAST) == 0) {
 #ifdef _LIBC
                struct sockaddr_in6 *ina;
-               int lastns = statp->nscount + EXT(statp).nscount6 - 1;
+               unsigned int map;
 
-               ina = EXT(statp).nsaddrs[0];
-               for (ns = 0; ns < lastns; ns++)
-                       EXT(statp).nsaddrs[ns] = EXT(statp).nsaddrs[ns + 1];
-               EXT(statp).nsaddrs[lastns] = ina;
+               n = 0;
+               while (n < MAXNS && EXT(statp).nsmap[n] == MAXNS)
+                       n++;
+               if (n < MAXNS) {
+                       ina = EXT(statp).nsaddrs[n];
+                       map = EXT(statp).nsmap[n];
+                       for (;;) {
+                               ns = n + 1;
+                               while (ns < MAXNS
+                                      && EXT(statp).nsmap[ns] == MAXNS)
+                                       ns++;
+                               if (ns == MAXNS)
+                                       break;
+                               EXT(statp).nsaddrs[n] = EXT(statp).nsaddrs[ns];
+                               EXT(statp).nsmap[n] = EXT(statp).nsmap[ns];
+                               n = ns;
+                       }
+                       EXT(statp).nsaddrs[n] = ina;
+                       EXT(statp).nsmap[n] = map;
+               }
 #else
                struct sockaddr_in ina;
                int lastns = statp->nscount - 1;
index 238ea59..09bddb8 100644 (file)
@@ -130,7 +130,7 @@ struct __res_state {
                char    pad[52];        /* On an i386 this means 512b total. */
                struct {
                        u_int16_t               nscount;
-                       u_int16_t               nstimes[MAXNS]; /* ms. */
+                       u_int16_t               nsmap[MAXNS];
                        int                     nssocks[MAXNS];
                        u_int16_t               nscount6;
                        u_int16_t               nsinit;