[tor-commits] [tor/master] Support multiple transports in a single transport line.

nickm at torproject.org nickm at torproject.org
Fri Oct 7 20:03:19 UTC 2011


commit 105cc42e96ea979b1111f3ba0d410c510cd229f0
Author: George Kadianakis <desnacked at gmail.com>
Date:   Fri Oct 7 14:13:41 2011 +0200

    Support multiple transports in a single transport line.
    
    Support multiple comma-separated transpotrs in a single
    {Client,Server}TransportPlugin line.
---
 src/or/config.c     |   78 ++++++++++++++++++++++++++++++++++++++------------
 src/or/transports.c |   22 +++++++++-----
 src/or/transports.h |   10 +++---
 3 files changed, 78 insertions(+), 32 deletions(-)

diff --git a/src/or/config.c b/src/or/config.c
index 95017b3..536324d 100644
--- a/src/or/config.c
+++ b/src/or/config.c
@@ -4693,7 +4693,8 @@ parse_client_transport_line(const char *line, int validate_only)
   int r;
   char *field2=NULL;
 
-  const char *name=NULL;
+  const char *transports=NULL;
+  smartlist_t *transport_list=NULL;
   char *addrport=NULL;
   tor_addr_t addr;
   uint16_t port = 0;
@@ -4717,11 +4718,20 @@ parse_client_transport_line(const char *line, int validate_only)
     goto err;
   }
 
-  name = smartlist_get(items, 0);
-  if (!string_is_C_identifier(name)) {
-    log_warn(LD_CONFIG, "Transport name is not a C identifier (%s).", name);
-    goto err;
-  }
+  /* Get the first line element, split it to commas into
+     transport_list (in case it's multiple transports) and validate
+     the transport names. */
+  transports = smartlist_get(items, 0);
+  transport_list = smartlist_create();
+  smartlist_split_string(transport_list, transports, ",",
+                         SPLIT_SKIP_SPACE|SPLIT_IGNORE_BLANK, 0);
+  SMARTLIST_FOREACH_BEGIN(transport_list, const char *, transport_name) {
+    if (!string_is_C_identifier(transport_name)) {
+      log_warn(LD_CONFIG, "Transport name is not a C identifier (%s).",
+               transport_name);
+      goto err;
+    }
+  } SMARTLIST_FOREACH_END(transport_name);
 
   /* field2 is either a SOCKS version or "exec" */
   field2 = smartlist_get(items, 1);
@@ -4753,9 +4763,15 @@ parse_client_transport_line(const char *line, int validate_only)
       *tmp = NULL; /*terminated with NUL pointer, just like execve() likes it*/
 
       /* kickstart the thing */
-      pt_kickstart_client_proxy(name, proxy_argv);
+      pt_kickstart_client_proxy(transport_list, proxy_argv);
     }
   } else { /* external */
+    if (smartlist_len(transport_list) != 1) {
+      log_warn(LD_CONFIG, "You can't have an external proxy with "
+               "more than one transports.");
+      goto err;
+    }
+
     addrport = smartlist_get(items, 2);
 
     if (tor_addr_port_parse(addrport, &addr, &port)<0) {
@@ -4770,10 +4786,11 @@ parse_client_transport_line(const char *line, int validate_only)
     }
 
     if (!validate_only) {
-      transport_add_from_config(&addr, port, name, socks_ver);
+      transport_add_from_config(&addr, port, smartlist_get(transport_list, 0),
+                                socks_ver);
 
-      log_info(LD_DIR, "Transport '%s' found at %s:%d", name,
-               fmt_addr(&addr), (int)port);
+      log_info(LD_DIR, "Transport '%s' found at %s:%d",
+               transports, fmt_addr(&addr), (int)port);
     }
   }
 
@@ -4786,6 +4803,9 @@ parse_client_transport_line(const char *line, int validate_only)
  done:
   SMARTLIST_FOREACH(items, char*, s, tor_free(s));
   smartlist_free(items);
+  SMARTLIST_FOREACH(transport_list, char*, s, tor_free(s));
+  smartlist_free(transport_list);
+
   return r;
 }
 
@@ -4799,7 +4819,8 @@ parse_server_transport_line(const char *line, int validate_only)
 {
   smartlist_t *items = NULL;
   int r;
-  const char *name=NULL;
+  const char *transports=NULL;
+  smartlist_t *transport_list=NULL;
   char *type=NULL;
   char *addrport=NULL;
   tor_addr_t addr;
@@ -4823,11 +4844,20 @@ parse_server_transport_line(const char *line, int validate_only)
     goto err;
   }
 
-  name = smartlist_get(items, 0);
-  if (!string_is_C_identifier(name)) {
-    log_warn(LD_CONFIG, "Transport name is not a C identifier (%s).", name);
-    goto err;
-  }
+  /* Get the first line element, split it to commas into
+     transport_list (in case it's multiple transports) and validate
+     the transport names. */
+  transports = smartlist_get(items, 0);
+  transport_list = smartlist_create();
+  smartlist_split_string(transport_list, transports, ",",
+                         SPLIT_SKIP_SPACE|SPLIT_IGNORE_BLANK, 0);
+  SMARTLIST_FOREACH_BEGIN(transport_list, const char *, transport_name) {
+    if (!string_is_C_identifier(transport_name)) {
+      log_warn(LD_CONFIG, "Transport name is not a C identifier (%s).",
+               transport_name);
+      goto err;
+    }
+  } SMARTLIST_FOREACH_END(transport_name);
 
   type = smartlist_get(items, 1);
 
@@ -4854,9 +4884,15 @@ parse_server_transport_line(const char *line, int validate_only)
       *tmp = NULL; /*terminated with NUL pointer, just like execve() likes it*/
 
       /* kickstart the thing */
-      pt_kickstart_server_proxy(name, proxy_argv);
+      pt_kickstart_server_proxy(transport_list, proxy_argv);
     }
   } else { /* external */
+    if (smartlist_len(transport_list) != 1) {
+      log_warn(LD_CONFIG, "You can't have an external proxy with "
+               "more than one transports.");
+      goto err;
+    }
+
     addrport = smartlist_get(items, 2);
 
     if (tor_addr_port_parse(addrport, &addr, &port)<0) {
@@ -4871,8 +4907,8 @@ parse_server_transport_line(const char *line, int validate_only)
     }
 
     if (!validate_only) {
-      log_info(LD_DIR, "Server transport '%s' at %s:%d.", name,
-               fmt_addr(&addr), (int)port);
+      log_info(LD_DIR, "Server transport '%s' at %s:%d.",
+               transports, fmt_addr(&addr), (int)port);
     }
   }
 
@@ -4885,6 +4921,9 @@ parse_server_transport_line(const char *line, int validate_only)
  done:
   SMARTLIST_FOREACH(items, char*, s, tor_free(s));
   smartlist_free(items);
+  SMARTLIST_FOREACH(transport_list, char*, s, tor_free(s));
+  smartlist_free(transport_list);
+
   return r;
 }
 
@@ -5993,3 +6032,4 @@ getinfo_helper_config(control_connection_t *conn,
   }
   return 0;
 }
+
diff --git a/src/or/transports.c b/src/or/transports.c
index c67fc68..465b8e1 100644
--- a/src/or/transports.c
+++ b/src/or/transports.c
@@ -890,7 +890,8 @@ set_managed_proxy_environment(char ***envp, const managed_proxy_t *mp)
  *  <b>proxy_argv</b>. If <b>is_server</b> is true, it's a server
  *  managed proxy. */
 static managed_proxy_t *
-managed_proxy_create(const char *transport, char **proxy_argv, int is_server)
+managed_proxy_create(const smartlist_t *transport_list,
+                     char **proxy_argv, int is_server)
 {
   managed_proxy_t *mp = tor_malloc_zero(sizeof(managed_proxy_t));
   mp->conf_state = PT_PROTO_INFANT;
@@ -899,7 +900,8 @@ managed_proxy_create(const char *transport, char **proxy_argv, int is_server)
   mp->transports = smartlist_create();
 
   mp->transports_to_launch = smartlist_create();
-  add_transport_to_proxy(transport, mp);
+  SMARTLIST_FOREACH(transport_list, const char *, transport,
+                    add_transport_to_proxy(transport, mp));
 
   /* register the managed proxy */
   if (!managed_proxy_list)
@@ -914,7 +916,8 @@ managed_proxy_create(const char *transport, char **proxy_argv, int is_server)
  *  the managed proxy subsystem.
  *  If <b>is_server</b> is true, then the proxy is a server proxy. */
 void
-pt_kickstart_proxy(const char *transport, char **proxy_argv, int is_server)
+pt_kickstart_proxy(const smartlist_t *transport_list,
+                   char **proxy_argv, int is_server)
 {
   managed_proxy_t *mp=NULL;
   transport_t *old_transport = NULL;
@@ -922,7 +925,7 @@ pt_kickstart_proxy(const char *transport, char **proxy_argv, int is_server)
   mp = get_managed_proxy_by_argv_and_type(proxy_argv, is_server);
 
   if (!mp) { /* we haven't seen this proxy before */
-    managed_proxy_create(transport, proxy_argv, is_server);
+    managed_proxy_create(transport_list, proxy_argv, is_server);
 
   } else { /* known proxy. add its transport to its transport list */
     if (mp->got_hup) {
@@ -938,12 +941,15 @@ pt_kickstart_proxy(const char *transport, char **proxy_argv, int is_server)
         unconfigured_proxies_n++;
       }
 
-      old_transport = transport_get_by_name(transport);
-      if (old_transport)
-        old_transport->marked_for_removal = 0;
+      SMARTLIST_FOREACH_BEGIN(transport_list, const char *, transport) {
+        old_transport = transport_get_by_name(transport);
+        if (old_transport)
+          old_transport->marked_for_removal = 0;
+      } SMARTLIST_FOREACH_END(transport);
     }
 
-    add_transport_to_proxy(transport, mp);
+    SMARTLIST_FOREACH(transport_list, const char *, transport,
+                      add_transport_to_proxy(transport, mp));
     free_execve_args(proxy_argv);
   }
 }
diff --git a/src/or/transports.h b/src/or/transports.h
index 57bfb5c..0b5cd5f 100644
--- a/src/or/transports.h
+++ b/src/or/transports.h
@@ -11,13 +11,13 @@
 #ifndef TOR_TRANSPORTS_H
 #define TOR_TRANSPORTS_H
 
-void pt_kickstart_proxy(const char *method, char **proxy_argv,
+void pt_kickstart_proxy(const smartlist_t *transport_list, char **proxy_argv,
                         int is_server);
 
-#define pt_kickstart_client_proxy(m, pa)  \
-  pt_kickstart_proxy(m, pa, 0)
-#define pt_kickstart_server_proxy(m, pa) \
-  pt_kickstart_proxy(m, pa, 1)
+#define pt_kickstart_client_proxy(tl, pa)  \
+  pt_kickstart_proxy(tl, pa, 0)
+#define pt_kickstart_server_proxy(tl, pa) \
+  pt_kickstart_proxy(tl, pa, 1)
 
 void pt_configure_remaining_proxies(void);
 





More information about the tor-commits mailing list