Browse Source

Fix another case of refusing to use a chosen exit node because we think it will reject _mostly_ everything. Based on patch from rovv. See bug 752.

svn:r17139
Nick Mathewson 17 years ago
parent
commit
b166a43cb6
2 changed files with 35 additions and 11 deletions
  1. 3 0
      ChangeLog
  2. 32 11
      src/or/circuituse.c

+ 3 - 0
ChangeLog

@@ -34,6 +34,9 @@ Changes in version 0.2.1.7-alpha - 2008-10-xx
     - If a broken client asks a non-exit router to connect somewhere,
     - If a broken client asks a non-exit router to connect somewhere,
       do not even do the DNS lookup before rejecting the connection.
       do not even do the DNS lookup before rejecting the connection.
       Fixes another case of bug 619.  Patch from rovv.
       Fixes another case of bug 619.  Patch from rovv.
+    - Fix another case of assuming, when a specific exit is requested,
+      that we know more than the user about what hosts it allows.
+      Fixes another case of bug 752.  Patch from rovv.
 
 
 
 
 Changes in version 0.2.1.6-alpha - 2008-09-30
 Changes in version 0.2.1.6-alpha - 2008-09-30

+ 32 - 11
src/or/circuituse.c

@@ -1069,17 +1069,38 @@ circuit_get_open_circ_or_launch(edge_connection_t *conn,
 
 
   /* Do we need to check exit policy? */
   /* Do we need to check exit policy? */
   if (check_exit_policy) {
   if (check_exit_policy) {
-    struct in_addr in;
-    uint32_t addr = 0;
-    if (tor_inet_aton(conn->socks_request->address, &in))
-      addr = ntohl(in.s_addr);
-    if (router_exit_policy_all_routers_reject(addr, conn->socks_request->port,
-                                              need_uptime)) {
-      log_notice(LD_APP,
-                 "No Tor server exists that allows exit to %s:%d. Rejecting.",
-                 safe_str(conn->socks_request->address),
-                 conn->socks_request->port);
-      return -1;
+    if (!conn->chosen_exit_name) {
+      struct in_addr in;
+      uint32_t addr = 0;
+      if (tor_inet_aton(conn->socks_request->address, &in))
+        addr = ntohl(in.s_addr);
+      if (router_exit_policy_all_routers_reject(addr, conn->socks_request->port,
+                                                need_uptime)) {
+        log_notice(LD_APP,
+                   "No Tor server exists that allows exit to %s:%d. Rejecting.",
+                   safe_str(conn->socks_request->address),
+                   conn->socks_request->port);
+        return -1;
+      }
+    } else {
+      /* XXXX021 Duplicates checks in connection_ap_handshake_attach_circuit
+       * XXXX021 Fix this, then backport it? */
+      routerinfo_t *router = router_get_by_nickname(conn->chosen_exit_name, 1);
+      int opt = conn->_base.chosen_exit_optional;
+      if (router && !connection_ap_can_use_exit(conn, router)) {
+        log_fn(opt ? LOG_INFO : LOG_WARN, LD_APP,
+               "Requested exit point '%s' would refuse request. %s.",
+               conn->chosen_exit_name, opt ? "Trying others" : "Closing");
+        if (opt) {
+          conn->_base.chosen_exit_optional = 0;
+          tor_free(conn->chosen_exit_name);
+          /* Try again. */
+          return circuit_get_open_circ_or_launch(conn,
+                                                 desired_circuit_purpose,
+                                                 circp);
+        }
+        return -1;
+      }
     }
     }
   }
   }