Browse Source

Merge remote branch 'sebastian/bug1238'

Nick Mathewson 15 years ago
parent
commit
6dd71d314d
3 changed files with 34 additions and 19 deletions
  1. 2 1
      src/or/connection_edge.c
  2. 22 16
      src/or/policies.c
  3. 10 2
      src/test/test.c

+ 2 - 1
src/or/connection_edge.c

@@ -2937,7 +2937,8 @@ parse_extended_hostname(char *address, int allowdotexit)
         return EXIT_HOSTNAME; /* .exit */
       } else {
         log_warn(LD_APP, "The \".exit\" notation is disabled in Tor due to "
-                 "security risks. Set AllowDotExit in your torrc to enable it.");
+                 "security risks. Set AllowDotExit in your torrc to enable "
+                 "it.");
         /* FFFF send a controller event too to notify Vidalia users */
         return BAD_HOSTNAME;
       }

+ 22 - 16
src/or/policies.c

@@ -870,7 +870,7 @@ policies_set_router_exitpolicy_to_reject_all(routerinfo_t *r)
 static int
 exit_policy_is_general_exit_helper(smartlist_t *policy, int port)
 {
-  uint32_t j;
+  uint32_t mask, ip, i;
   /* Is this /8 rejected (1), or undecided (0)? */
   char subnet_status[256];
 
@@ -878,24 +878,30 @@ exit_policy_is_general_exit_helper(smartlist_t *policy, int port)
   SMARTLIST_FOREACH(policy, addr_policy_t *, p, {
     if (p->prt_min > port || p->prt_max < port)
       continue; /* Doesn't cover our port. */
-    for (j = 0; j < 256; ++j) {
+    mask = 0;
+    tor_assert(p->maskbits <= 32);
+
+    if (p->maskbits)
+      mask = UINT32_MAX<<(32-p->maskbits);
+    ip = tor_addr_to_ipv4h(&p->addr);
+
+    /* Calculate the first and last subnet that this exit policy touches
+     * and set it as loop boundaries. */
+    for (i = ((mask & ip)>>24); i <= (~((mask & ip) ^ mask)>>24); ++i) {
       tor_addr_t addr;
-      if (subnet_status[j] != 0)
+      if (subnet_status[i] != 0)
         continue; /* We already reject some part of this /8 */
-      tor_addr_from_ipv4h(&addr, j<<24);
-      if (tor_addr_is_internal(&addr, 1)) /* 1 because * = 0.0.0.0 */
+      tor_addr_from_ipv4h(&addr, i<<24);
+      if (tor_addr_is_internal(&addr, 0))
         continue; /* Local or non-routable addresses */
-      if (tor_addr_compare_masked(&addr, &p->addr, p->maskbits,
-                                  CMP_EXACT) == 0) {
-        if (p->policy_type == ADDR_POLICY_ACCEPT) {
-          if (p->maskbits > 8)
-            continue; /* Narrower than a /8. */
-          /* We found an allowed subnet of at least size /8. Done
-           * for this port! */
-          return 1;
-        } else if (p->policy_type == ADDR_POLICY_REJECT) {
-          subnet_status[j] = 1;
-        }
+      if (p->policy_type == ADDR_POLICY_ACCEPT) {
+        if (p->maskbits > 8)
+          continue; /* Narrower than a /8. */
+        /* We found an allowed subnet of at least size /8. Done
+         * for this port! */
+        return 1;
+      } else if (p->policy_type == ADDR_POLICY_REJECT) {
+        subnet_status[i] = 1;
       }
     }
   });

+ 10 - 2
src/test/test.c

@@ -648,7 +648,8 @@ test_policies(void)
 {
   int i;
   smartlist_t *policy = NULL, *policy2 = NULL, *policy3 = NULL,
-              *policy4 = NULL, *policy5 = NULL, *policy6 = NULL;
+              *policy4 = NULL, *policy5 = NULL, *policy6 = NULL,
+              *policy7 = NULL;
   addr_policy_t *p;
   tor_addr_t tar;
   config_line_t line;
@@ -725,12 +726,17 @@ test_policies(void)
   p = router_parse_addr_policy_item_from_string("accept *:1-65535",-1);
   test_assert(p != NULL);
   smartlist_add(policy5, p);
-  
+
   policy6 = smartlist_create();
   p = router_parse_addr_policy_item_from_string("accept 43.3.0.0/9:*",-1);
   test_assert(p != NULL);
   smartlist_add(policy6, p);
 
+  policy7 = smartlist_create();
+  p = router_parse_addr_policy_item_from_string("accept 0.0.0.0/8:*",-1);
+  test_assert(p != NULL);
+  smartlist_add(policy7, p);
+
   test_assert(!exit_policy_is_general_exit(policy));
   test_assert(exit_policy_is_general_exit(policy2));
   test_assert(!exit_policy_is_general_exit(NULL));
@@ -738,6 +744,7 @@ test_policies(void)
   test_assert(!exit_policy_is_general_exit(policy4));
   test_assert(!exit_policy_is_general_exit(policy5));
   test_assert(!exit_policy_is_general_exit(policy6));
+  test_assert(!exit_policy_is_general_exit(policy7));
 
   test_assert(cmp_addr_policies(policy, policy2));
   test_assert(cmp_addr_policies(policy, NULL));
@@ -853,6 +860,7 @@ test_policies(void)
   addr_policy_list_free(policy4);
   addr_policy_list_free(policy5);
   addr_policy_list_free(policy6);
+  addr_policy_list_free(policy7);
   tor_free(policy_str);
   if (sm) {
     SMARTLIST_FOREACH(sm, char *, s, tor_free(s));