[Author Prev][Author Next][Thread Prev][Thread Next][Author Index][Thread Index]

[or-cvs] r9440: Bring us one step closer to being able to establish an encry (in tor/trunk: . src/or)



Author: arma
Date: 2007-01-27 14:29:16 -0500 (Sat, 27 Jan 2007)
New Revision: 9440

Modified:
   tor/trunk/ChangeLog
   tor/trunk/src/or/circuitbuild.c
   tor/trunk/src/or/circuituse.c
   tor/trunk/src/or/or.h
Log:
Bring us one step closer to being able to establish an encrypted
directory tunnel without knowing a descriptor first. Still not
ready yet. As part of the change, now assume we can use a
create_fast cell if we don't know anything about a router.


Modified: tor/trunk/ChangeLog
===================================================================
--- tor/trunk/ChangeLog	2007-01-27 19:05:45 UTC (rev 9439)
+++ tor/trunk/ChangeLog	2007-01-27 19:29:16 UTC (rev 9440)
@@ -75,6 +75,10 @@
     - Inform the server operator when we decide not to advertise a
       DirPort due to AccountingMax enabled or a low BandwidthRate. It
       was confusing Zax, so now we're hopefully more helpful.
+    - Bring us one step closer to being able to establish an encrypted
+      directory tunnel without knowing a descriptor first. Still not
+      ready yet. As part of the change, now assume we can use a
+      create_fast cell if we don't know anything about a router.
 
   o Minor features (controller):
     - Track reasons for OR connection failure; make these reasons

Modified: tor/trunk/src/or/circuitbuild.c
===================================================================
--- tor/trunk/src/or/circuitbuild.c	2007-01-27 19:05:45 UTC (rev 9439)
+++ tor/trunk/src/or/circuitbuild.c	2007-01-27 19:29:16 UTC (rev 9440)
@@ -519,20 +519,28 @@
 }
 
 /** Return true iff we should send a create_fast cell to build a circuit
- * starting at <b>router</b>.  (If <b>router</b> is NULL, we don't have
- * information on the router, so return false.) */
+ * starting at <b>router</b>. (If <b>router</b> is NULL, we don't have
+ * information on the router, so assume true.) */
 static INLINE int
-should_use_create_fast_for_router(routerinfo_t *router)
+should_use_create_fast_for_router(routerinfo_t *router,
+                                  origin_circuit_t *circ)
 {
   or_options_t *options = get_options();
 
-  if (!options->FastFirstHopPK || server_mode(options))
+  if (!options->FastFirstHopPK) /* create_fast is disabled */
     return 0;
-  else if (!router || !router->platform ||
-           !tor_version_as_new_as(router->platform, "0.1.0.6-rc"))
+  if (router && router->platform &&
+      !tor_version_as_new_as(router->platform, "0.1.0.6-rc")) {
+    /* known not to work */
     return 0;
-  else
-    return 1;
+  }
+  if (server_mode(options) && circ->cpath->extend_info->onion_key) {
+    /* We're a server, and we know an onion key. We can choose.
+     * Prefer to blend in. */
+    return 0;
+  }
+
+  return 1;
 }
 
 /** This is the backbone function for building circuits.
@@ -562,8 +570,13 @@
     log_debug(LD_CIRC,"First skin; sending create cell.");
 
     router = router_get_by_digest(circ->_base.n_conn->identity_digest);
-    fast = should_use_create_fast_for_router(router);
-    if (! fast) {
+    fast = should_use_create_fast_for_router(router, circ);
+    if (!fast && !circ->cpath->extend_info->onion_key) {
+      log_warn(LD_CIRC,
+               "Can't send create_fast, but have no onion key. Failing.");
+      return - END_CIRC_REASON_INTERNAL;
+    }
+    if (!fast) {
       /* We are an OR, or we are connecting to an old Tor: we should
        * send an old slow create cell.
        */
@@ -1722,12 +1735,29 @@
   return info;
 }
 
+/** Allocate and return a new extend_info_t that can be used to build a
+ * circuit to or through the router <b>r</b>. */
+extend_info_t *
+extend_info_from_routerstatus(routerstatus_t *s)
+{
+  extend_info_t *info;
+  tor_assert(s);
+  info = tor_malloc_zero(sizeof(extend_info_t));
+  strlcpy(info->nickname, s->nickname, sizeof(info->nickname));
+  memcpy(info->identity_digest, s->identity_digest, DIGEST_LEN);
+  info->onion_key = NULL; /* routerstatus doesn't include this! */
+  info->addr = s->addr;
+  info->port = s->or_port;
+  return info;
+}
+
 /** Release storage held by an extend_info_t struct. */
 void
 extend_info_free(extend_info_t *info)
 {
   tor_assert(info);
-  crypto_free_pk_env(info->onion_key);
+  if (info->onion_key)
+    crypto_free_pk_env(info->onion_key);
   tor_free(info);
 }
 
@@ -1740,7 +1770,10 @@
   tor_assert(info);
   newinfo = tor_malloc(sizeof(extend_info_t));
   memcpy(newinfo, info, sizeof(extend_info_t));
-  newinfo->onion_key = crypto_pk_dup_key(info->onion_key);
+  if (info->onion_key)
+    newinfo->onion_key = crypto_pk_dup_key(info->onion_key);
+  else
+    newinfo->onion_key = NULL;
   return newinfo;
 }
 

Modified: tor/trunk/src/or/circuituse.c
===================================================================
--- tor/trunk/src/or/circuituse.c	2007-01-27 19:05:45 UTC (rev 9439)
+++ tor/trunk/src/or/circuituse.c	2007-01-27 19:29:16 UTC (rev 9440)
@@ -1011,18 +1011,38 @@
       if (conn->chosen_exit_name) {
         routerinfo_t *r;
         int opt = conn->_base.chosen_exit_optional;
-        if (!(r = router_get_by_nickname(conn->chosen_exit_name, 1))) {
-          log_fn(opt ? LOG_INFO : LOG_WARN, LD_APP,
-                 "Requested exit point '%s' is not known. %s.",
-                 conn->chosen_exit_name, opt ? "Trying others" : "Closing");
-          if (opt) {
-            conn->_base.chosen_exit_optional = 0;
-            tor_free(conn->chosen_exit_name);
-            return 0;
+        r = router_get_by_nickname(conn->chosen_exit_name, 1);
+        if (r) {
+          extend_info = extend_info_from_router(r);
+        } else {
+          if (want_onehop && conn->chosen_exit_name[0] == '$') {
+            /* We're asking for a one-hop circuit to a router that
+             * we don't have a routerinfo about. Hope we have a
+             * routerstatus or equivalent. */
+            routerstatus_t *s =
+              routerstatus_get_by_hexdigest(conn->chosen_exit_name+1);
+            if (s) {
+              extend_info = extend_info_from_routerstatus(s);
+            } else {
+              log_warn(LD_APP,
+                       "Requested router '%s' is not known. Closing.",
+                       conn->chosen_exit_name);
+              return -1;
+            }
+          } else {
+            /* We will need an onion key for the router, and we
+             * don't have one. Refuse or relax requirements. */
+            log_fn(opt ? LOG_INFO : LOG_WARN, LD_APP,
+                   "Requested exit point '%s' is not known. %s.",
+                   conn->chosen_exit_name, opt ? "Trying others" : "Closing");
+            if (opt) {
+              conn->_base.chosen_exit_optional = 0;
+              tor_free(conn->chosen_exit_name);
+              return 0;
+            }
+            return -1;
           }
-          return -1;
         }
-        extend_info = extend_info_from_router(r);
       }
     }
 

Modified: tor/trunk/src/or/or.h
===================================================================
--- tor/trunk/src/or/or.h	2007-01-27 19:05:45 UTC (rev 9439)
+++ tor/trunk/src/or/or.h	2007-01-27 19:29:16 UTC (rev 9440)
@@ -1176,9 +1176,10 @@
   tor_mmap_t *mmap_descriptors;
 } routerlist_t;
 
-/** Information on router used when extending a circuit.  (We don't need a
+/** Information on router used when extending a circuit. We don't need a
  * full routerinfo_t to extend: we only need addr:port:keyid to build an OR
- * connection, and onion_key to create the onionskin.) */
+ * connection, and onion_key to create the onionskin. Note that for onehop
+ * general-purpose tunnels, the onion_key is NULL. */
 typedef struct extend_info_t {
   char nickname[MAX_HEX_NICKNAME_LEN+1]; /**< This router's nickname for
                                           * display. */
@@ -1905,6 +1906,7 @@
 int circuit_extend_to_new_exit(origin_circuit_t *circ, extend_info_t *info);
 void onion_append_to_cpath(crypt_path_t **head_ptr, crypt_path_t *new_hop);
 extend_info_t *extend_info_from_router(routerinfo_t *r);
+extend_info_t *extend_info_from_routerstatus(routerstatus_t *s);
 extend_info_t *extend_info_dup(extend_info_t *info);
 void extend_info_free(extend_info_t *info);
 routerinfo_t *build_state_get_exit_router(cpath_build_state_t *state);
@@ -2894,6 +2896,7 @@
 int any_trusted_dir_is_v1_authority(void);
 networkstatus_t *networkstatus_get_by_digest(const char *digest);
 local_routerstatus_t *router_get_combined_status_by_digest(const char *digest);
+routerstatus_t *routerstatus_get_by_hexdigest(const char *hexdigest);
 void update_networkstatus_downloads(time_t now);
 void update_router_descriptor_downloads(time_t now);
 void routers_update_all_from_networkstatus(void);