Removed resolver cache, cleanup client code
authorThomas Helvey <tom.helvey@cox.net>
Sat, 11 Jan 2003 05:46:51 +0000 (05:46 +0000)
committerThomas Helvey <tom.helvey@cox.net>
Sat, 11 Jan 2003 05:46:51 +0000 (05:46 +0000)
git-svn-id: file:///home/klmitch/undernet-ircu/undernet-ircu-svn/ircu2/trunk@909 c9e4aea6-c8fd-4c43-8297-357d70d61c8c

12 files changed:
ChangeLog
include/client.h
include/res.h
include/s_bsd.h
ircd/ircd.c
ircd/list.c
ircd/m_connect.c
ircd/res_adns.c
ircd/res_libresolv.c
ircd/s_auth.c
ircd/s_bsd.c
ircd/s_conf.c

index 3ff3012d74edb7aab756be5e3c40d3a314b86cc1..6a801dd8830fcc5fd32fe6b486b0799c8c1c4ee7 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,9 @@
+2003-01-10  Thomas Helvey <tom.helvey@cox.net>
+       * include/client.h, include/res.h, include/s_bsd.h,
+       ircd/ircd.c, ircd/list.c ircd/m_connect.c, ircd/res_adns.c,
+       ircd/res_libresolv.c, ircd/s_auth.c, ircd/s_bsd.c, ircd/s_conf.c:
+       Remove resolver cache wart, change hostent representation, cleanup
+       resolver clients.
 2003-01-10  Thomas Helvey <tom.helvey@cox.net>
        * ircd/map.c, ircd/Makefile.in, include/map.h: Remove 
         HEAD_IN_SAND macros to get server to build, rebuild dependencies.
index 4d61472e7f12c13f0f0598773c828b2ccb6b879a..ec918b007d08d24acc9fd831909b33d8368722f9 100644 (file)
@@ -53,7 +53,6 @@ struct SLink;
 struct Server;
 struct User;
 struct Whowas;
-struct DNSReply;
 struct hostent;
 struct Privs;
 struct AuthRequest;
@@ -191,7 +190,7 @@ struct Connection
   struct SLink*       con_confs; /* Configuration record associated */
   HandlerType         con_handler; /* message index into command table
                                      for parsing */
-  struct DNSReply*    con_dns_reply; /* DNS reply used during client
+  struct hostent*    con_dns_reply; /* DNS reply used during client
                                        registration */
   struct ListingArgs* con_listing;
   unsigned int        con_max_sendq; /* cached max send queue for client */
index 05c037ba5f40df1025d067b1bcae40ce2c71e423..6a10c08a32c0da59ca8354273c25b265b6daa7e1 100644 (file)
 struct Client;
 struct hostent;
 
-struct DNSReply {
-  struct hostent* hp;        /* hostent struct  */
-  int             ref_count; /* reference count */
-};
-
 struct DNSQuery {
   void* vptr;               /* pointer used by callback to identify request */
-  void (*callback)(void* vptr, struct DNSReply* reply); /* callback to call */
+  void (*callback)(void* vptr, struct hostent* he); /* callback to call */
 };
 
 extern int ResolverFileDescriptor;  /* GLOBAL - file descriptor (s_bsd.c) */
 
 extern void get_res(void);
-extern struct DNSReply* gethost_byname(const char* name, 
-                                       const struct DNSQuery* req);
-extern struct DNSReply* gethost_byaddr(const char* name, 
-                                       const struct DNSQuery* req);
+extern void gethost_byname(const char* name, const struct DNSQuery* req);
+extern void gethost_byaddr(const char* name, const struct DNSQuery* req);
 extern int             init_resolver(void);
 extern void            restart_resolver(void);
 extern time_t          timeout_resolver(time_t now);
+
 /*
  * delete_resolver_queries - delete all outstanding queries for the
  * pointer arg, DO NOT call this from a resolver callback function the
index 5952d480a411e38a59b8d22430ea92a700a6da9e..289c5ecfb2946af59b3e5b0c55097cd613b50a08 100644 (file)
@@ -17,7 +17,6 @@
 struct Client;
 struct ConfItem;
 struct Listener;
-struct DNSReply;
 struct MsgQ;
 
 /*
@@ -79,8 +78,7 @@ struct Pollable {
  * Proto types
  */
 extern unsigned int deliver_it(struct Client *cptr, struct MsgQ *buf);
-extern int connect_server(struct ConfItem* aconf, struct Client* by,
-                          struct DNSReply* reply);
+extern int connect_server(struct ConfItem* aconf, struct Client* by);
 extern void release_dns_reply(struct Client* cptr);
 extern int  net_close_unregistered_connections(struct Client* source);
 extern void close_connection(struct Client *cptr);
index 5888513a7b965406965457d9533caf4b67322276..7dd10811415c1ee1d3ffd1e6ab906536990c6e6c 100644 (file)
@@ -308,7 +308,7 @@ static void try_connections(struct Event* ev) {
       (*pconf = con_conf)->next = 0;
     }
 
-    if (connect_server(con_conf, 0, 0))
+    if (connect_server(con_conf, 0))
       sendto_opmask_butone(0, SNO_OLDSNO, "Connection to %s activated.",
                           con_conf->name);
   }
index 10fe8406e11589591bfb1902783f02c08c34640c..813ccbca95cc53b1fab13527338d544f5d2d3081 100644 (file)
@@ -154,8 +154,11 @@ static void dealloc_connection(struct Connection* con)
 
   Debug((DEBUG_LIST, "Deallocating connection %p", con));
 
-  if (con_dns_reply(con))
-    --(con_dns_reply(con)->ref_count);
+  
+  if (con_dns_reply(con)) {
+    MyFree(con_dns_reply(con));
+    con_dns_reply(con) = 0;
+  }
   if (-1 < con_fd(con))
     close(con_fd(con));
   MsgQClear(&(con_sendQ(con)));
index 2fc7ec92bd121e7e171cb590eb150a22ab19ec09..b7dfd3ce5c91f06ec8a75c5ea23f9ca9a8c41c0f 100644 (file)
@@ -202,7 +202,7 @@ int ms_connect(struct Client* cptr, struct Client* sptr, int parc, char* parv[])
   log_write(LS_NETWORK, L_INFO, 0, "CONNECT From %C : %s %s", sptr, parv[1],
            parv[2] ? parv[2] : "");
 
-  if (connect_server(aconf, sptr, 0)) {
+  if (connect_server(aconf, sptr)) {
     sendcmdto_one(&me, CMD_NOTICE, sptr, "%C :*** Connecting to %s.", sptr,
                  aconf->name);
   }
@@ -332,7 +332,7 @@ int mo_connect(struct Client* cptr, struct Client* sptr, int parc, char* parv[])
   tmpport = aconf->port;
   aconf->port = port;
 
-  if (connect_server(aconf, sptr, 0)) {
+  if (connect_server(aconf, sptr)) {
     sendcmdto_one(&me, CMD_NOTICE, sptr, "%C :*** Connecting to %s.", sptr,
                  aconf->name);
   }
index 590d5ef737c25b72fc7616219c7f2bdbf0fe097d..1692c1875a918c924be1013aa29a3cb736b2f8e0 100644 (file)
  */
 
 struct Hostent {
-  struct hostent h;      /* the hostent struct we are passing around */
-  char*          buf;    /* buffer for data pointed to from hostent */
+  struct hostent h;        /* the hostent struct we are passing around */
+  char           buf[1];   /* buffer for data pointed to from hostent */
 };
 
 struct ResRequest {
@@ -166,30 +166,14 @@ struct ResRequest {
   struct in_addr     addr;
   char*              name;
   struct DNSQuery    query;         /* query callback for this request */
-  struct Hostent     he;
+  struct hostent     he;
+  char*              buf;
 };
 
-struct CacheEntry {
-  struct CacheEntry* hname_next;
-  struct CacheEntry* hnum_next;
-  struct CacheEntry* list_next;
-  time_t             expireat;
-  time_t             ttl;
-  struct Hostent     he;
-  struct DNSReply    reply;
-};
-
-struct CacheTable {
-  struct CacheEntry* num_list;
-  struct CacheEntry* name_list;
-};
-
-
 int ResolverFileDescriptor    = -1;   /* GLOBAL - used in s_bsd.c */
 
 static struct Socket resSock;          /* Socket describing resolver */
 static struct Timer  resExpireDNS;     /* Timer for DNS expiration */
-static struct Timer  resExpireCache;   /* Timer for cache expiration */
 static adns_state adns = NULL;
 
 /*
@@ -201,9 +185,6 @@ static adns_state adns = NULL;
  */ 
 static int                spare_fd = -1;
 
-static int                cachedCount = 0;
-static struct CacheTable  hashtable[ARES_CACSIZE];
-static struct CacheEntry* cacheTop;
 static struct ResRequest* requestListHead;   /* head of resolver request list */
 static struct ResRequest* requestListTail;   /* tail of resolver request list */
 
@@ -212,31 +193,15 @@ static void     add_request(struct ResRequest* request);
 static void     rem_request(struct ResRequest* request);
 static struct ResRequest*   make_request(const struct DNSQuery* query);
 static time_t   timeout_query_list(time_t now);
-static time_t   expire_cache(time_t now);
-static void     rem_cache(struct CacheEntry*);
 static void     do_query_name(const struct DNSQuery* query, 
                               const char* name, 
                               struct ResRequest* request);
 static void     do_query_number(const struct DNSQuery* query,
                                 const struct in_addr*, 
                                 struct ResRequest* request);
-static struct CacheEntry*  make_cache(struct ResRequest* request);
-static struct CacheEntry*  find_cache_name(const char* name);
-static struct CacheEntry*  find_cache_number(struct ResRequest* request, 
-                                             const char* addr);
 static void res_adns_callback(adns_state state, adns_query q, void *context);
 
-static struct cacheinfo {
-  int  ca_adds;
-  int  ca_dels;
-  int  ca_expires;
-  int  ca_lookups;
-  int  ca_na_hits;
-  int  ca_nu_hits;
-  int  ca_updates;
-} cainfo;
-
-static  struct  resinfo {
+static struct  resinfo {
   int  re_errors;
   int  re_nu_look;
   int  re_na_look;
@@ -323,7 +288,8 @@ static void start_resolver(void)
     return;
 
   if ((res = adns_init(&adns, adns_if_debug /*| adns_if_noautosys*/, NULL))) {
-    report_error("Resolver: error initializing adns for %s: %s", cli_name(&me), res);
+    report_error("Resolver: error initializing adns for %s: %s",
+                 cli_name(&me), res);
     errno = res;
     return;
   }
@@ -347,16 +313,6 @@ static void expire_DNS_callback(struct Event* ev)
   timer_add(&resExpireDNS, expire_DNS_callback, 0, TT_ABSOLUTE, next);
 }
 
-/* Call the cache expire function */
-static void expire_cache_callback(struct Event* ev)
-{
-  time_t next;
-
-  next = expire_cache(CurrentTime);
-
-  timer_add(&resExpireCache, expire_cache_callback, 0, TT_ABSOLUTE, next);
-}
-
 /*
  * init_resolver - initialize resolver and resolver library
  */
@@ -366,8 +322,6 @@ int init_resolver(void)
 #ifdef  LRAND48
   srand48(CurrentTime);
 #endif
-  memset(&cainfo,   0, sizeof(cainfo));
-  memset(hashtable, 0, sizeof(hashtable));
   memset(&reinfo,   0, sizeof(reinfo));
 
   requestListHead = requestListTail = 0;
@@ -375,8 +329,6 @@ int init_resolver(void)
   /* initiate the resolver timers */
   timer_add(timer_init(&resExpireDNS), expire_DNS_callback, 0,
            TT_RELATIVE, 1);
-  timer_add(timer_init(&resExpireCache), expire_cache_callback, 0,
-           TT_RELATIVE, 1);
 
   errno = h_errno = 0;
 
@@ -392,7 +344,6 @@ int init_resolver(void)
  */
 void restart_resolver(void)
 {
-  /* flush_cache();  flush the dns cache */
   start_resolver();
 }
 
@@ -435,7 +386,7 @@ static void rem_request(struct ResRequest* request)
   }
   if (request->aq)
     adns_cancel(request->aq);
-  MyFree(request->he.buf);
+  MyFree(request->buf);
   MyFree(request->name);
   MyFree(request);
 }
@@ -450,19 +401,12 @@ static struct ResRequest* make_request(const struct DNSQuery* query)
   request = (struct ResRequest*) MyMalloc(sizeof(struct ResRequest));
   memset(request, 0, sizeof(struct ResRequest));
 
-  request->addr.s_addr      = INADDR_NONE;
-  request->he.h.h_addrtype  = AF_INET;
-  request->he.h.h_length    = sizeof(struct in_addr);
-  request->query.vptr       = query->vptr;
-  request->query.callback   = query->callback;
-
-#if defined(NULL_POINTER_NOT_ZERO)
-  request->next             = NULL;
-  request->he.buf           = NULL;
-  request->he.h.h_name      = NULL;
-  request->he.h.h_aliases   = NULL;
-  request->he.h.h_addr_list = NULL;
-#endif
+  request->addr.s_addr    = INADDR_NONE;
+  request->he.h_addrtype  = AF_INET;
+  request->he.h_length    = sizeof(struct in_addr);
+  request->query.vptr     = query->vptr;
+  request->query.callback = query->callback;
+
   add_request(request);
   return request;
 }
@@ -490,30 +434,6 @@ static time_t timeout_query_list(time_t now)
   return now + next;
 }
 
-/*
- * expire_cache - removes entries from the cache which are older 
- * than their expiry times. returns the time at which the server 
- * should next poll the cache.
- */
-static time_t expire_cache(time_t now)
-{
-  struct CacheEntry* cp;
-  struct CacheEntry* cp_next;
-  time_t             expire = 0;
-
-  Debug((DEBUG_DNS, "Resolver: expire_cache at %s", myctime(now)));
-  for (cp = cacheTop; cp; cp = cp_next) {
-    cp_next = cp->list_next;
-    if (cp->expireat < now) {
-      ++cainfo.ca_expires;
-      rem_cache(cp);
-    }
-    else if (!expire || expire > cp->expireat)
-      expire = cp->expireat;
-  }
-  return (expire > now) ? expire : (now + AR_TTL);
-}
-
 /*
  * delete_resolver_queries - cleanup outstanding queries 
  * for which there no longer exist clients or conf lines.
@@ -533,39 +453,24 @@ void delete_resolver_queries(const void* vptr)
 /*
  * gethost_byname - get host address from name
  */
-struct DNSReply* gethost_byname(const char* name, 
-                               const struct DNSQuery* query)
+void gethost_byname(const char* name, const struct DNSQuery* query)
 {
-  struct CacheEntry* cp;
   assert(0 != name);
 
   Debug((DEBUG_DNS, "Resolver: gethost_byname %s", name));
   ++reinfo.re_na_look;
-  if ((cp = find_cache_name(name)))
-    return &(cp->reply);
-
   do_query_name(query, name, NULL);
-  return NULL;
 }
 
 /*
  * gethost_byaddr - get host name from address
  */
-struct DNSReply* gethost_byaddr(const char* addr,
-                                const struct DNSQuery* query)
+void gethost_byaddr(const char* addr, const struct DNSQuery* query)
 {
-  struct CacheEntry *cp;
-
   assert(0 != addr);
-
   Debug((DEBUG_DNS, "Resolver: gethost_byaddr %s", ircd_ntoa(addr)));
-
   ++reinfo.re_nu_look;
-  if ((cp = find_cache_number(NULL, addr)))
-    return &(cp->reply);
-
   do_query_number(query, (const struct in_addr*) addr, NULL);
-  return NULL;
 }
 
 /*
@@ -587,7 +492,8 @@ static void do_query_name(const struct DNSQuery* query,
     request->name = (char*) MyMalloc(strlen(hname) + 1);
     strcpy(request->name, hname);
   }
-  res = adns_submit_callback(adns, hname, adns_r_a, adns_qf_owner, request, &request->aq, res_adns_callback);
+  res = adns_submit_callback(adns, hname, adns_r_a, adns_qf_owner,
+                             request, &request->aq, res_adns_callback);
   assert(!res);
   timer_chg(&resExpireDNS, TT_RELATIVE, 1);
 }
@@ -614,7 +520,8 @@ static void do_query_number(const struct DNSQuery* query,
     request->type        = adns_r_ptr;
     request->addr.s_addr = addr->s_addr;
   }
-  res = adns_submit_callback(adns, ipbuf, adns_r_ptr, adns_qf_owner, request, &request->aq, res_adns_callback);
+  res = adns_submit_callback(adns, ipbuf, adns_r_ptr, adns_qf_owner,
+                             request, &request->aq, res_adns_callback);
   assert(!res);
   timer_chg(&resExpireDNS, TT_RELATIVE, 1);
 }
@@ -634,6 +541,73 @@ static int validate_name(char *name)
   return 1;
 }
 
+/*
+ * dup_hostent - Duplicate a hostent struct, allocate only enough memory for
+ * the data we're putting in it.
+ */
+static struct hostent* dup_hostent(struct hostent* hp)
+{
+  char*  p;
+  char** ap;
+  char** pp;
+  int    alias_count = 0;
+  int    addr_count = 0;
+  size_t bytes_needed = 0;
+  struct Hostent* new_hp = 0;
+
+  assert(0 != hp);
+
+  /* how much buffer do we need? */
+  bytes_needed += (strlen(hp->h_name) + 1);
+
+  pp = hp->h_aliases;
+  while (*pp) {
+    bytes_needed += (strlen(*pp++) + 1 + sizeof(char*));
+    ++alias_count;
+  }
+  pp = hp->h_addr_list;
+  while (*pp++) {
+    bytes_needed += (hp->h_length + sizeof(char*));
+    ++addr_count;
+  }
+  /* Reserve space for 2 nulls to terminate h_aliases and h_addr_list */
+  bytes_needed += (2 * sizeof(char*));
+
+  /* Allocate memory */
+  new_hp = (struct Hostent*) MyMalloc(sizeof(struct Hostent) + bytes_needed);
+
+  new_hp->h.h_addrtype = hp->h_addrtype;
+  new_hp->h.h_length = hp->h_length;
+
+  /* first write the address list */
+  pp = hp->h_addr_list;
+  ap = new_hp->h.h_addr_list =
+      (char**)(new_hp->buf + ((alias_count + 1) * sizeof(char*)));
+  p = (char*)ap + ((addr_count + 1) * sizeof(char*));
+  while (*pp)
+  {
+    *ap++ = p;
+    memcpy(p, *pp++, hp->h_length);
+    p += hp->h_length;
+  }
+  *ap = 0;
+  /* next write the name */
+  new_hp->h.h_name = p;
+  strcpy(p, hp->h_name);
+  p += (strlen(p) + 1);
+
+  /* last write the alias list */
+  pp = hp->h_aliases;
+  ap = new_hp->h.h_aliases = (char**) new_hp->buf;
+  while (*pp) {
+    *ap++ = p;
+    strcpy(p, *pp++);
+    p += (strlen(p) + 1);
+  }
+  *ap = 0;
+  return (struct hostent*) new_hp;
+}
+
 static void res_adns_callback(adns_state state, adns_query q, void *context)
 {
   struct ResRequest *request = (struct ResRequest *) context;
@@ -649,7 +623,6 @@ static void res_adns_callback(adns_state state, adns_query q, void *context)
   char*  endp;                 /* end of our buffer */
   int    addr_count  = 0;      /* number of addresses in hostent */
   int    alias_count = 0;      /* number of aliases in hostent */
-  struct CacheEntry* cp           = 0;
   
   assert(request);
   assert(q);
@@ -666,7 +639,8 @@ static void res_adns_callback(adns_state state, adns_query q, void *context)
     return;
   }
 
-  Debug((DEBUG_DNS, "Resolver: adns_check status %d nrrs %d", answer->status, answer->nrrs));
+  Debug((DEBUG_DNS, "Resolver: adns_check status %d nrrs %d",
+        answer->status, answer->nrrs));
   
   /* No error, we have a valid answer structure */
   if (answer->status != adns_s_ok || !answer->nrrs) {
@@ -675,20 +649,20 @@ static void res_adns_callback(adns_state state, adns_query q, void *context)
     (*request->query.callback)(request->query.vptr, 0);
   } else {
     ++reinfo.re_replies;
-    hp = &(request->he.h);    
-    if (!request->he.buf) {
-      request->he.buf = (char*) MyMalloc(MAXGETHOSTLEN + 1);
-      request->he.buf[MAXGETHOSTLEN] = '\0';
+    hp = &(request->he);    
+    if (!request->buf) {
+      request->buf = (char*) MyMalloc(MAXGETHOSTLEN + 1);
+      request->buf[MAXGETHOSTLEN] = '\0';
       /*
        * array of alias list pointers starts at beginning of buf
        */
-      hp->h_aliases = (char**) request->he.buf;
+      hp->h_aliases = (char**) request->buf;
       hp->h_aliases[0] = NULL;
       /*
        * array of address list pointers starts after alias list pointers
        * the actual addresses follow the the address list pointers
        */ 
-      hp->h_addr_list = (char**)(request->he.buf + ALIAS_BLEN);
+      hp->h_addr_list = (char**)(request->buf + ALIAS_BLEN);
       /*
        * don't copy the host address to the beginning of h_addr_list
        */
@@ -697,7 +671,7 @@ static void res_adns_callback(adns_state state, adns_query q, void *context)
 
     hp->h_addrtype = AF_INET;
 
-    endp = request->he.buf + MAXGETHOSTLEN;
+    endp = request->buf + MAXGETHOSTLEN;
     /*
      * find the end of the address list
      */
@@ -710,7 +684,7 @@ static void res_adns_callback(adns_state state, adns_query q, void *context)
     /*
      * make address point to first available address slot
      */
-    address = request->he.buf + ADDRS_OFFSET +
+    address = request->buf + ADDRS_OFFSET +
                       (sizeof(struct in_addr) * addr_count);
     base_address = address;
 
@@ -732,7 +706,7 @@ static void res_adns_callback(adns_state state, adns_query q, void *context)
     else if (hp->h_name)
       name = hp->h_name + strlen(hp->h_name) + 1;
     else
-      name = request->he.buf + ADDRS_OFFSET + ADDRS_DLEN;
+      name = request->buf + ADDRS_OFFSET + ADDRS_DLEN;
 
     switch (request->type) {
     case adns_r_a:
@@ -743,7 +717,8 @@ static void res_adns_callback(adns_state state, adns_query q, void *context)
           *addr = 0;
           address += sizeof(struct in_addr);
        }
-        Debug((DEBUG_DNS, "Resolver: A %s for %s", ircd_ntoa((char*) &answer->rrs.inaddr[k]), answer->owner));
+        Debug((DEBUG_DNS, "Resolver: A %s for %s",
+              ircd_ntoa((char*) &answer->rrs.inaddr[k]), answer->owner));
       }
       if (!hp->h_name) {
         strcpy(name, answer->owner);
@@ -769,34 +744,30 @@ static void res_adns_callback(adns_state state, adns_query q, void *context)
       *alias++ = name;
       *alias   = 0;
       name += strlen(name) + 1;
-      Debug((DEBUG_DNS, "Resolver: CNAME %s for %s", answer->cname, answer->owner));
+      Debug((DEBUG_DNS, "Resolver: CNAME %s for %s",
+            answer->cname, answer->owner));
     }
 
     if (request->type == adns_r_ptr) {
-      struct DNSReply* reply;
 
       Debug((DEBUG_DNS, "relookup %s <-> %s",
-             request->he.h.h_name, ircd_ntoa((char*) &request->addr)));
+             request->he.h_name, ircd_ntoa((char*) &request->addr)));
       /*
        * Lookup the 'authoritive' name that we were given for the
        * ip#.  By using this call rather than regenerating the
        * type we automatically gain the use of the cache with no
        * extra kludges.
        */
-      reply = gethost_byname(request->he.h.h_name, &request->query);
-      if (reply) {
-        (*request->query.callback)(request->query.vptr, reply);
-      } else {
-        /*
-         * If name wasn't found, a request has been queued and it will
-         * be the last one queued.  This is rather nasty way to keep
-         * a host alias with the query. -avalon
-         */
-        MyFree(requestListTail->he.buf);
-        requestListTail->he.buf = request->he.buf;
-        request->he.buf = 0;
-        memcpy(&requestListTail->he.h, &request->he.h, sizeof(struct hostent));
-      }
+      gethost_byname(request->he.h_name, &request->query);
+      /*
+       * If name wasn't found, a request has been queued and it will
+       * be the last one queued.  This is rather nasty way to keep
+       * a host alias with the query. -avalon
+       */
+      MyFree(requestListTail->buf);
+      requestListTail->buf = request->buf;
+      request->buf = 0;
+      memcpy(&requestListTail->he, &request->he, sizeof(struct hostent));
     } else {
       /*
        * got a name and address response, client resolved
@@ -805,10 +776,8 @@ static void res_adns_callback(adns_state state, adns_query q, void *context)
        * PTR returned a CNAME, cp was not checked before so the
        * callback was being called with a value of 0x2C != NULL.
        */
-      struct DNSReply* reply = 0;
-      if ((cp = make_cache(request)))
-        reply = &cp->reply;
-      (*request->query.callback)(request->query.vptr, reply);
+      struct hostent* he = dup_hostent(&request->he);
+      (*request->query.callback)(request->query.vptr, he);
     }
   }
   
@@ -820,569 +789,17 @@ static void res_adns_callback(adns_state state, adns_query q, void *context)
   free(answer);
 }
 
-
-static size_t calc_hostent_buffer_size(const struct hostent* hp)
-{
-  char** p;
-  size_t count = 0;
-  assert(0 != hp);
-
-  /*
-   * space for name
-   */
-  count += (strlen(hp->h_name) + 1);
-  /*
-   * space for aliases
-   */
-  for (p = hp->h_aliases; *p; ++p)
-    count += (strlen(*p) + 1 + sizeof(char*));
-  /*
-   * space for addresses
-   */
-  for (p = hp->h_addr_list; *p; ++p)
-    count += (hp->h_length + sizeof(char*));
-  /*
-   * space for 2 nulls to terminate h_aliases and h_addr_list 
-   */
-  count += (2 * sizeof(char*));
-  return count;
-}
-
-
-/*
- * dup_hostent - Duplicate a hostent struct, allocate only enough memory for
- * the data we're putting in it.
- */
-static void dup_hostent(struct Hostent* new_hp, struct hostent* hp)
-{
-  char*  p;
-  char** ap;
-  char** pp;
-  int    alias_count = 0;
-  int    addr_count = 0;
-  size_t bytes_needed = 0;
-
-  assert(0 != new_hp);
-  assert(0 != hp);
-
-  /* how much buffer do we need? */
-  bytes_needed += (strlen(hp->h_name) + 1);
-
-  pp = hp->h_aliases;
-  while (*pp) {
-    bytes_needed += (strlen(*pp++) + 1 + sizeof(char*));
-    ++alias_count;
-  }
-  pp = hp->h_addr_list;
-  while (*pp++) {
-    bytes_needed += (hp->h_length + sizeof(char*));
-    ++addr_count;
-  }
-  /* Reserve space for 2 nulls to terminate h_aliases and h_addr_list */
-  bytes_needed += (2 * sizeof(char*));
-
-  /* Allocate memory */
-  new_hp->buf = (char*) MyMalloc(bytes_needed);
-
-  new_hp->h.h_addrtype = hp->h_addrtype;
-  new_hp->h.h_length = hp->h_length;
-
-  /* first write the address list */
-  pp = hp->h_addr_list;
-  ap = new_hp->h.h_addr_list =
-      (char**)(new_hp->buf + ((alias_count + 1) * sizeof(char*)));
-  p = (char*)ap + ((addr_count + 1) * sizeof(char*));
-  while (*pp)
-  {
-    *ap++ = p;
-    memcpy(p, *pp++, hp->h_length);
-    p += hp->h_length;
-  }
-  *ap = 0;
-  /* next write the name */
-  new_hp->h.h_name = p;
-  strcpy(p, hp->h_name);
-  p += (strlen(p) + 1);
-
-  /* last write the alias list */
-  pp = hp->h_aliases;
-  ap = new_hp->h.h_aliases = (char**) new_hp->buf;
-  while (*pp) {
-    *ap++ = p;
-    strcpy(p, *pp++);
-    p += (strlen(p) + 1);
-  }
-  *ap = 0;
-}
-
-/*
- * update_hostent - Add records to a Hostent struct in place.
- */
-static void update_hostent(struct Hostent* hp, char** addr, char** alias)
-{
-  char*  p;
-  char** ap;
-  char** pp;
-  int    alias_count = 0;
-  int    addr_count = 0;
-  char*  buf = NULL;
-  size_t bytes_needed = 0;
-
-  if (!hp || !hp->buf)
-    return;
-
-  /* how much buffer do we need? */
-  bytes_needed = strlen(hp->h.h_name) + 1;
-  pp = hp->h.h_aliases;
-  while (*pp) {
-    bytes_needed += (strlen(*pp++) + 1 + sizeof(char*));
-    ++alias_count;
-  }
-  if (alias) {
-    pp = alias;
-    while (*pp) {
-      bytes_needed += (strlen(*pp++) + 1 + sizeof(char*));
-      ++alias_count;
-    }
-  }
-  pp = hp->h.h_addr_list;
-  while (*pp++) {
-    bytes_needed += (hp->h.h_length + sizeof(char*));
-    ++addr_count;
-  }
-  if (addr) {
-    pp = addr;
-    while (*pp++) {
-      bytes_needed += (hp->h.h_length + sizeof(char*));
-      ++addr_count;
-    }
-  }
-  /* Reserve space for 2 nulls to terminate h_aliases and h_addr_list */
-  bytes_needed += 2 * sizeof(char*);
-
-  /* Allocate memory */
-  buf = (char*) MyMalloc(bytes_needed);
-  assert(0 != buf);
-
-  /* first write the address list */
-  pp = hp->h.h_addr_list;
-  ap = hp->h.h_addr_list =
-      (char**)(buf + ((alias_count + 1) * sizeof(char*)));
-  p = (char*)ap + ((addr_count + 1) * sizeof(char*));
-  while (*pp) {
-    memcpy(p, *pp++, hp->h.h_length);
-    *ap++ = p;
-    p += hp->h.h_length;
-  }
-  if (addr) {
-    while (*addr) {
-      memcpy(p, *addr++, hp->h.h_length);
-      *ap++ = p;
-      p += hp->h.h_length;
-    }
-  }
-  *ap = 0;
-
-  /* next write the name */
-  strcpy(p, hp->h.h_name);
-  hp->h.h_name = p;
-  p += (strlen(p) + 1);
-
-  /* last write the alias list */
-  pp = hp->h.h_aliases;
-  ap = hp->h.h_aliases = (char**) buf;
-  while (*pp) {
-    strcpy(p, *pp++);
-    *ap++ = p;
-    p += (strlen(p) + 1);
-  }
-  if (alias) {
-    while (*alias) {
-      strcpy(p, *alias++);
-      *ap++ = p;
-      p += (strlen(p) + 1);
-    }
-  }
-  *ap = 0;
-  /* release the old buffer */
-  p = hp->buf;
-  hp->buf = buf;
-  MyFree(p);
-}
-
-/*
- * hash_number - IP address hash function
- */
-static int hash_number(const unsigned char* ip)
-{
-  /* could use loop but slower */
-  unsigned int hashv;
-  const u_char* p = (const u_char*) ip;
-
-  assert(0 != p);
-
-  hashv = *p++;
-  hashv += hashv + *p++;
-  hashv += hashv + *p++;
-  hashv += hashv + *p;
-  hashv %= ARES_CACSIZE;
-  return hashv;
-}
-
-/*
- * hash_name - hostname hash function
- */
-static int hash_name(const char* name)
-{
-  unsigned int hashv = 0;
-  const u_char* p = (const u_char*) name;
-
-  assert(0 != p);
-
-  for (; *p && *p != '.'; ++p)
-    hashv += *p;
-  hashv %= ARES_CACSIZE;
-  return hashv;
-}
-
-/*
- * add_to_cache - Add a new cache item to the queue and hash table.
- */
-static struct CacheEntry* add_to_cache(struct CacheEntry* ocp)
-{
-  int  hashv;
-
-  assert(0 != ocp);
-
-  ocp->list_next = cacheTop;
-  cacheTop = ocp;
-
-  hashv = hash_name(ocp->he.h.h_name);
-
-  ocp->hname_next = hashtable[hashv].name_list;
-  hashtable[hashv].name_list = ocp;
-
-  hashv = hash_number((const unsigned char*) ocp->he.h.h_addr);
-
-  ocp->hnum_next = hashtable[hashv].num_list;
-  hashtable[hashv].num_list = ocp;
-
-  /*
-   * LRU deletion of excessive cache entries.
-   */
-  if (++cachedCount > MAXCACHED) {
-    struct CacheEntry* cp;
-    struct CacheEntry* cp_next;
-    for (cp = ocp->list_next; cp; cp = cp_next) {
-      cp_next = cp->list_next;
-      rem_cache(cp);
-    }
-  }
-  ++cainfo.ca_adds;
-  return ocp;
-}
-
-/*
- * update_list - does not alter the cache structure passed. It is assumed that
- * it already contains the correct expire time, if it is a new entry. Old
- * entries have the expirey time updated.
-*/
-static void update_list(struct ResRequest* request, struct CacheEntry* cachep)
-{
-  struct CacheEntry*  cp = cachep;
-  char*    s;
-  char*    t;
-  int      i;
-  int      j;
-  char**   ap;
-  char*    addrs[RES_MAXADDRS + 1];
-  char*    aliases[RES_MAXALIASES + 1];
-
-  /*
-   * search for the new cache item in the cache list by hostname.
-   * If found, move the entry to the top of the list and return.
-   */
-  ++cainfo.ca_updates;
-
-  if (!request)
-    return;
-  /*
-   * Compare the cache entry against the new record.  Add any
-   * previously missing names for this entry.
-   */
-  *aliases = 0;
-  ap = aliases;
-  for (i = 0, s = request->he.h.h_name; s; s = request->he.h.h_aliases[i++]) {
-    for (j = 0, t = cp->he.h.h_name; t; t = cp->he.h.h_aliases[j++]) {
-      if (0 == ircd_strcmp(t, s))
-        break;
-    }
-    if (!t) {
-      *ap++ = s;
-      *ap = 0;
-    }
-  }
-  /*
-   * Do the same again for IP#'s.
-   */
-  *addrs = 0;
-  ap = addrs;
-  for (i = 0; (s = request->he.h.h_addr_list[i]); i++) {
-    for (j = 0; (t = cp->he.h.h_addr_list[j]); j++) {
-      if (!memcmp(t, s, sizeof(struct in_addr)))
-        break;
-    }
-    if (!t) {
-      *ap++ = s;
-      *ap = 0;
-    }
-  }
-  if (*addrs || *aliases)
-    update_hostent(&cp->he, addrs, aliases);
-}
-
-/*
- * find_cache_name - find name in nameserver cache
- */
-static struct CacheEntry* find_cache_name(const char* name)
-{
-  struct CacheEntry* cp;
-  char*   s;
-  int     hashv;
-  int     i;
-
-  assert(0 != name);
-  hashv = hash_name(name);
-
-  cp = hashtable[hashv].name_list;
-
-  for (; cp; cp = cp->hname_next) {
-    for (i = 0, s = cp->he.h.h_name; s; s = cp->he.h.h_aliases[i++]) {
-      if (0 == ircd_strcmp(s, name)) {
-        ++cainfo.ca_na_hits;
-        return cp;
-      }
-    }
-  }
-
-  for (cp = cacheTop; cp; cp = cp->list_next) {
-    /*
-     * if no aliases or the hash value matches, we've already
-     * done this entry and all possiblilities concerning it.
-     */
-    if (!cp->he.h.h_name || hashv == hash_name(cp->he.h.h_name))
-      continue;
-    for (i = 0, s = cp->he.h.h_aliases[i]; s; s = cp->he.h.h_aliases[++i]) {
-      if (0 == ircd_strcmp(name, s)) {
-        ++cainfo.ca_na_hits;
-        return cp;
-      }
-    }
-  }
-  return NULL;
-}
-
-/*
- * find_cache_number - find a cache entry by ip# and update its expire time
- */
-static struct CacheEntry* find_cache_number(struct ResRequest* request,
-                                            const char* addr)
-{
-  struct CacheEntry* cp;
-  int     hashv;
-  int     i;
-
-  assert(0 != addr);
-  hashv = hash_number((const unsigned char*) addr);
-  cp = hashtable[hashv].num_list;
-
-  for (; cp; cp = cp->hnum_next) {
-    for (i = 0; cp->he.h.h_addr_list[i]; ++i) {
-      if (!memcmp(cp->he.h.h_addr_list[i], addr, sizeof(struct in_addr))) {
-        ++cainfo.ca_nu_hits;
-        return cp;
-      }
-    }
-  }
-  for (cp = cacheTop; cp; cp = cp->list_next) {
-    /*
-     * single address entry...would have been done by hashed
-     * search above...
-     * if the first IP# has the same hashnumber as the IP# we
-     * are looking for, its been done already.
-     */
-    if (!cp->he.h.h_addr_list[1] || 
-        hashv == hash_number((const unsigned char*) cp->he.h.h_addr_list[0]))
-      continue;
-    for (i = 1; cp->he.h.h_addr_list[i]; ++i) {
-      if (!memcmp(cp->he.h.h_addr_list[i], addr, sizeof(struct in_addr))) {
-        ++cainfo.ca_nu_hits;
-        return cp;
-      }
-    }
-  }
-  return NULL;
-}
-
-static struct CacheEntry* make_cache(struct ResRequest* request)
-{
-  struct CacheEntry* cp;
-  int     i;
-  struct hostent* hp;
-  assert(0 != request);
-
-  hp = &request->he.h;
-  /*
-   * shouldn't happen but it just might...
-   */
-  assert(0 != hp->h_name);
-/*    assert(0 != hp->h_addr_list[0]); */
-  if (!hp->h_name || !hp->h_addr_list[0])
-    return NULL;
-  /*
-   * Make cache entry.  First check to see if the cache already exists
-   * and if so, return a pointer to it.
-   */
-  for (i = 0; hp->h_addr_list[i]; ++i) {
-    if ((cp = find_cache_number(request, hp->h_addr_list[i]))) {
-      update_list(request, cp);
-      return cp;
-    }
-  }
-  /*
-   * a matching entry wasnt found in the cache so go and make one up.
-   */ 
-  cp = (struct CacheEntry*) MyMalloc(sizeof(struct CacheEntry));
-  assert(0 != cp);
-
-  memset(cp, 0, sizeof(struct CacheEntry));
-  dup_hostent(&cp->he, hp);
-  cp->reply.hp = &cp->he.h;
-  /*
-   * hmmm... we could time out the cache after 10 minutes regardless
-   * would that be reasonable since we don't save the reply?
-   */ 
-#if 0
-  if (request->ttl < AR_TTL) {
-    ++reinfo.re_shortttl;
-    cp->ttl = AR_TTL;
-  }
-  else
-    cp->ttl = request->ttl;
-#else
-  cp->ttl = AR_TTL;
-#endif
-  cp->expireat = CurrentTime + cp->ttl;
-  return add_to_cache(cp);
-}
-
-/*
- * rem_cache - delete a cache entry from the cache structures 
- * and lists and return all memory used for the cache back to the memory pool.
- */
-static void rem_cache(struct CacheEntry* ocp)
-{
-  struct CacheEntry** cp;
-  int                 hashv;
-  struct hostent*     hp;
-  assert(0 != ocp);
-
-
-  if (0 < ocp->reply.ref_count) {
-    if (ocp->expireat < CurrentTime) {
-      ocp->expireat = CurrentTime + AR_TTL;
-      Debug((DEBUG_DNS, "Resolver: referenced cache entry not removed for: %s",
-            ocp->he.h.h_name));
-    }
-    return;
-  }
-  /*
-   * remove cache entry from linked list
-   */
-  for (cp = &cacheTop; *cp; cp = &((*cp)->list_next)) {
-    if (*cp == ocp) {
-      *cp = ocp->list_next;
-      break;
-    }
-  }
-  hp = &ocp->he.h;
-  /*
-   * remove cache entry from hashed name list
-   */
-  assert(0 != hp->h_name);
-  hashv = hash_name(hp->h_name);
-
-  for (cp = &hashtable[hashv].name_list; *cp; cp = &((*cp)->hname_next)) {
-    if (*cp == ocp) {
-      *cp = ocp->hname_next;
-      break;
-    }
-  }
-  /*
-   * remove cache entry from hashed number list
-   */
-  hashv = hash_number((const unsigned char*) hp->h_addr);
-  assert(-1 < hashv);
-
-  for (cp = &hashtable[hashv].num_list; *cp; cp = &((*cp)->hnum_next)) {
-    if (*cp == ocp) {
-      *cp = ocp->hnum_next;
-      break;
-    }
-  }
-  /*
-   * free memory used to hold the various host names and the array
-   * of alias pointers.
-   */
-  MyFree(ocp->he.buf);
-  MyFree(ocp);
-  --cachedCount;
-  ++cainfo.ca_dels;
-}
-
-void flush_resolver_cache(void)
-{
-  /*
-   * stubbed - iterate cache and remove everything that isn't referenced
-   */
-}
-
 /*
  * m_dns - dns status query
  */
 int m_dns(struct Client *cptr, struct Client *sptr, int parc, char *parv[])
 {
 #if !defined(NDEBUG)
-  struct CacheEntry* cp;
-  int     i;
-  struct hostent* hp;
-
-  if (parv[1] && *parv[1] == 'l') {
-    for(cp = cacheTop; cp; cp = cp->list_next) {
-      hp = &cp->he.h;
-      sendcmdto_one(&me, CMD_NOTICE, sptr, "%C :Ex %d ttl %d host %s(%s)",
-                   sptr, cp->expireat - CurrentTime, cp->ttl,
-                   hp->h_name, ircd_ntoa(hp->h_addr));
-      for (i = 0; hp->h_aliases[i]; i++)
-        sendcmdto_one(&me, CMD_NOTICE, sptr, "%C : %s = %s (CN)", sptr,
-                     hp->h_name, hp->h_aliases[i]);
-      for (i = 1; hp->h_addr_list[i]; i++)
-        sendcmdto_one(&me, CMD_NOTICE, sptr, "%C : %s = %s (IP)", sptr,
-                     hp->h_name, ircd_ntoa(hp->h_addr_list[i]));
-    }
-    return 0;
-  }
   if (parv[1] && *parv[1] == 'd') {
     sendcmdto_one(&me, CMD_NOTICE, sptr, "%C :ResolverFileDescriptor = %d", 
                  sptr, ResolverFileDescriptor);
     return 0;
   }
-  sendcmdto_one(&me, CMD_NOTICE, sptr,"%C :Ca %d Cd %d Ce %d Cl %d Ch %d:%d "
-               "Cu %d", sptr,
-               cainfo.ca_adds, cainfo.ca_dels, cainfo.ca_expires,
-               cainfo.ca_lookups, cainfo.ca_na_hits, cainfo.ca_nu_hits, 
-               cainfo.ca_updates);
-  
   sendcmdto_one(&me, CMD_NOTICE, sptr,"%C :Re %d Rl %d/%d Rp %d Rq %d",
                sptr, reinfo.re_errors, reinfo.re_nu_look,
                reinfo.re_na_look, reinfo.re_replies, reinfo.re_requests);
@@ -1395,36 +812,21 @@ int m_dns(struct Client *cptr, struct Client *sptr, int parc, char *parv[])
 
 size_t cres_mem(struct Client* sptr)
 {
-  struct CacheEntry* entry;
   struct ResRequest* request;
-  size_t cache_mem     = 0;
   size_t request_mem   = 0;
-  int    cache_count   = 0;
   int    request_count = 0;
 
-  for (entry = cacheTop; entry; entry = entry->list_next) {
-    cache_mem += sizeof(struct CacheEntry);
-    cache_mem += calc_hostent_buffer_size(&entry->he.h); 
-    ++cache_count;
-  }
   for (request = requestListHead; request; request = request->next) {
     request_mem += sizeof(struct ResRequest);
     if (request->name)
       request_mem += strlen(request->name) + 1; 
-    if (request->he.buf)
+    if (request->buf)
       request_mem += MAXGETHOSTLEN + 1;
     ++request_count;
   }
 
-  if (cachedCount != cache_count) {
-    send_reply(sptr, SND_EXPLICIT | RPL_STATSDEBUG,
-              ":Resolver: cache count mismatch: %d != %d", cachedCount,
-              cache_count);
-    assert(cachedCount == cache_count);
-  }
   send_reply(sptr, SND_EXPLICIT | RPL_STATSDEBUG,
-            ":Resolver: cache %d(%d) requests %d(%d)", cache_count,
-            cache_mem, request_count, request_mem);
-  return cache_mem + request_mem;
+            ":Resolver: requests %d(%d)", request_count, request_mem);
+  return request_mem;
 }
 
index d4d85fd848c1c021646ebeb33a00bc09864ad88d..44010293356d1b6f5b7f61cd765e9af78abbc571 100644 (file)
 
 #define AR_TTL          600   /* TTL in seconds for dns cache entries */
 
-/*
- * the following values should be prime
- */
-#define ARES_CACSIZE    307
-#define MAXCACHED       281
-
 /*
  * RFC 1104/1105 wasn't very helpful about what these fields
  * should be named, so for now, we'll just name them this way.
  */
 
 struct Hostent {
-  struct hostent h;      /* the hostent struct we are passing around */
-  char*          buf;    /* buffer for data pointed to from hostent */
+  struct hostent h;       /* the hostent struct we are passing around */
+  char           buf[1];  /* buffer for data pointed to from hostent */
 };
 
 struct ResRequest {
@@ -180,22 +174,8 @@ struct ResRequest {
   struct in_addr     addr;
   char*              name;
   struct DNSQuery    query;         /* query callback for this request */
-  struct Hostent     he;
-};
-
-struct CacheEntry {
-  struct CacheEntry* hname_next;
-  struct CacheEntry* hnum_next;
-  struct CacheEntry* list_next;
-  time_t             expireat;
-  time_t             ttl;
-  struct Hostent     he;
-  struct DNSReply    reply;
-};
-
-struct CacheTable {
-  struct CacheEntry* num_list;
-  struct CacheEntry* name_list;
+  struct hostent     he;
+  char*              buf;
 };
 
 
@@ -203,10 +183,8 @@ int ResolverFileDescriptor    = -1;   /* GLOBAL - used in s_bsd.c */
 
 static struct Socket resSock;          /* Socket describing resolver */
 static struct Timer  resExpireDNS;     /* Timer for DNS expiration */
-static struct Timer  resExpireCache;   /* Timer for cache expiration */
 
 static time_t nextDNSCheck    = 0;
-static time_t nextCacheExpire = 1;
 
 /*
  * Keep a spare file descriptor open. res_init calls fopen to read the
@@ -217,9 +195,6 @@ static time_t nextCacheExpire = 1;
  */ 
 static int                spare_fd = -1;
 
-static int                cachedCount = 0;
-static struct CacheTable  hashtable[ARES_CACSIZE];
-static struct CacheEntry* cacheTop;
 static struct ResRequest* requestListHead;   /* head of resolver request list */
 static struct ResRequest* requestListTail;   /* tail of resolver request list */
 
@@ -228,8 +203,6 @@ static void     add_request(struct ResRequest* request);
 static void     rem_request(struct ResRequest* request);
 static struct ResRequest*   make_request(const struct DNSQuery* query);
 static time_t   timeout_query_list(time_t now);
-static time_t   expire_cache(time_t now);
-static void     rem_cache(struct CacheEntry*);
 static void     do_query_name(const struct DNSQuery* query, 
                               const char* name, 
                               struct ResRequest* request);
@@ -241,22 +214,8 @@ static void     query_name(const char* name,
                            int query_type, 
                            struct ResRequest* request);
 static void     resend_query(struct ResRequest* request);
-static struct CacheEntry*  make_cache(struct ResRequest* request);
-static struct CacheEntry*  find_cache_name(const char* name);
-static struct CacheEntry*  find_cache_number(struct ResRequest* request, 
-                                             const char* addr);
 static struct ResRequest*   find_id(int);
 
-static struct cacheinfo {
-  int  ca_adds;
-  int  ca_dels;
-  int  ca_expires;
-  int  ca_lookups;
-  int  ca_na_hits;
-  int  ca_nu_hits;
-  int  ca_updates;
-} cainfo;
-
 static  struct  resinfo {
   int  re_errors;
   int  re_nu_look;
@@ -373,16 +332,6 @@ static void expire_DNS_callback(struct Event* ev)
   timer_add(&resExpireDNS, expire_DNS_callback, 0, TT_ABSOLUTE, next);
 }
 
-/* Call the cache expire function */
-static void expire_cache_callback(struct Event* ev)
-{
-  time_t next;
-
-  next = expire_cache(CurrentTime);
-
-  timer_add(&resExpireCache, expire_cache_callback, 0, TT_ABSOLUTE, next);
-}
-
 /*
  * init_resolver - initialize resolver and resolver library
  */
@@ -392,17 +341,12 @@ int init_resolver(void)
 #ifdef  LRAND48
   srand48(CurrentTime);
 #endif
-  memset(&cainfo,   0, sizeof(cainfo));
-  memset(hashtable, 0, sizeof(hashtable));
-  memset(&reinfo,   0, sizeof(reinfo));
-
+  memset(&reinfo, 0, sizeof(reinfo));
   requestListHead = requestListTail = 0;
 
   /* initiate the resolver timers */
   timer_add(timer_init(&resExpireDNS), expire_DNS_callback, 0,
            TT_RELATIVE, 1);
-  timer_add(timer_init(&resExpireCache), expire_cache_callback, 0,
-           TT_RELATIVE, 1);
 
   errno = h_errno = 0;
 
@@ -471,7 +415,7 @@ static void rem_request(struct ResRequest* request)
     prev    = *current;
     current = &(*current)->next;
   }
-  MyFree(request->he.buf);
+  MyFree(request->buf);
   MyFree(request->name);
   MyFree(request);
 }
@@ -491,18 +435,11 @@ static struct ResRequest* make_request(const struct DNSQuery* query)
   request->resend           = 1;
   request->timeout          = 5;    /* start at 5 per RFC1123 */
   request->addr.s_addr      = INADDR_NONE;
-  request->he.h.h_addrtype  = AF_INET;
-  request->he.h.h_length    = sizeof(struct in_addr);
+  request->he.h_addrtype    = AF_INET;
+  request->he.h_length      = sizeof(struct in_addr);
   request->query.vptr       = query->vptr;
   request->query.callback   = query->callback;
 
-#if defined(NULL_POINTER_NOT_ZERO)
-  request->next             = NULL;
-  request->he.buf           = NULL;
-  request->he.h.h_name      = NULL;
-  request->he.h.h_aliases   = NULL;
-  request->he.h.h_addr_list = NULL;
-#endif
   add_request(request);
   return request;
 }
@@ -542,30 +479,6 @@ static time_t timeout_query_list(time_t now)
   return (next_time > now) ? next_time : (now + AR_TTL);
 }
 
-/*
- * expire_cache - removes entries from the cache which are older 
- * than their expiry times. returns the time at which the server 
- * should next poll the cache.
- */
-static time_t expire_cache(time_t now)
-{
-  struct CacheEntry* cp;
-  struct CacheEntry* cp_next;
-  time_t             expire = 0;
-
-  Debug((DEBUG_DNS, "Resolver: expire_cache at %s", myctime(now)));
-  for (cp = cacheTop; cp; cp = cp_next) {
-    cp_next = cp->list_next;
-    if (cp->expireat < now) {
-      ++cainfo.ca_expires;
-      rem_cache(cp);
-    }
-    else if (!expire || expire > cp->expireat)
-      expire = cp->expireat;
-  }
-  return (expire > now) ? expire : (now + AR_TTL);
-}
-
 /*
  * timeout_resolver - check request list and cache for expired entries
  */
@@ -573,9 +486,7 @@ time_t timeout_resolver(time_t now)
 {
   if (nextDNSCheck < now)
     nextDNSCheck = timeout_query_list(now);
-  if (nextCacheExpire < now)
-    nextCacheExpire = expire_cache(now);
-  return IRCD_MIN(nextDNSCheck, nextCacheExpire);
+  return nextDNSCheck;
 }
 
 
@@ -648,41 +559,32 @@ static struct ResRequest* find_id(int id)
 /*
  * gethost_byname - get host address from name
  */
-struct DNSReply* gethost_byname(const char* name, 
-                               const struct DNSQuery* query)
+void gethost_byname(const char* name, const struct DNSQuery* query)
 {
-  struct CacheEntry* cp;
   assert(0 != name);
 
   Debug((DEBUG_DNS, "Resolver: gethost_byname %s", name));
   ++reinfo.re_na_look;
+#if 0
   if ((cp = find_cache_name(name)))
     return &(cp->reply);
-
+#endif
   do_query_name(query, name, NULL);
   nextDNSCheck = 1;
-  return NULL;
 }
 
 /*
  * gethost_byaddr - get host name from address
  */
-struct DNSReply* gethost_byaddr(const char* addr,
-                                const struct DNSQuery* query)
+void gethost_byaddr(const char* addr, const struct DNSQuery* query)
 {
-  struct CacheEntry *cp;
-
   assert(0 != addr);
 
   Debug((DEBUG_DNS, "Resolver: gethost_byaddr %s", ircd_ntoa(addr)));
 
   ++reinfo.re_nu_look;
-  if ((cp = find_cache_number(NULL, addr)))
-    return &(cp->reply);
-
   do_query_number(query, (const struct in_addr*) addr, NULL);
   nextDNSCheck = 1;
-  return NULL;
 }
 
 /*
@@ -736,7 +638,7 @@ static void do_query_number(const struct DNSQuery* query,
 static void query_name(const char* name, int query_class,
                        int type, struct ResRequest* request)
 {
-  char buf[MAXPACKET];
+  unsigned char buf[MAXPACKET + 1];
   int  request_len = 0;
 
   assert(0 != name);
@@ -745,7 +647,8 @@ static void query_name(const char* name, int query_class,
   Debug((DEBUG_DNS, "Resolver: query_name: %s %d %d", name, query_class, type));
   memset(buf, 0, sizeof(buf));
   if ((request_len = res_mkquery(QUERY, name, query_class, type, 
-                                 0, 0, 0, (unsigned char*) buf, sizeof(buf))) > 0) {
+                                 0, 0, 0,
+                                 buf, sizeof(buf) - 1)) > 0) {
     HEADER* header = (HEADER*) buf;
 #ifndef LRAND48
     int            k = 0;
@@ -772,13 +675,13 @@ static void query_name(const char* name, int query_class,
     ++request->sends;
     Debug((DEBUG_DNS, "Resolver: query_name %d: %s %d %d", request->id, 
           name, query_class, type));
-    request->sent += send_res_msg((const unsigned char*) buf, request_len, request->sends);
+    request->sent += send_res_msg(buf, request_len, request->sends);
   }
 }
 
 static void resend_query(struct ResRequest* request)
 {
-  assert(0 != request);
+  assert(request);
 
   if (request->resend == 0)
     return;
@@ -821,36 +724,36 @@ static int proc_answer(struct ResRequest* request, HEADER* header,
   int    t_ptr_seen = 0;       /* Seen a T_PTR in proc_answer? */
   struct hostent* hp;          /* hostent getting filled */
 
-  assert(0 != request);
-  assert(0 != header);
-  assert(0 != buf);
-  assert(0 != eob);
+  assert(request);
+  assert(header);
+  assert(buf);
+  assert(eob);
   
   current = buf + sizeof(HEADER);
-  hp = &(request->he.h);
+  hp = &(request->he);
   /*
    * lazy allocation of request->he.buf, we don't allocate a buffer
    * unless there is something to put in it.
    */
-  if (!request->he.buf) {
-    request->he.buf = (char*) MyMalloc(MAXGETHOSTLEN + 1);
-    request->he.buf[MAXGETHOSTLEN] = '\0';
+  if (!request->buf) {
+    request->buf = (char*) MyMalloc(MAXGETHOSTLEN + 1);
+    request->buf[MAXGETHOSTLEN] = '\0';
     /*
      * array of alias list pointers starts at beginning of buf
      */
-    hp->h_aliases = (char**) request->he.buf;
+    hp->h_aliases = (char**) request->buf;
     hp->h_aliases[0] = NULL;
     /*
      * array of address list pointers starts after alias list pointers
      * the actual addresses follow the the address list pointers
      */ 
-    hp->h_addr_list = (char**)(request->he.buf + ALIAS_BLEN);
+    hp->h_addr_list = (char**)(request->buf + ALIAS_BLEN);
     /*
      * don't copy the host address to the beginning of h_addr_list
      */
     hp->h_addr_list[0] = NULL;
   }
-  endp = request->he.buf + MAXGETHOSTLEN;
+  endp = request->buf + MAXGETHOSTLEN;
   /*
    * find the end of the address list
    */
@@ -863,7 +766,7 @@ static int proc_answer(struct ResRequest* request, HEADER* header,
   /*
    * make address point to first available address slot
    */
-  address = request->he.buf + ADDRS_OFFSET +
+  address = request->buf + ADDRS_OFFSET +
                     (sizeof(struct in_addr) * addr_count);
   base_address = address;
 
@@ -885,7 +788,7 @@ static int proc_answer(struct ResRequest* request, HEADER* header,
   else if (hp->h_name)
     name = hp->h_name + strlen(hp->h_name) + 1;
   else
-    name = request->he.buf + ADDRS_OFFSET + ADDRS_DLEN;
+    name = request->buf + ADDRS_OFFSET + ADDRS_DLEN;
  
   /*
    * skip past queries
@@ -1024,16 +927,82 @@ static int proc_answer(struct ResRequest* request, HEADER* header,
   return answer_count;
 }
 
+/*
+ * dup_hostent - Duplicate a hostent struct, allocate only enough memory for
+ * the data we're putting in it.
+ */
+static struct hostent* dup_hostent(struct hostent* hp)
+{
+  char*  p;
+  char** ap;
+  char** pp;
+  int    alias_count = 0;
+  int    addr_count = 0;
+  size_t bytes_needed = 0;
+  struct Hostent* new_hp = 0;
+
+  assert(0 != hp);
+
+  /* how much buffer do we need? */
+  bytes_needed += (strlen(hp->h_name) + 1);
+
+  pp = hp->h_aliases;
+  while (*pp) {
+    bytes_needed += (strlen(*pp++) + 1 + sizeof(char*));
+    ++alias_count;
+  }
+  pp = hp->h_addr_list;
+  while (*pp++) {
+    bytes_needed += (hp->h_length + sizeof(char*));
+    ++addr_count;
+  }
+  /* Reserve space for 2 nulls to terminate h_aliases and h_addr_list */
+  bytes_needed += (2 * sizeof(char*));
+
+  /* Allocate memory */
+  new_hp = (struct Hostent*) MyMalloc(sizeof(struct Hostent) + bytes_needed);
+
+  new_hp->h.h_addrtype = hp->h_addrtype;
+  new_hp->h.h_length = hp->h_length;
+
+  /* first write the address list */
+  pp = hp->h_addr_list;
+  ap = new_hp->h.h_addr_list =
+      (char**)(new_hp->buf + ((alias_count + 1) * sizeof(char*)));
+  p = (char*)ap + ((addr_count + 1) * sizeof(char*));
+  while (*pp)
+  {
+    *ap++ = p;
+    memcpy(p, *pp++, hp->h_length);
+    p += hp->h_length;
+  }
+  *ap = 0;
+  /* next write the name */
+  new_hp->h.h_name = p;
+  strcpy(p, hp->h_name);
+  p += (strlen(p) + 1);
+
+  /* last write the alias list */
+  pp = hp->h_aliases;
+  ap = new_hp->h.h_aliases = (char**) new_hp->buf;
+  while (*pp) {
+    *ap++ = p;
+    strcpy(p, *pp++);
+    p += (strlen(p) + 1);
+  }
+  *ap = 0;
+  return (struct hostent*) new_hp;
+}
+
 /*
  * resolver_read - read a dns reply from the nameserver and process it.
  * return 0 if nothing was read from the socket, otherwise return 1
  */
 int resolver_read(void)
 {
-  u_char             buf[sizeof(HEADER) + MAXPACKET];
+  unsigned char      buf[sizeof(HEADER) + MAXPACKET];
   HEADER*            header       = 0;
   struct ResRequest* request      = 0;
-  struct CacheEntry* cp           = 0;
   unsigned int       rc           = 0;
   int                answer_count = 0;
   struct sockaddr_in sin;
@@ -1070,7 +1039,8 @@ int resolver_read(void)
    * check against possibly fake replies
    */
   if (!res_ourserver(&_res, &sin)) {
-    Debug((DEBUG_DNS, "Resolver: fake reply from: %s", (const char*) &sin.sin_addr));
+    Debug((DEBUG_DNS, "Resolver: fake reply from: %s",
+           (const char*) &sin.sin_addr));
     ++reinfo.re_unkrep;
     return 1;
   }
@@ -1122,40 +1092,35 @@ int resolver_read(void)
    */
   answer_count = proc_answer(request, header, buf, buf + rc);
   if (answer_count) {
+    struct hostent* hp = 0;
     if (T_PTR == request->type) {
-      struct DNSReply* reply = 0;
-      if (0 == request->he.h.h_name) {
+      if (0 == request->he.h_name) {
         /*
          * got a PTR response with no name, something bogus is happening
          * don't bother trying again, the client address doesn't resolve 
          */
-        (*request->query.callback)(request->query.vptr, reply);
+        (*request->query.callback)(request->query.vptr, hp);
         rem_request(request); 
         return 1;
       }
       Debug((DEBUG_DNS, "relookup %s <-> %s",
-             request->he.h.h_name, ircd_ntoa((char*) &request->addr)));
+             request->he.h_name, ircd_ntoa((char*) &request->addr)));
       /*
        * Lookup the 'authoritive' name that we were given for the
        * ip#.  By using this call rather than regenerating the
        * type we automatically gain the use of the cache with no
        * extra kludges.
        */
-      reply = gethost_byname(request->he.h.h_name, &request->query);
-      if (reply) {
-        (*request->query.callback)(request->query.vptr, reply);
-      }
-      else {
-        /*
-         * If name wasn't found, a request has been queued and it will
-         * be the last one queued.  This is rather nasty way to keep
-         * a host alias with the query. -avalon
-         */
-        MyFree(requestListTail->he.buf);
-        requestListTail->he.buf = request->he.buf;
-        request->he.buf = 0;
-        memcpy(&requestListTail->he.h, &request->he.h, sizeof(struct hostent));
-      }
+      gethost_byname(request->he.h_name, &request->query);
+      /*
+       * If name wasn't found, a request has been queued and it will
+       * be the last one queued.  This is rather nasty way to keep
+       * a host alias with the query. -avalon
+       */
+      MyFree(requestListTail->buf);
+      requestListTail->buf = request->buf;
+      request->buf = 0;
+      memcpy(&requestListTail->he, &request->he, sizeof(struct hostent));
       rem_request(request);
     }
     else {
@@ -1166,12 +1131,9 @@ int resolver_read(void)
        * PTR returned a CNAME, cp was not checked before so the
        * callback was being called with a value of 0x2C != NULL.
        */
-      struct DNSReply* reply = 0;
-      if (validate_hostent(&request->he.h)) {
-        if ((cp = make_cache(request)))
-          reply = &cp->reply;
-      }
-      (*request->query.callback)(request->query.vptr, reply);
+      if (validate_hostent(&request->he))
+        hp = dup_hostent(&request->he);
+      (*request->query.callback)(request->query.vptr, hp);
       rem_request(request);
     }
   }
@@ -1198,563 +1160,17 @@ void resolver_read_multiple(int count)
   }
 }
 
-static size_t calc_hostent_buffer_size(const struct hostent* hp)
-{
-  char** p;
-  size_t count = 0;
-  assert(0 != hp);
-
-  /*
-   * space for name
-   */
-  count += (strlen(hp->h_name) + 1);
-  /*
-   * space for aliases
-   */
-  for (p = hp->h_aliases; *p; ++p)
-    count += (strlen(*p) + 1 + sizeof(char*));
-  /*
-   * space for addresses
-   */
-  for (p = hp->h_addr_list; *p; ++p)
-    count += (hp->h_length + sizeof(char*));
-  /*
-   * space for 2 nulls to terminate h_aliases and h_addr_list 
-   */
-  count += (2 * sizeof(char*));
-  return count;
-}
-
-
-/*
- * dup_hostent - Duplicate a hostent struct, allocate only enough memory for
- * the data we're putting in it.
- */
-static void dup_hostent(struct Hostent* new_hp, struct hostent* hp)
-{
-  char*  p;
-  char** ap;
-  char** pp;
-  int    alias_count = 0;
-  int    addr_count = 0;
-  size_t bytes_needed = 0;
-
-  assert(0 != new_hp);
-  assert(0 != hp);
-
-  /* how much buffer do we need? */
-  bytes_needed += (strlen(hp->h_name) + 1);
-
-  pp = hp->h_aliases;
-  while (*pp) {
-    bytes_needed += (strlen(*pp++) + 1 + sizeof(char*));
-    ++alias_count;
-  }
-  pp = hp->h_addr_list;
-  while (*pp++) {
-    bytes_needed += (hp->h_length + sizeof(char*));
-    ++addr_count;
-  }
-  /* Reserve space for 2 nulls to terminate h_aliases and h_addr_list */
-  bytes_needed += (2 * sizeof(char*));
-
-  /* Allocate memory */
-  new_hp->buf = (char*) MyMalloc(bytes_needed);
-
-  new_hp->h.h_addrtype = hp->h_addrtype;
-  new_hp->h.h_length = hp->h_length;
-
-  /* first write the address list */
-  pp = hp->h_addr_list;
-  ap = new_hp->h.h_addr_list =
-      (char**)(new_hp->buf + ((alias_count + 1) * sizeof(char*)));
-  p = (char*)ap + ((addr_count + 1) * sizeof(char*));
-  while (*pp)
-  {
-    *ap++ = p;
-    memcpy(p, *pp++, hp->h_length);
-    p += hp->h_length;
-  }
-  *ap = 0;
-  /* next write the name */
-  new_hp->h.h_name = p;
-  strcpy(p, hp->h_name);
-  p += (strlen(p) + 1);
-
-  /* last write the alias list */
-  pp = hp->h_aliases;
-  ap = new_hp->h.h_aliases = (char**) new_hp->buf;
-  while (*pp) {
-    *ap++ = p;
-    strcpy(p, *pp++);
-    p += (strlen(p) + 1);
-  }
-  *ap = 0;
-}
-
-/*
- * update_hostent - Add records to a Hostent struct in place.
- */
-static void update_hostent(struct Hostent* hp, char** addr, char** alias)
-{
-  char*  p;
-  char** ap;
-  char** pp;
-  int    alias_count = 0;
-  int    addr_count = 0;
-  char*  buf = NULL;
-  size_t bytes_needed = 0;
-
-  if (!hp || !hp->buf)
-    return;
-
-  /* how much buffer do we need? */
-  bytes_needed = strlen(hp->h.h_name) + 1;
-  pp = hp->h.h_aliases;
-  while (*pp) {
-    bytes_needed += (strlen(*pp++) + 1 + sizeof(char*));
-    ++alias_count;
-  }
-  if (alias) {
-    pp = alias;
-    while (*pp) {
-      bytes_needed += (strlen(*pp++) + 1 + sizeof(char*));
-      ++alias_count;
-    }
-  }
-  pp = hp->h.h_addr_list;
-  while (*pp++) {
-    bytes_needed += (hp->h.h_length + sizeof(char*));
-    ++addr_count;
-  }
-  if (addr) {
-    pp = addr;
-    while (*pp++) {
-      bytes_needed += (hp->h.h_length + sizeof(char*));
-      ++addr_count;
-    }
-  }
-  /* Reserve space for 2 nulls to terminate h_aliases and h_addr_list */
-  bytes_needed += 2 * sizeof(char*);
-
-  /* Allocate memory */
-  buf = (char*) MyMalloc(bytes_needed);
-  assert(0 != buf);
-
-  /* first write the address list */
-  pp = hp->h.h_addr_list;
-  ap = hp->h.h_addr_list =
-      (char**)(buf + ((alias_count + 1) * sizeof(char*)));
-  p = (char*)ap + ((addr_count + 1) * sizeof(char*));
-  while (*pp) {
-    memcpy(p, *pp++, hp->h.h_length);
-    *ap++ = p;
-    p += hp->h.h_length;
-  }
-  if (addr) {
-    while (*addr) {
-      memcpy(p, *addr++, hp->h.h_length);
-      *ap++ = p;
-      p += hp->h.h_length;
-    }
-  }
-  *ap = 0;
-
-  /* next write the name */
-  strcpy(p, hp->h.h_name);
-  hp->h.h_name = p;
-  p += (strlen(p) + 1);
-
-  /* last write the alias list */
-  pp = hp->h.h_aliases;
-  ap = hp->h.h_aliases = (char**) buf;
-  while (*pp) {
-    strcpy(p, *pp++);
-    *ap++ = p;
-    p += (strlen(p) + 1);
-  }
-  if (alias) {
-    while (*alias) {
-      strcpy(p, *alias++);
-      *ap++ = p;
-      p += (strlen(p) + 1);
-    }
-  }
-  *ap = 0;
-  /* release the old buffer */
-  p = hp->buf;
-  hp->buf = buf;
-  MyFree(p);
-}
-
-/*
- * hash_number - IP address hash function
- */
-static int hash_number(const unsigned char* ip)
-{
-  /* could use loop but slower */
-  unsigned int hashv;
-  const u_char* p = (const u_char*) ip;
-
-  assert(0 != p);
-
-  hashv = *p++;
-  hashv += hashv + *p++;
-  hashv += hashv + *p++;
-  hashv += hashv + *p;
-  hashv %= ARES_CACSIZE;
-  return hashv;
-}
-
-/*
- * hash_name - hostname hash function
- */
-static int hash_name(const char* name)
-{
-  unsigned int hashv = 0;
-  const u_char* p = (const u_char*) name;
-
-  assert(0 != p);
-
-  for (; *p && *p != '.'; ++p)
-    hashv += *p;
-  hashv %= ARES_CACSIZE;
-  return hashv;
-}
-
-/*
- * add_to_cache - Add a new cache item to the queue and hash table.
- */
-static struct CacheEntry* add_to_cache(struct CacheEntry* ocp)
-{
-  int  hashv;
-
-  assert(0 != ocp);
-
-  ocp->list_next = cacheTop;
-  cacheTop = ocp;
-
-  hashv = hash_name(ocp->he.h.h_name);
-
-  ocp->hname_next = hashtable[hashv].name_list;
-  hashtable[hashv].name_list = ocp;
-
-  hashv = hash_number((const unsigned char*) ocp->he.h.h_addr);
-
-  ocp->hnum_next = hashtable[hashv].num_list;
-  hashtable[hashv].num_list = ocp;
-
-  /*
-   * LRU deletion of excessive cache entries.
-   */
-  if (++cachedCount > MAXCACHED) {
-    struct CacheEntry* cp;
-    struct CacheEntry* cp_next;
-    for (cp = ocp->list_next; cp; cp = cp_next) {
-      cp_next = cp->list_next;
-      rem_cache(cp);
-    }
-  }
-  ++cainfo.ca_adds;
-  return ocp;
-}
-
-/*
- * update_list - does not alter the cache structure passed. It is assumed that
- * it already contains the correct expire time, if it is a new entry. Old
- * entries have the expirey time updated.
-*/
-static void update_list(struct ResRequest* request, struct CacheEntry* cachep)
-{
-  struct CacheEntry*  cp = cachep;
-  char*    s;
-  char*    t;
-  int      i;
-  int      j;
-  char**   ap;
-  char*    addrs[RES_MAXADDRS + 1];
-  char*    aliases[RES_MAXALIASES + 1];
-
-  /*
-   * search for the new cache item in the cache list by hostname.
-   * If found, move the entry to the top of the list and return.
-   */
-  ++cainfo.ca_updates;
-
-  if (!request)
-    return;
-  /*
-   * Compare the cache entry against the new record.  Add any
-   * previously missing names for this entry.
-   */
-  *aliases = 0;
-  ap = aliases;
-  for (i = 0, s = request->he.h.h_name; s; s = request->he.h.h_aliases[i++]) {
-    for (j = 0, t = cp->he.h.h_name; t; t = cp->he.h.h_aliases[j++]) {
-      if (0 == ircd_strcmp(t, s))
-        break;
-    }
-    if (!t) {
-      *ap++ = s;
-      *ap = 0;
-    }
-  }
-  /*
-   * Do the same again for IP#'s.
-   */
-  *addrs = 0;
-  ap = addrs;
-  for (i = 0; (s = request->he.h.h_addr_list[i]); i++) {
-    for (j = 0; (t = cp->he.h.h_addr_list[j]); j++) {
-      if (!memcmp(t, s, sizeof(struct in_addr)))
-        break;
-    }
-    if (!t) {
-      *ap++ = s;
-      *ap = 0;
-    }
-  }
-  if (*addrs || *aliases)
-    update_hostent(&cp->he, addrs, aliases);
-}
-
-/*
- * find_cache_name - find name in nameserver cache
- */
-static struct CacheEntry* find_cache_name(const char* name)
-{
-  struct CacheEntry* cp;
-  char*   s;
-  int     hashv;
-  int     i;
-
-  assert(0 != name);
-  hashv = hash_name(name);
-
-  cp = hashtable[hashv].name_list;
-
-  for (; cp; cp = cp->hname_next) {
-    for (i = 0, s = cp->he.h.h_name; s; s = cp->he.h.h_aliases[i++]) {
-      if (0 == ircd_strcmp(s, name)) {
-        ++cainfo.ca_na_hits;
-        return cp;
-      }
-    }
-  }
-
-  for (cp = cacheTop; cp; cp = cp->list_next) {
-    /*
-     * if no aliases or the hash value matches, we've already
-     * done this entry and all possiblilities concerning it.
-     */
-    if (!cp->he.h.h_name || hashv == hash_name(cp->he.h.h_name))
-      continue;
-    for (i = 0, s = cp->he.h.h_aliases[i]; s; s = cp->he.h.h_aliases[++i]) {
-      if (0 == ircd_strcmp(name, s)) {
-        ++cainfo.ca_na_hits;
-        return cp;
-      }
-    }
-  }
-  return NULL;
-}
-
-/*
- * find_cache_number - find a cache entry by ip# and update its expire time
- */
-static struct CacheEntry* find_cache_number(struct ResRequest* request,
-                                            const char* addr)
-{
-  struct CacheEntry* cp;
-  int     hashv;
-  int     i;
-
-  assert(0 != addr);
-  hashv = hash_number((const unsigned char*) addr);
-  cp = hashtable[hashv].num_list;
-
-  for (; cp; cp = cp->hnum_next) {
-    for (i = 0; cp->he.h.h_addr_list[i]; ++i) {
-      if (!memcmp(cp->he.h.h_addr_list[i], addr, sizeof(struct in_addr))) {
-        ++cainfo.ca_nu_hits;
-        return cp;
-      }
-    }
-  }
-  for (cp = cacheTop; cp; cp = cp->list_next) {
-    /*
-     * single address entry...would have been done by hashed
-     * search above...
-     * if the first IP# has the same hashnumber as the IP# we
-     * are looking for, its been done already.
-     */
-    if (!cp->he.h.h_addr_list[1] || 
-        hashv == hash_number((const unsigned char*) cp->he.h.h_addr_list[0]))
-      continue;
-    for (i = 1; cp->he.h.h_addr_list[i]; ++i) {
-      if (!memcmp(cp->he.h.h_addr_list[i], addr, sizeof(struct in_addr))) {
-        ++cainfo.ca_nu_hits;
-        return cp;
-      }
-    }
-  }
-  return NULL;
-}
-
-static struct CacheEntry* make_cache(struct ResRequest* request)
-{
-  struct CacheEntry* cp;
-  int     i;
-  struct hostent* hp;
-  assert(0 != request);
-
-  hp = &request->he.h;
-  /*
-   * shouldn't happen but it just might...
-   */
-  assert(0 != hp->h_name);
-/*    assert(0 != hp->h_addr_list[0]); */
-  if (!hp->h_name || !hp->h_addr_list[0])
-    return NULL;
-  /*
-   * Make cache entry.  First check to see if the cache already exists
-   * and if so, return a pointer to it.
-   */
-  for (i = 0; hp->h_addr_list[i]; ++i) {
-    if ((cp = find_cache_number(request, hp->h_addr_list[i]))) {
-      update_list(request, cp);
-      return cp;
-    }
-  }
-  /*
-   * a matching entry wasnt found in the cache so go and make one up.
-   */ 
-  cp = (struct CacheEntry*) MyMalloc(sizeof(struct CacheEntry));
-  assert(0 != cp);
-
-  memset(cp, 0, sizeof(struct CacheEntry));
-  dup_hostent(&cp->he, hp);
-  cp->reply.hp = &cp->he.h;
-  /*
-   * hmmm... we could time out the cache after 10 minutes regardless
-   * would that be reasonable since we don't save the reply?
-   */ 
-  if (request->ttl < AR_TTL) {
-    ++reinfo.re_shortttl;
-    cp->ttl = AR_TTL;
-  }
-  else
-    cp->ttl = request->ttl;
-  cp->expireat = CurrentTime + cp->ttl;
-  return add_to_cache(cp);
-}
-
-/*
- * rem_cache - delete a cache entry from the cache structures 
- * and lists and return all memory used for the cache back to the memory pool.
- */
-static void rem_cache(struct CacheEntry* ocp)
-{
-  struct CacheEntry** cp;
-  int                 hashv;
-  struct hostent*     hp;
-  assert(0 != ocp);
-
-
-  if (0 < ocp->reply.ref_count) {
-    if (ocp->expireat < CurrentTime) {
-      ocp->expireat = CurrentTime + AR_TTL;
-      Debug((DEBUG_DNS, "Resolver: referenced cache entry not removed for: %s",
-            ocp->he.h.h_name));
-    }
-    return;
-  }
-  /*
-   * remove cache entry from linked list
-   */
-  for (cp = &cacheTop; *cp; cp = &((*cp)->list_next)) {
-    if (*cp == ocp) {
-      *cp = ocp->list_next;
-      break;
-    }
-  }
-  hp = &ocp->he.h;
-  /*
-   * remove cache entry from hashed name list
-   */
-  assert(0 != hp->h_name);
-  hashv = hash_name(hp->h_name);
-
-  for (cp = &hashtable[hashv].name_list; *cp; cp = &((*cp)->hname_next)) {
-    if (*cp == ocp) {
-      *cp = ocp->hname_next;
-      break;
-    }
-  }
-  /*
-   * remove cache entry from hashed number list
-   */
-  hashv = hash_number((const unsigned char*) hp->h_addr);
-  assert(-1 < hashv);
-
-  for (cp = &hashtable[hashv].num_list; *cp; cp = &((*cp)->hnum_next)) {
-    if (*cp == ocp) {
-      *cp = ocp->hnum_next;
-      break;
-    }
-  }
-  /*
-   * free memory used to hold the various host names and the array
-   * of alias pointers.
-   */
-  MyFree(ocp->he.buf);
-  MyFree(ocp);
-  --cachedCount;
-  ++cainfo.ca_dels;
-}
-
-void flush_resolver_cache(void)
-{
-  /*
-   * stubbed - iterate cache and remove everything that isn't referenced
-   */
-}
-
 /*
  * m_dns - dns status query
  */
 int m_dns(struct Client *cptr, struct Client *sptr, int parc, char *parv[])
 {
 #if !defined(NDEBUG)
-  struct CacheEntry* cp;
-  int     i;
-  struct hostent* hp;
-
-  if (parv[1] && *parv[1] == 'l') {
-    for(cp = cacheTop; cp; cp = cp->list_next) {
-      hp = &cp->he.h;
-      sendcmdto_one(&me, CMD_NOTICE, sptr, "%C :Ex %d ttl %d host %s(%s)",
-                   sptr, cp->expireat - CurrentTime, cp->ttl,
-                   hp->h_name, ircd_ntoa(hp->h_addr));
-      for (i = 0; hp->h_aliases[i]; i++)
-        sendcmdto_one(&me, CMD_NOTICE, sptr, "%C : %s = %s (CN)", sptr,
-                     hp->h_name, hp->h_aliases[i]);
-      for (i = 1; hp->h_addr_list[i]; i++)
-        sendcmdto_one(&me, CMD_NOTICE, sptr, "%C : %s = %s (IP)", sptr,
-                     hp->h_name, ircd_ntoa(hp->h_addr_list[i]));
-    }
-    return 0;
-  }
   if (parv[1] && *parv[1] == 'd') {
     sendcmdto_one(&me, CMD_NOTICE, sptr, "%C :ResolverFileDescriptor = %d", 
                  sptr, ResolverFileDescriptor);
     return 0;
   }
-  sendcmdto_one(&me, CMD_NOTICE, sptr,"%C :Ca %d Cd %d Ce %d Cl %d Ch %d:%d "
-               "Cu %d", sptr,
-               cainfo.ca_adds, cainfo.ca_dels, cainfo.ca_expires,
-               cainfo.ca_lookups, cainfo.ca_na_hits, cainfo.ca_nu_hits, 
-               cainfo.ca_updates);
   
   sendcmdto_one(&me, CMD_NOTICE, sptr,"%C :Re %d Rl %d/%d Rp %d Rq %d",
                sptr, reinfo.re_errors, reinfo.re_nu_look,
@@ -1768,36 +1184,21 @@ int m_dns(struct Client *cptr, struct Client *sptr, int parc, char *parv[])
 
 size_t cres_mem(struct Client* sptr)
 {
-  struct CacheEntry* entry;
   struct ResRequest* request;
-  size_t cache_mem     = 0;
   size_t request_mem   = 0;
-  int    cache_count   = 0;
   int    request_count = 0;
 
-  for (entry = cacheTop; entry; entry = entry->list_next) {
-    cache_mem += sizeof(struct CacheEntry);
-    cache_mem += calc_hostent_buffer_size(&entry->he.h); 
-    ++cache_count;
-  }
   for (request = requestListHead; request; request = request->next) {
     request_mem += sizeof(struct ResRequest);
     if (request->name)
       request_mem += strlen(request->name) + 1; 
-    if (request->he.buf)
+    if (request->buf)
       request_mem += MAXGETHOSTLEN + 1;
     ++request_count;
   }
 
-  if (cachedCount != cache_count) {
-    send_reply(sptr, SND_EXPLICIT | RPL_STATSDEBUG,
-              ":Resolver: cache count mismatch: %d != %d", cachedCount,
-              cache_count);
-    assert(cachedCount == cache_count);
-  }
   send_reply(sptr, SND_EXPLICIT | RPL_STATSDEBUG,
-            ":Resolver: cache %d(%d) requests %d(%d)", cache_count,
-            cache_mem, request_count, request_mem);
-  return cache_mem + request_mem;
+            ":Resolver: requests %d(%d)", request_count, request_mem);
+  return request_mem;
 }
 
index b9019ecc284d1f30b9c1e25400cadd98230c952e..f00e83f8043e534dbc30d4709bfaac6fb72255d2 100644 (file)
@@ -337,11 +337,10 @@ static void auth_kill_client(struct AuthRequest* auth)
  * set the client on it's way to a connection completion, regardless
  * of success of failure
  */
-static void auth_dns_callback(void* vptr, struct DNSReply* reply)
+static void auth_dns_callback(void* vptr, struct hostent* hp)
 {
   struct AuthRequest* auth = (struct AuthRequest*) vptr;
-
-  assert(0 != auth);
+  assert(auth);
   /*
    * need to do this here so auth_kill_client doesn't
    * try have the resolver delete the query it's about
@@ -349,10 +348,8 @@ static void auth_dns_callback(void* vptr, struct DNSReply* reply)
    */
   ClearDNSPending(auth);
 
-  if (reply) {
-    const struct hostent* hp = reply->hp;
+  if (hp) {
     int i;
-    assert(0 != hp);
     /*
      * Verify that the host to ip mapping is correct both ways and that
      * the ip#(s) for the socket is listed for the host.
@@ -380,8 +377,7 @@ static void auth_dns_callback(void* vptr, struct DNSReply* reply)
     }
     else
     {
-      ++reply->ref_count;
-      cli_dns_reply(auth->client) = reply;
+      cli_dns_reply(auth->client) = hp;
       ircd_strncpy(cli_sockhost(auth->client), hp->h_name, HOSTLEN);
       if (IsUserPort(auth->client))
         sendheader(auth->client, REPORT_FIN_DNS);
@@ -620,18 +616,8 @@ void start_auth(struct Client* client)
       if (IsUserPort(auth->client))
        sendheader(client, REPORT_DO_DNS);
 
-      cli_dns_reply(client) = gethost_byaddr((const char*) &(cli_ip(client)),
-                                            &query);
-
-      if (cli_dns_reply(client)) {
-       ++(cli_dns_reply(client))->ref_count;
-       ircd_strncpy(cli_sockhost(client), cli_dns_reply(client)->hp->h_name,
-                    HOSTLEN);
-       if (IsUserPort(auth->client))
-         sendheader(client, REPORT_FIN_DNSC);
-       Debug((DEBUG_LIST, "DNS entry for %p was cached", auth->client));
-      } else
-       SetDNSPending(auth);
+      gethost_byaddr((const char*) &(cli_ip(client)), &query);
+      SetDNSPending(auth);
     }
   }
 
index 010d631151a8497cedc6192f9861015fefb682be..5498a0c7154c96669fe58d6521faae9282ab8f15 100644 (file)
@@ -27,6 +27,7 @@
 #include "channel.h"
 #include "class.h"
 #include "hash.h"
+#include "ircd_alloc.h"
 #include "ircd_log.h"
 #include "ircd_features.h"
 #include "ircd_osdep.h"
@@ -176,13 +177,15 @@ void report_error(const char* text, const char* who, int err)
  * a non-null pointer, otherwise reply will be null.
  * if successful start the connection, otherwise notify opers
  */
-static void connect_dns_callback(void* vptr, struct DNSReply* reply)
+static void connect_dns_callback(void* vptr, struct hostent* hp)
 {
   struct ConfItem* aconf = (struct ConfItem*) vptr;
+  assert(aconf);
   aconf->dns_pending = 0;
-  if (reply) {
-    memcpy(&aconf->ipnum, reply->hp->h_addr, sizeof(struct in_addr));
-    connect_server(aconf, 0, reply);
+  if (hp) {
+    memcpy(&aconf->ipnum, hp->h_addr, sizeof(struct in_addr));
+    MyFree(hp);
+    connect_server(aconf, 0);
   }
   else
     sendto_opmask_butone(0, SNO_OLDSNO, "Connect to %s failed: host lookup",
@@ -393,8 +396,7 @@ void release_dns_reply(struct Client* cptr)
   assert(MyConnect(cptr));
 
   if (cli_dns_reply(cptr)) {
-    assert(0 < cli_dns_reply(cptr)->ref_count);
-    --(cli_dns_reply(cptr))->ref_count;
+    MyFree(cli_dns_reply(cptr));
     cli_dns_reply(cptr) = 0;
   }
 }
@@ -816,8 +818,7 @@ static int read_packet(struct Client *cptr, int socket_ready)
  * be done, we loose the information about who started the connection and
  * it's considered an auto connect.
  */
-int connect_server(struct ConfItem* aconf, struct Client* by,
-                   struct DNSReply* reply)
+int connect_server(struct ConfItem* aconf, struct Client* by)
 {
   struct Client*   cptr = 0;
   assert(0 != aconf);
@@ -853,9 +854,8 @@ int connect_server(struct ConfItem* aconf, struct Client* by,
    * not a ip# string, then try and find the appropriate host record.
    */
   if (INADDR_NONE == aconf->ipnum.s_addr) {
-    char buf[HOSTLEN + 1];
-    assert(0 == reply);
     if (INADDR_NONE == (aconf->ipnum.s_addr = inet_addr(aconf->host))) {
+      char buf[HOSTLEN + 1];
       struct DNSQuery  query;
 
       query.vptr     = aconf;
@@ -863,19 +863,12 @@ int connect_server(struct ConfItem* aconf, struct Client* by,
       host_from_uh(buf, aconf->host, HOSTLEN);
       buf[HOSTLEN] = '\0';
 
-      reply = gethost_byname(buf, &query);
-
-      if (!reply) {
-        aconf->dns_pending = 1;
-        return 0;
-      }
-      memcpy(&aconf->ipnum, reply->hp->h_addr, sizeof(struct in_addr));
+      gethost_byname(buf, &query);
+      aconf->dns_pending = 1;
     }
+    return 0;
   }
   cptr = make_client(NULL, STAT_UNKNOWN_SERVER);
-  if (reply)
-    ++reply->ref_count;
-  cli_dns_reply(cptr) = reply;
 
   /*
    * Copy these in so we have something for error detection.
index d09dfd8c8b8b29d8b1168c4058c06ffd83983607..1bbab6682299f10a5a672118f290d648372312e0 100644 (file)
@@ -202,12 +202,15 @@ static void detach_conf(struct Client* cptr, struct ConfItem* aconf)
  * a non-null pointer, otherwise hp will be null.
  * if successful save hp in the conf item it was called with
  */
-static void conf_dns_callback(void* vptr, struct DNSReply* reply)
+static void conf_dns_callback(void* vptr, struct hostent* hp)
 {
   struct ConfItem* aconf = (struct ConfItem*) vptr;
+  assert(aconf);
   aconf->dns_pending = 0;
-  if (reply)
-    memcpy(&aconf->ipnum, reply->hp->h_addr, sizeof(struct in_addr));
+  if (hp) {
+    memcpy(&aconf->ipnum, hp->h_addr, sizeof(struct in_addr));
+    MyFree(hp);
+  }
 }
 
 /*
@@ -215,9 +218,8 @@ static void conf_dns_callback(void* vptr, struct DNSReply* reply)
  * if the conf entry is currently doing a ns lookup do nothing, otherwise
  * if the lookup returns a null pointer, set the conf dns_pending flag
  */
-static struct DNSReply* conf_dns_lookup(struct ConfItem* aconf)
+static void conf_dns_lookup(struct ConfItem* aconf)
 {
-  struct DNSReply* dns_reply = 0;
   if (!aconf->dns_pending) {
     char            buf[HOSTLEN + 1];
     struct DNSQuery query;
@@ -226,10 +228,9 @@ static struct DNSReply* conf_dns_lookup(struct ConfItem* aconf)
     host_from_uh(buf, aconf->host, HOSTLEN);
     buf[HOSTLEN] = '\0';
 
-    if (0 == (dns_reply = gethost_byname(buf, &query)))
-      aconf->dns_pending = 1;
+    gethost_byname(buf, &query);
+    aconf->dns_pending = 1;
   }
-  return dns_reply;
 }
 
 
@@ -242,8 +243,6 @@ static struct DNSReply* conf_dns_lookup(struct ConfItem* aconf)
 void
 lookup_confhost(struct ConfItem *aconf)
 {
-  struct DNSReply* reply;
-
   if (EmptyString(aconf->host) || EmptyString(aconf->name)) {
     Debug((DEBUG_ERROR, "Host/server name error: (%s) (%s)",
            aconf->host, aconf->name));
@@ -264,8 +263,8 @@ lookup_confhost(struct ConfItem *aconf)
             aconf->host, aconf->name));
     }
   }
-  else if ((reply = conf_dns_lookup(aconf)))
-    memcpy(&aconf->ipnum, reply->hp->h_addr, sizeof(struct in_addr));
+  else 
+    conf_dns_lookup(aconf);
 }
 
 /*
@@ -375,7 +374,7 @@ enum AuthorizationCheckResult attach_iline(struct Client*  cptr)
   assert(0 != cptr);
 
   if (cli_dns_reply(cptr))
-    hp = cli_dns_reply(cptr)->hp;
+    hp = cli_dns_reply(cptr);
 
   for (aconf = GlobalConfList; aconf; aconf = aconf->next) {
     if (aconf->status != CONF_CLIENT)
@@ -1047,7 +1046,7 @@ int rehash(struct Client *cptr, int sig)
   clearNickJupes();
 
   if (sig != 2)
-    flush_resolver_cache();
+    restart_resolver();
 
   class_mark_delete();
   mark_listeners_closing();
@@ -1283,7 +1282,7 @@ int conf_check_server(struct Client *cptr)
   if (!c_conf) {
     if (cli_dns_reply(cptr)) {
       int             i;
-      struct hostent* hp = cli_dns_reply(cptr)->hp;
+      struct hostent* hp = cli_dns_reply(cptr);
       const char*     name = hp->h_name;
       /*
        * If we are missing a C or N line from above, search for
@@ -1340,7 +1339,8 @@ int conf_check_server(struct Client *cptr)
   if (INADDR_NONE == c_conf->ipnum.s_addr)
     c_conf->ipnum.s_addr = cli_ip(cptr).s_addr;
 
-  Debug((DEBUG_DNS, "sv_cl: access ok: %s[%s]", cli_name(cptr), cli_sockhost(cptr)));
+  Debug((DEBUG_DNS, "sv_cl: access ok: %s[%s]",
+         cli_name(cptr), cli_sockhost(cptr)));
   return 0;
 }