瀏覽代碼

the tor-spec says router->address must be an IP address. so refuse
it if it's not.
(this also fixes some potential security problems with people providing
hostnames as their address and then preferentially resolving them and
partitioning users.)


svn:r4790

Roger Dingledine 19 年之前
父節點
當前提交
5e76bac1dd
共有 2 個文件被更改,包括 13 次插入63 次删除
  1. 7 61
      src/or/routerlist.c
  2. 6 2
      src/or/routerparse.c

+ 7 - 61
src/or/routerlist.c

@@ -27,8 +27,7 @@ router_pick_trusteddirserver_impl(int requireother, int fascistfirewall);
 static void mark_all_trusteddirservers_up(void);
 static int router_nickname_is_in_list(routerinfo_t *router, const char *list);
 static int router_nickname_matches(routerinfo_t *router, const char *nickname);
-static int router_resolve(routerinfo_t *router);
-static int router_resolve_routerlist(routerlist_t *dir);
+static void router_normalize_routerlist(routerlist_t *rl);
 
 /****************************************************************************/
 
@@ -883,9 +882,6 @@ router_add_to_routerlist(routerinfo_t *router, const char **msg)
         log_fn(LOG_DEBUG, "Replacing entry for router '%s/%s' [%s]",
                router->nickname, r->nickname, hex_str(id_digest,DIGEST_LEN));
 //XXXRD        /* Remember whether we trust this router as a dirserver. */
-        /* If the address hasn't changed; no need to re-resolve. */
-        if (!strcasecmp(r->address, router->address))
-          router->addr = r->addr;
         routerinfo_free(r);
         smartlist_set(routerlist->routers, i, router);
         return 0;
@@ -988,12 +984,6 @@ router_load_single_router(const char *s, const char **msg)
     routerinfo_free(ri);
     return 0;
   }
-  if (router_resolve(ri)<0) {
-    log_fn(LOG_WARN, "Couldn't resolve router address '%s'; dropping.", ri->address);
-    *msg = "Couldn't resolve router address.";
-    routerinfo_free(ri);
-    return 0;
-  }
   if (routerlist && routerlist->running_routers) {
     running_routers_t *rr = routerlist->running_routers;
     router_update_status_from_smartlist(ri,
@@ -1061,10 +1051,7 @@ router_load_routerlist_from_directory(const char *s,
     routerlist = new_list;
     control_event_descriptors_changed(routerlist->routers);
   }
-  if (router_resolve_routerlist(routerlist)) {
-    log_fn(LOG_WARN, "Error resolving routerlist");
-    return -1;
-  }
+  router_normalize_routerlist(routerlist);
   if (get_options()->AuthoritativeDir) {
     /* Learn about the descriptors in the directory. */
     dirserv_load_from_directory_string(s);
@@ -1073,67 +1060,26 @@ router_load_routerlist_from_directory(const char *s,
   return 0;
 }
 
-/** Helper function: resolve the hostname for <b>router</b>. */
-static int
-router_resolve(routerinfo_t *router)
-{
-  if (authdir_mode(get_options())) {
-    /* don't let authdirservers do resolves; this is an easy DoS avenue */
-    struct in_addr iaddr;
-    if (!tor_inet_aton(router->address, &iaddr)) { /* not an IP */
-      log_fn(LOG_WARN,"Refusing to resolve non-IP address '%s' for router '%s'",
-             router->address, router->nickname);
-      return -1;
-    }
-    memcpy((void *)&router->addr, &iaddr.s_addr, 4);
-  } else {
-    if (tor_lookup_hostname(router->address, &router->addr) != 0
-        || !router->addr) {
-      log_fn(LOG_WARN,"Could not resolve address '%s' for router '%s'",
-             router->address, router->nickname);
-      return -1;
-    }
-  }
-  router->addr = ntohl(router->addr); /* get it back into host order */
-  return 0;
-}
-
-/** Helper function: resolve every router in rl, and ensure that our own
- * routerinfo is at the front.
+/** Ensure that our own routerinfo is at the front, and remove duplicates
+ * of our routerinfo.
  */
-static int
-router_resolve_routerlist(routerlist_t *rl)
+static void
+router_normalize_routerlist(routerlist_t *rl)
 {
-  int i, remove;
+  int i=0;
   routerinfo_t *r;
-  if (!rl)
-    rl = routerlist;
-
-  i = 0;
   if ((r = router_get_my_routerinfo())) {
     smartlist_insert(rl->routers, 0, routerinfo_copy(r));
     ++i;
   }
 
   for ( ; i < smartlist_len(rl->routers); ++i) {
-    remove = 0;
     r = smartlist_get(rl->routers,i);
     if (router_is_me(r)) {
-      remove = 1;
-    } else if (r->addr) {
-      /* already resolved. */
-    } else if (router_resolve(r)) {
-      log_fn(LOG_WARN, "Couldn't resolve address '%s' for router '%s'; not using",
-             r->address, r->nickname);
-      remove = 1;
-    }
-    if (remove) {
       routerinfo_free(r);
       smartlist_del_keeporder(rl->routers, i--);
     }
   }
-
-  return 0;
 }
 
 /** Decide whether a given addr:port is definitely accepted,

+ 6 - 2
src/or/routerparse.c

@@ -823,6 +823,7 @@ router_parse_entry_from_string(const char *s, const char *end)
   directory_token_t *tok;
   int t;
   int ports_set, bw_set;
+  struct in_addr in;
 
   if (!end) {
     end = s + strlen(s);
@@ -865,7 +866,11 @@ router_parse_entry_from_string(const char *s, const char *end)
       goto err;
     }
     router->address = tor_strdup(tok->args[1]);
-    router->addr = 0;
+    if (!tor_inet_aton(router->address, &in)) {
+      log_fn(LOG_WARN,"Router address is not an IP.");
+      goto err;
+    }
+    router->addr = ntohl(in.s_addr);
 
     if (tok->n_args >= 5) {
       router->or_port = (uint16_t) tor_parse_long(tok->args[2],10,0,65535,NULL,NULL);
@@ -1013,7 +1018,6 @@ router_parse_entry_from_string(const char *s, const char *end)
   }
 
   goto done;
-  return router;
 
  err:
   routerinfo_free(router);