浏览代码

r17554@catbus: nickm | 2008-01-10 12:48:29 -0500
Do not send bridge descriptors over unencrypted connections.


svn:r13094

Nick Mathewson 18 年之前
父节点
当前提交
04263648c4
共有 7 个文件被更改,包括 48 次插入9 次删除
  1. 4 0
      ChangeLog
  2. 1 1
      doc/TODO
  3. 2 1
      src/or/directory.c
  4. 30 5
      src/or/dirserv.c
  5. 4 1
      src/or/or.h
  6. 1 0
      src/or/routerlist.c
  7. 6 1
      src/or/routerparse.c

+ 4 - 0
ChangeLog

@@ -54,6 +54,10 @@ Changes in version 0.2.0.16-alpha - 2008-01-??
     - Actually implement the -s option to tor-gencert.
     - Actually implement the -s option to tor-gencert.
     - Add a manual page for tor-gencert.
     - Add a manual page for tor-gencert.
 
 
+  o Minor features (bridges):
+    - Bridge authorities no longer serve bridge descriptors over unencrypted
+      connections.
+
   o Minor features (other):
   o Minor features (other):
     - Add hidden services and DNSPorts to the list of things that make
     - Add hidden services and DNSPorts to the list of things that make
       Tor accept that it has running ports.  Change starting Tor with
       Tor accept that it has running ports.  Change starting Tor with

+ 1 - 1
doc/TODO

@@ -28,7 +28,7 @@ RK- make it easier to set up a private tor network on your own computer
   - Make BEGIN_DIR mandatory for asking questions of bridge authorities?
   - Make BEGIN_DIR mandatory for asking questions of bridge authorities?
     (but only for bridge descriptors. not for ordinary cache stuff.)
     (but only for bridge descriptors. not for ordinary cache stuff.)
     o Implement connection_dir_is_encrypted().
     o Implement connection_dir_is_encrypted().
-    - set up a filter to not answer any bridge descriptors on a
+    o set up a filter to not answer any bridge descriptors on a
       non-encrypted request
       non-encrypted request
   o write a tor-gencert man page
   o write a tor-gencert man page
 
 

+ 2 - 1
src/or/directory.c

@@ -2421,7 +2421,8 @@ directory_handle_command_get(dir_connection_t *conn, const char *headers,
     url += is_extra ? strlen("/tor/extra/") : strlen("/tor/server/");
     url += is_extra ? strlen("/tor/extra/") : strlen("/tor/server/");
     conn->fingerprint_stack = smartlist_create();
     conn->fingerprint_stack = smartlist_create();
     res = dirserv_get_routerdesc_fingerprints(conn->fingerprint_stack, url,
     res = dirserv_get_routerdesc_fingerprints(conn->fingerprint_stack, url,
-                                              &msg);
+                                          &msg,
+                                          !connection_dir_is_encrypted(conn));
 
 
     if (!strcmpstart(url, "fp/")) {
     if (!strcmpstart(url, "fp/")) {
       request_type = deflated?"/tor/server/fp.z":"/tor/server/fp";
       request_type = deflated?"/tor/server/fp.z":"/tor/server/fp";

+ 30 - 5
src/or/dirserv.c

@@ -57,7 +57,9 @@ dirserv_get_status_impl(const char *fp, const char *nickname,
                         const char *platform, const char *contact,
                         const char *platform, const char *contact,
                         const char **msg, int should_log);
                         const char **msg, int should_log);
 static void clear_cached_dir(cached_dir_t *d);
 static void clear_cached_dir(cached_dir_t *d);
-
+static signed_descriptor_t *get_signed_descriptor_by_fp(const char *fp,
+                                                        int extrainfo,
+                                                        time_t publish_cutoff);
 static int dirserv_add_extrainfo(extrainfo_t *ei, const char **msg);
 static int dirserv_add_extrainfo(extrainfo_t *ei, const char **msg);
 
 
 /************** Fingerprint handling code ************/
 /************** Fingerprint handling code ************/
@@ -2571,8 +2573,9 @@ dirserv_get_networkstatus_v2(smartlist_t *result,
  */
  */
 int
 int
 dirserv_get_routerdesc_fingerprints(smartlist_t *fps_out, const char *key,
 dirserv_get_routerdesc_fingerprints(smartlist_t *fps_out, const char *key,
-                                    const char **msg)
+                                    const char **msg, int for_unencrypted_conn)
 {
 {
+  int by_id = 1;
   *msg = NULL;
   *msg = NULL;
 
 
   if (!strcmp(key, "all")) {
   if (!strcmp(key, "all")) {
@@ -2586,6 +2589,7 @@ dirserv_get_routerdesc_fingerprints(smartlist_t *fps_out, const char *key,
       smartlist_add(fps_out,
       smartlist_add(fps_out,
                     tor_memdup(ri->cache_info.identity_digest, DIGEST_LEN));
                     tor_memdup(ri->cache_info.identity_digest, DIGEST_LEN));
   } else if (!strcmpstart(key, "d/")) {
   } else if (!strcmpstart(key, "d/")) {
+    by_id = 0;
     key += strlen("d/");
     key += strlen("d/");
     dir_split_resource_into_fingerprints(key, fps_out, NULL, 1, 1);
     dir_split_resource_into_fingerprints(key, fps_out, NULL, 1, 1);
   } else if (!strcmpstart(key, "fp/")) {
   } else if (!strcmpstart(key, "fp/")) {
@@ -2596,6 +2600,19 @@ dirserv_get_routerdesc_fingerprints(smartlist_t *fps_out, const char *key,
     return -1;
     return -1;
   }
   }
 
 
+  if (for_unencrypted_conn) {
+    /* Remove anything whose purpose isn't general. */
+    SMARTLIST_FOREACH(fps_out, char *, cp, {
+        signed_descriptor_t *sd =
+          by_id ? get_signed_descriptor_by_fp(cp,0,0) :
+                  router_get_by_descriptor_digest(cp);
+        if (sd && !sd->send_unencrypted) {
+          tor_free(cp);
+          SMARTLIST_DEL_CURRENT(fps_out, cp);
+        }
+      });
+  }
+
   if (!smartlist_len(fps_out)) {
   if (!smartlist_len(fps_out)) {
     *msg = "Servers unavailable";
     *msg = "Servers unavailable";
     return -1;
     return -1;
@@ -2618,12 +2635,12 @@ dirserv_get_routerdesc_fingerprints(smartlist_t *fps_out, const char *key,
  * If -1 is returned *<b>msg</b> will be set to an appropriate error
  * If -1 is returned *<b>msg</b> will be set to an appropriate error
  * message.
  * message.
  *
  *
- * (Despite its name, this function is also called from the controller, which
- * exposes a similar means to fetch descriptors.)
+ * XXXX020 rename this function.  IT's only called from the controller.
+ * XXXX020 in fact, refactor this function, mergeing as much as possible.
  */
  */
 int
 int
 dirserv_get_routerdescs(smartlist_t *descs_out, const char *key,
 dirserv_get_routerdescs(smartlist_t *descs_out, const char *key,
-  const char **msg)
+                        const char **msg)
 {
 {
   *msg = NULL;
   *msg = NULL;
 
 
@@ -2938,6 +2955,14 @@ connection_dirserv_add_servers_to_outbuf(dir_connection_t *conn)
     tor_free(fp);
     tor_free(fp);
     if (!sd)
     if (!sd)
       continue;
       continue;
+    if (!connection_dir_is_encrypted(conn) && !sd->send_unencrypted) {
+      /* we did this check once before (so we could have an accurate size
+       * estimate and maybe send a 404 if somebody asked for only bridges on a
+       * connection), but we need to do it again in case a previously
+       * unknown bridge descriptor has shown up between then and now. */
+      continue;
+    }
+
     body = signed_descriptor_get_body(sd);
     body = signed_descriptor_get_body(sd);
     if (conn->zlib_state) {
     if (conn->zlib_state) {
       int last = ! smartlist_len(conn->fingerprint_stack);
       int last = ! smartlist_len(conn->fingerprint_stack);

+ 4 - 1
src/or/or.h

@@ -1245,6 +1245,8 @@ typedef struct signed_descriptor_t {
   /* If true, we got an extrainfo for this item, and the digest was right,
   /* If true, we got an extrainfo for this item, and the digest was right,
    * but it was incompatible. */
    * but it was incompatible. */
   unsigned int extrainfo_is_bogus : 1;
   unsigned int extrainfo_is_bogus : 1;
+  /* If true, we are willing to transmit this item unencrypted. */
+  unsigned int send_unencrypted : 1;
 } signed_descriptor_t;
 } signed_descriptor_t;
 
 
 /** Information about another onion router in the network. */
 /** Information about another onion router in the network. */
@@ -3113,7 +3115,8 @@ void dirserv_get_networkstatus_v2(smartlist_t *result, const char *key);
 void dirserv_get_networkstatus_v2_fingerprints(smartlist_t *result,
 void dirserv_get_networkstatus_v2_fingerprints(smartlist_t *result,
                                                const char *key);
                                                const char *key);
 int dirserv_get_routerdesc_fingerprints(smartlist_t *fps_out, const char *key,
 int dirserv_get_routerdesc_fingerprints(smartlist_t *fps_out, const char *key,
-                                        const char **msg);
+                                        const char **msg,
+                                        int for_unencrypted_conn);
 int dirserv_get_routerdescs(smartlist_t *descs_out, const char *key,
 int dirserv_get_routerdescs(smartlist_t *descs_out, const char *key,
                             const char **msg);
                             const char **msg);
 void dirserv_orconn_tls_done(const char *address,
 void dirserv_orconn_tls_done(const char *address,

+ 1 - 0
src/or/routerlist.c

@@ -4226,6 +4226,7 @@ routerinfo_incompatible_with_extrainfo(routerinfo_t *ri, extrainfo_t *ei,
       goto err; /* Bad signature, or no match. */
       goto err; /* Bad signature, or no match. */
     }
     }
 
 
+    ei->cache_info.send_unencrypted = ri->cache_info.send_unencrypted;
     tor_free(ei->pending_sig);
     tor_free(ei->pending_sig);
   }
   }
 
 

+ 6 - 1
src/or/routerparse.c

@@ -1172,6 +1172,8 @@ router_parse_entry_from_string(const char *s, const char *end,
   } else {
   } else {
     router->purpose = ROUTER_PURPOSE_GENERAL;
     router->purpose = ROUTER_PURPOSE_GENERAL;
   }
   }
+  router->cache_info.send_unencrypted =
+    (router->purpose == ROUTER_PURPOSE_GENERAL) ? 1 : 0;
 
 
   if ((tok = find_first_by_keyword(tokens, K_UPTIME))) {
   if ((tok = find_first_by_keyword(tokens, K_UPTIME))) {
     tor_assert(tok->n_args >= 1);
     tor_assert(tok->n_args >= 1);
@@ -1326,7 +1328,7 @@ extrainfo_parse_entry_from_string(const char *s, const char *end,
   smartlist_t *tokens = NULL;
   smartlist_t *tokens = NULL;
   directory_token_t *tok;
   directory_token_t *tok;
   crypto_pk_env_t *key = NULL;
   crypto_pk_env_t *key = NULL;
-  routerinfo_t *router;
+  routerinfo_t *router = NULL;
 
 
   if (!end) {
   if (!end) {
     end = s + strlen(s);
     end = s + strlen(s);
@@ -1405,6 +1407,9 @@ extrainfo_parse_entry_from_string(const char *s, const char *end,
     if (check_signature_token(digest, tok, key, 0, "extra-info") < 0)
     if (check_signature_token(digest, tok, key, 0, "extra-info") < 0)
       goto err;
       goto err;
 
 
+    if (router)
+      extrainfo->cache_info.send_unencrypted =
+        router->cache_info.send_unencrypted;
   } else {
   } else {
     extrainfo->pending_sig = tor_memdup(tok->object_body,
     extrainfo->pending_sig = tor_memdup(tok->object_body,
                                         tok->object_size);
                                         tok->object_size);