Browse Source

Merge branch 'feature15482_squashed'

Nick Mathewson 8 years ago
parent
commit
fcec1f3381
5 changed files with 38 additions and 3 deletions
  1. 5 0
      changes/feature15482
  2. 6 1
      doc/tor.1.txt
  3. 9 2
      src/or/circuituse.c
  4. 11 0
      src/or/config.c
  5. 7 0
      src/or/or.h

+ 5 - 0
changes/feature15482

@@ -0,0 +1,5 @@
+  o Minor features (client-side privacy)
+    - Indefinitely extend circuit lifespan by resetting dirtyness, if
+      IsolateSOCKSAuth is in use, the new `KeepAliveIsolateSOCKSAuth`
+      option is set, and streams with SOCKS authentication are attached
+      to the circuit. Implements feature 15482.

+ 6 - 1
doc/tor.1.txt

@@ -934,7 +934,9 @@ The following options are useful only for clients (that is, if
     Feel free to reuse a circuit that was first used at most NUM seconds ago,
     Feel free to reuse a circuit that was first used at most NUM seconds ago,
     but never attach a new stream to a circuit that is too old.  For hidden
     but never attach a new stream to a circuit that is too old.  For hidden
     services, this applies to the __last__ time a circuit was used, not the
     services, this applies to the __last__ time a circuit was used, not the
-    first.  (Default: 10 minutes)
+    first. Circuits with streams constructed with SOCKS authentication via
+    SocksPorts that have **KeepAliveIsolateSOCKSAuth** ignore this value.
+    (Default: 10 minutes)
 
 
 [[MaxClientCircuitsPending]] **MaxClientCircuitsPending** __NUM__::
 [[MaxClientCircuitsPending]] **MaxClientCircuitsPending** __NUM__::
     Do not allow more than NUM circuits to be pending at a time for handling
     Do not allow more than NUM circuits to be pending at a time for handling
@@ -991,6 +993,9 @@ The following options are useful only for clients (that is, if
     **IsolateDestAddr**;;
     **IsolateDestAddr**;;
         Don't share circuits with streams targeting a different
         Don't share circuits with streams targeting a different
         destination address.
         destination address.
+    **KeepAliveIsolateSOCKSAuth**;;
+        If **IsolateSOCKSAuth** is enabled, keep alive circuits that have
+        streams with SOCKS authentication set indefinitely.
     **SessionGroup=**__INT__;;
     **SessionGroup=**__INT__;;
         If no other isolation rules would prevent it, allow streams
         If no other isolation rules would prevent it, allow streams
         on this port to share circuits with streams from every other
         on this port to share circuits with streams from every other

+ 9 - 2
src/or/circuituse.c

@@ -2284,8 +2284,15 @@ connection_ap_handshake_attach_chosen_circuit(entry_connection_t *conn,
 
 
   base_conn->state = AP_CONN_STATE_CIRCUIT_WAIT;
   base_conn->state = AP_CONN_STATE_CIRCUIT_WAIT;
 
 
-  if (!circ->base_.timestamp_dirty)
-    circ->base_.timestamp_dirty = time(NULL);
+  if (!circ->base_.timestamp_dirty ||
+      ((conn->entry_cfg.isolation_flags & ISO_SOCKSAUTH) &&
+       (conn->entry_cfg.socks_iso_keep_alive) &&
+       (conn->socks_request->usernamelen ||
+        conn->socks_request->passwordlen))) {
+    /* When stream isolation is in use and controlled by an application
+     * we are willing to keep using the stream. */
+    circ->base_.timestamp_dirty = approx_time();
+  }
 
 
   pathbias_count_use_attempt(circ);
   pathbias_count_use_attempt(circ);
 
 

+ 11 - 0
src/or/config.c

@@ -6037,6 +6037,7 @@ parse_port_config(smartlist_t *out,
     int sessiongroup = SESSION_GROUP_UNSET;
     int sessiongroup = SESSION_GROUP_UNSET;
     unsigned isolation = ISO_DEFAULT;
     unsigned isolation = ISO_DEFAULT;
     int prefer_no_auth = 0;
     int prefer_no_auth = 0;
+    int socks_iso_keep_alive = 0;
 
 
     char *addrport;
     char *addrport;
     uint16_t ptmp=0;
     uint16_t ptmp=0;
@@ -6261,6 +6262,8 @@ parse_port_config(smartlist_t *out,
           isoflag = ISO_CLIENTPROTO;
           isoflag = ISO_CLIENTPROTO;
         } else if (!strcasecmp(elt, "IsolateClientAddr")) {
         } else if (!strcasecmp(elt, "IsolateClientAddr")) {
           isoflag = ISO_CLIENTADDR;
           isoflag = ISO_CLIENTADDR;
+        } else if (!strcasecmp(elt, "KeepAliveIsolateSOCKSAuth")) {
+          socks_iso_keep_alive = 1;
         } else {
         } else {
           log_warn(LD_CONFIG, "Unrecognized %sPort option '%s'",
           log_warn(LD_CONFIG, "Unrecognized %sPort option '%s'",
                    portname, escaped(elt_orig));
                    portname, escaped(elt_orig));
@@ -6291,6 +6294,13 @@ parse_port_config(smartlist_t *out,
       goto err;
       goto err;
     }
     }
 
 
+    if (!(isolation & ISO_SOCKSAUTH) && socks_iso_keep_alive) {
+      log_warn(LD_CONFIG, "You have a %sPort entry with both "
+               "NoIsolateSOCKSAuth and KeepAliveIsolateSOCKSAuth set.",
+               portname);
+      goto err;
+    }
+
     if (out && port) {
     if (out && port) {
       size_t namelen = unix_socket_path ? strlen(unix_socket_path) : 0;
       size_t namelen = unix_socket_path ? strlen(unix_socket_path) : 0;
       port_cfg_t *cfg = port_cfg_new(namelen);
       port_cfg_t *cfg = port_cfg_new(namelen);
@@ -6324,6 +6334,7 @@ parse_port_config(smartlist_t *out,
       cfg->entry_cfg.socks_prefer_no_auth = prefer_no_auth;
       cfg->entry_cfg.socks_prefer_no_auth = prefer_no_auth;
       if (! (isolation & ISO_SOCKSAUTH))
       if (! (isolation & ISO_SOCKSAUTH))
         cfg->entry_cfg.socks_prefer_no_auth = 1;
         cfg->entry_cfg.socks_prefer_no_auth = 1;
+      cfg->entry_cfg.socks_iso_keep_alive = socks_iso_keep_alive;
 
 
       smartlist_add(out, cfg);
       smartlist_add(out, cfg);
     }
     }

+ 7 - 0
src/or/or.h

@@ -1155,6 +1155,8 @@ typedef struct entry_port_cfg_t {
   /** When both no-auth and user/pass are advertised by a SOCKS client, select
   /** When both no-auth and user/pass are advertised by a SOCKS client, select
    * no-auth. */
    * no-auth. */
   unsigned int socks_prefer_no_auth : 1;
   unsigned int socks_prefer_no_auth : 1;
+  /** When ISO_SOCKSAUTH is in use, Keep-Alive circuits indefinitely. */
+  unsigned int socks_iso_keep_alive : 1;
 
 
   /* Client port types only: */
   /* Client port types only: */
   unsigned int ipv4_traffic : 1;
   unsigned int ipv4_traffic : 1;
@@ -2877,6 +2879,11 @@ typedef struct circuit_t {
    * circuits entered certain states.  This usage probably won't
    * circuits entered certain states.  This usage probably won't
    * interfere with this field's primary purpose, but we should
    * interfere with this field's primary purpose, but we should
    * document it more thoroughly to make sure of that.
    * document it more thoroughly to make sure of that.
+   *
+   * XXX027 The SocksPort option KeepaliveIsolateSOCKSAuth will artificially
+   * adjust this value forward each time a suitable stream is attached to an
+   * already constructed circuit, potentially keeping the circuit alive
+   * indefinitely.
    */
    */
   time_t timestamp_dirty;
   time_t timestamp_dirty;