Loading changes/bug3589 0 → 100644 +3 −0 Changes for changes/bug3589: 3 added lines, 0 removed lines. Original line number Diff line number Diff line o Major features: - Bridges now report the pluggable transports they support to the bridge authority. Implements ticket 3589. src/or/circuitbuild.c +0 −196 Changes for src/or/circuitbuild.c: 0 added lines, 196 removed lines. Original line number Diff line number Diff line Loading @@ -4970,199 +4970,6 @@ bridge_free(bridge_info_t *bridge) tor_free(bridge); } /** A list of pluggable transports found in torrc. */ static smartlist_t *transport_list = NULL; /** Mark every entry of the transport list to be removed on our next call to * sweep_transport_list unless it has first been un-marked. */ void mark_transport_list(void) { if (!transport_list) transport_list = smartlist_new(); SMARTLIST_FOREACH(transport_list, transport_t *, t, t->marked_for_removal = 1); } /** Remove every entry of the transport list that was marked with * mark_transport_list if it has not subsequently been un-marked. */ void sweep_transport_list(void) { if (!transport_list) transport_list = smartlist_new(); SMARTLIST_FOREACH_BEGIN(transport_list, transport_t *, t) { if (t->marked_for_removal) { SMARTLIST_DEL_CURRENT(transport_list, t); transport_free(t); } } SMARTLIST_FOREACH_END(t); } /** Initialize the pluggable transports list to empty, creating it if * needed. */ void clear_transport_list(void) { if (!transport_list) transport_list = smartlist_new(); SMARTLIST_FOREACH(transport_list, transport_t *, t, transport_free(t)); smartlist_clear(transport_list); } /** Free the pluggable transport struct <b>transport</b>. */ void transport_free(transport_t *transport) { if (!transport) return; tor_free(transport->name); tor_free(transport); } /** Returns the transport in our transport list that has the name <b>name</b>. * Else returns NULL. */ transport_t * transport_get_by_name(const char *name) { tor_assert(name); if (!transport_list) return NULL; SMARTLIST_FOREACH_BEGIN(transport_list, transport_t *, transport) { if (!strcmp(transport->name, name)) return transport; } SMARTLIST_FOREACH_END(transport); return NULL; } /** Returns a transport_t struct for a transport proxy supporting the protocol <b>name</b> listening at <b>addr</b>:<b>port</b> using SOCKS version <b>socks_ver</b>. */ transport_t * transport_new(const tor_addr_t *addr, uint16_t port, const char *name, int socks_ver) { transport_t *t = tor_malloc_zero(sizeof(transport_t)); tor_addr_copy(&t->addr, addr); t->port = port; t->name = tor_strdup(name); t->socks_version = socks_ver; return t; } /** Resolve any conflicts that the insertion of transport <b>t</b> * might cause. * Return 0 if <b>t</b> is OK and should be registered, 1 if there is * a transport identical to <b>t</b> already registered and -1 if * <b>t</b> cannot be added due to conflicts. */ static int transport_resolve_conflicts(transport_t *t) { /* This is how we resolve transport conflicts: If there is already a transport with the same name and addrport, we either have duplicate torrc lines OR we are here post-HUP and this transport was here pre-HUP as well. In any case, mark the old transport so that it doesn't get removed and ignore the new one. Our caller has to free the new transport so we return '1' to signify this. If there is already a transport with the same name but different addrport: * if it's marked for removal, it means that it either has a lower priority than 't' in torrc (otherwise the mark would have been cleared by the paragraph above), or it doesn't exist at all in the post-HUP torrc. We destroy the old transport and register 't'. * if it's *not* marked for removal, it means that it was newly added in the post-HUP torrc or that it's of higher priority, in this case we ignore 't'. */ transport_t *t_tmp = transport_get_by_name(t->name); if (t_tmp) { /* same name */ if (tor_addr_eq(&t->addr, &t_tmp->addr) && (t->port == t_tmp->port)) { /* same name *and* addrport */ t_tmp->marked_for_removal = 0; return 1; } else { /* same name but different addrport */ if (t_tmp->marked_for_removal) { /* marked for removal */ log_notice(LD_GENERAL, "You tried to add transport '%s' at '%s:%u' " "but there was already a transport marked for deletion at " "'%s:%u'. We deleted the old transport and registered the " "new one.", t->name, fmt_addr(&t->addr), t->port, fmt_addr(&t_tmp->addr), t_tmp->port); smartlist_remove(transport_list, t_tmp); transport_free(t_tmp); } else { /* *not* marked for removal */ log_notice(LD_GENERAL, "You tried to add transport '%s' at '%s:%u' " "but the same transport already exists at '%s:%u'. " "Skipping.", t->name, fmt_addr(&t->addr), t->port, fmt_addr(&t_tmp->addr), t_tmp->port); return -1; } } } return 0; } /** Add transport <b>t</b> to the internal list of pluggable * transports. * Returns 0 if the transport was added correctly, 1 if the same * transport was already registered (in this case the caller must * free the transport) and -1 if there was an error. */ int transport_add(transport_t *t) { int r; tor_assert(t); r = transport_resolve_conflicts(t); switch (r) { case 0: /* should register transport */ if (!transport_list) transport_list = smartlist_new(); smartlist_add(transport_list, t); return 0; default: /* let our caller know the return code */ return r; } } /** Remember a new pluggable transport proxy at <b>addr</b>:<b>port</b>. * <b>name</b> is set to the name of the protocol this proxy uses. * <b>socks_ver</b> is set to the SOCKS version of the proxy. */ int transport_add_from_config(const tor_addr_t *addr, uint16_t port, const char *name, int socks_ver) { transport_t *t = transport_new(addr, port, name, socks_ver); int r = transport_add(t); switch (r) { case -1: default: log_notice(LD_GENERAL, "Could not add transport %s at %s:%u. Skipping.", t->name, fmt_addr(&t->addr), t->port); transport_free(t); return -1; case 1: log_info(LD_GENERAL, "Succesfully registered transport %s at %s:%u.", t->name, fmt_addr(&t->addr), t->port); transport_free(t); /* falling */ return 0; case 0: log_info(LD_GENERAL, "Succesfully registered transport %s at %s:%u.", t->name, fmt_addr(&t->addr), t->port); return 0; } } /** Return a bridge pointer if <b>ri</b> is one of our known bridges * (either by comparing keys if possible, else by comparing addr/port). Loading Loading @@ -5800,10 +5607,7 @@ entry_guards_free_all(void) entry_guards = NULL; } clear_bridge_list(); clear_transport_list(); smartlist_free(bridge_list); smartlist_free(transport_list); bridge_list = NULL; transport_list = NULL; } src/or/circuitbuild.h +1 −27 Changes for src/or/circuitbuild.h: 1 added line, 27 removed lines. Original line number Diff line number Diff line Loading @@ -12,21 +12,6 @@ #ifndef _TOR_CIRCUITBUILD_H #define _TOR_CIRCUITBUILD_H /** Represents a pluggable transport proxy used by a bridge. */ typedef struct { /** SOCKS version: One of PROXY_SOCKS4, PROXY_SOCKS5. */ int socks_version; /** Name of pluggable transport protocol */ char *name; /** Address of proxy */ tor_addr_t addr; /** Port of proxy */ uint16_t port; /** Boolean: We are re-parsing our transport list, and we are going to remove * this one if we don't find it in the list of configured transports. */ unsigned marked_for_removal : 1; } transport_t; char *circuit_list_path(origin_circuit_t *circ, int verbose); char *circuit_list_path_for_controller(origin_circuit_t *circ); void circuit_log_path(int severity, unsigned int domain, Loading Loading @@ -82,8 +67,6 @@ int getinfo_helper_entry_guards(control_connection_t *conn, void mark_bridge_list(void); void sweep_bridge_list(void); void mark_transport_list(void); void sweep_transport_list(void); int routerinfo_is_a_configured_bridge(const routerinfo_t *ri); int node_is_a_configured_bridge(const node_t *node); Loading Loading @@ -151,21 +134,12 @@ void circuit_build_times_network_circ_success(circuit_build_times_t *cbt); /* DOCDOC circuit_build_times_get_bw_scale */ int circuit_build_times_get_bw_scale(networkstatus_t *ns); void clear_transport_list(void); int transport_add_from_config(const tor_addr_t *addr, uint16_t port, const char *name, int socks_ver); int transport_add(transport_t *t); void transport_free(transport_t *transport); transport_t *transport_new(const tor_addr_t *addr, uint16_t port, const char *name, int socks_ver); /* DOCDOC find_transport_name_by_bridge_addrport */ const char *find_transport_name_by_bridge_addrport(const tor_addr_t *addr, uint16_t port); typedef struct transport_t transport_t; int find_transport_by_bridge_addrport(const tor_addr_t *addr, uint16_t port, const transport_t **transport); transport_t *transport_get_by_name(const char *name); #endif src/or/connection.c +1 −0 Changes for src/or/connection.c: 1 added line, 0 removed lines. Original line number Diff line number Diff line Loading @@ -34,6 +34,7 @@ #include "rendcommon.h" #include "rephist.h" #include "router.h" #include "transports.h" #include "routerparse.h" #ifdef USE_BUFFEREVENTS Loading src/or/router.c +8 −0 Changes for src/or/router.c: 8 added lines, 0 removed lines. Original line number Diff line number Diff line Loading @@ -27,6 +27,7 @@ #include "router.h" #include "routerlist.h" #include "routerparse.h" #include "transports.h" /** * \file router.c Loading Loading @@ -2344,6 +2345,13 @@ extrainfo_dump_to_string(char **s_out, extrainfo_t *extrainfo, } } /* Add information about the pluggable transports we support. */ if (options->ServerTransportPlugin) { char *pluggable_transports = pt_get_extra_info_descriptor_string(); if (pluggable_transports) smartlist_add(chunks, pluggable_transports); } if (should_record_bridge_info(options) && write_stats_to_extrainfo) { const char *bridge_stats = geoip_get_bridge_stats_extrainfo(now); if (bridge_stats) { Loading Loading
changes/bug3589 0 → 100644 +3 −0 Changes for changes/bug3589: 3 added lines, 0 removed lines. Original line number Diff line number Diff line o Major features: - Bridges now report the pluggable transports they support to the bridge authority. Implements ticket 3589.
src/or/circuitbuild.c +0 −196 Changes for src/or/circuitbuild.c: 0 added lines, 196 removed lines. Original line number Diff line number Diff line Loading @@ -4970,199 +4970,6 @@ bridge_free(bridge_info_t *bridge) tor_free(bridge); } /** A list of pluggable transports found in torrc. */ static smartlist_t *transport_list = NULL; /** Mark every entry of the transport list to be removed on our next call to * sweep_transport_list unless it has first been un-marked. */ void mark_transport_list(void) { if (!transport_list) transport_list = smartlist_new(); SMARTLIST_FOREACH(transport_list, transport_t *, t, t->marked_for_removal = 1); } /** Remove every entry of the transport list that was marked with * mark_transport_list if it has not subsequently been un-marked. */ void sweep_transport_list(void) { if (!transport_list) transport_list = smartlist_new(); SMARTLIST_FOREACH_BEGIN(transport_list, transport_t *, t) { if (t->marked_for_removal) { SMARTLIST_DEL_CURRENT(transport_list, t); transport_free(t); } } SMARTLIST_FOREACH_END(t); } /** Initialize the pluggable transports list to empty, creating it if * needed. */ void clear_transport_list(void) { if (!transport_list) transport_list = smartlist_new(); SMARTLIST_FOREACH(transport_list, transport_t *, t, transport_free(t)); smartlist_clear(transport_list); } /** Free the pluggable transport struct <b>transport</b>. */ void transport_free(transport_t *transport) { if (!transport) return; tor_free(transport->name); tor_free(transport); } /** Returns the transport in our transport list that has the name <b>name</b>. * Else returns NULL. */ transport_t * transport_get_by_name(const char *name) { tor_assert(name); if (!transport_list) return NULL; SMARTLIST_FOREACH_BEGIN(transport_list, transport_t *, transport) { if (!strcmp(transport->name, name)) return transport; } SMARTLIST_FOREACH_END(transport); return NULL; } /** Returns a transport_t struct for a transport proxy supporting the protocol <b>name</b> listening at <b>addr</b>:<b>port</b> using SOCKS version <b>socks_ver</b>. */ transport_t * transport_new(const tor_addr_t *addr, uint16_t port, const char *name, int socks_ver) { transport_t *t = tor_malloc_zero(sizeof(transport_t)); tor_addr_copy(&t->addr, addr); t->port = port; t->name = tor_strdup(name); t->socks_version = socks_ver; return t; } /** Resolve any conflicts that the insertion of transport <b>t</b> * might cause. * Return 0 if <b>t</b> is OK and should be registered, 1 if there is * a transport identical to <b>t</b> already registered and -1 if * <b>t</b> cannot be added due to conflicts. */ static int transport_resolve_conflicts(transport_t *t) { /* This is how we resolve transport conflicts: If there is already a transport with the same name and addrport, we either have duplicate torrc lines OR we are here post-HUP and this transport was here pre-HUP as well. In any case, mark the old transport so that it doesn't get removed and ignore the new one. Our caller has to free the new transport so we return '1' to signify this. If there is already a transport with the same name but different addrport: * if it's marked for removal, it means that it either has a lower priority than 't' in torrc (otherwise the mark would have been cleared by the paragraph above), or it doesn't exist at all in the post-HUP torrc. We destroy the old transport and register 't'. * if it's *not* marked for removal, it means that it was newly added in the post-HUP torrc or that it's of higher priority, in this case we ignore 't'. */ transport_t *t_tmp = transport_get_by_name(t->name); if (t_tmp) { /* same name */ if (tor_addr_eq(&t->addr, &t_tmp->addr) && (t->port == t_tmp->port)) { /* same name *and* addrport */ t_tmp->marked_for_removal = 0; return 1; } else { /* same name but different addrport */ if (t_tmp->marked_for_removal) { /* marked for removal */ log_notice(LD_GENERAL, "You tried to add transport '%s' at '%s:%u' " "but there was already a transport marked for deletion at " "'%s:%u'. We deleted the old transport and registered the " "new one.", t->name, fmt_addr(&t->addr), t->port, fmt_addr(&t_tmp->addr), t_tmp->port); smartlist_remove(transport_list, t_tmp); transport_free(t_tmp); } else { /* *not* marked for removal */ log_notice(LD_GENERAL, "You tried to add transport '%s' at '%s:%u' " "but the same transport already exists at '%s:%u'. " "Skipping.", t->name, fmt_addr(&t->addr), t->port, fmt_addr(&t_tmp->addr), t_tmp->port); return -1; } } } return 0; } /** Add transport <b>t</b> to the internal list of pluggable * transports. * Returns 0 if the transport was added correctly, 1 if the same * transport was already registered (in this case the caller must * free the transport) and -1 if there was an error. */ int transport_add(transport_t *t) { int r; tor_assert(t); r = transport_resolve_conflicts(t); switch (r) { case 0: /* should register transport */ if (!transport_list) transport_list = smartlist_new(); smartlist_add(transport_list, t); return 0; default: /* let our caller know the return code */ return r; } } /** Remember a new pluggable transport proxy at <b>addr</b>:<b>port</b>. * <b>name</b> is set to the name of the protocol this proxy uses. * <b>socks_ver</b> is set to the SOCKS version of the proxy. */ int transport_add_from_config(const tor_addr_t *addr, uint16_t port, const char *name, int socks_ver) { transport_t *t = transport_new(addr, port, name, socks_ver); int r = transport_add(t); switch (r) { case -1: default: log_notice(LD_GENERAL, "Could not add transport %s at %s:%u. Skipping.", t->name, fmt_addr(&t->addr), t->port); transport_free(t); return -1; case 1: log_info(LD_GENERAL, "Succesfully registered transport %s at %s:%u.", t->name, fmt_addr(&t->addr), t->port); transport_free(t); /* falling */ return 0; case 0: log_info(LD_GENERAL, "Succesfully registered transport %s at %s:%u.", t->name, fmt_addr(&t->addr), t->port); return 0; } } /** Return a bridge pointer if <b>ri</b> is one of our known bridges * (either by comparing keys if possible, else by comparing addr/port). Loading Loading @@ -5800,10 +5607,7 @@ entry_guards_free_all(void) entry_guards = NULL; } clear_bridge_list(); clear_transport_list(); smartlist_free(bridge_list); smartlist_free(transport_list); bridge_list = NULL; transport_list = NULL; }
src/or/circuitbuild.h +1 −27 Changes for src/or/circuitbuild.h: 1 added line, 27 removed lines. Original line number Diff line number Diff line Loading @@ -12,21 +12,6 @@ #ifndef _TOR_CIRCUITBUILD_H #define _TOR_CIRCUITBUILD_H /** Represents a pluggable transport proxy used by a bridge. */ typedef struct { /** SOCKS version: One of PROXY_SOCKS4, PROXY_SOCKS5. */ int socks_version; /** Name of pluggable transport protocol */ char *name; /** Address of proxy */ tor_addr_t addr; /** Port of proxy */ uint16_t port; /** Boolean: We are re-parsing our transport list, and we are going to remove * this one if we don't find it in the list of configured transports. */ unsigned marked_for_removal : 1; } transport_t; char *circuit_list_path(origin_circuit_t *circ, int verbose); char *circuit_list_path_for_controller(origin_circuit_t *circ); void circuit_log_path(int severity, unsigned int domain, Loading Loading @@ -82,8 +67,6 @@ int getinfo_helper_entry_guards(control_connection_t *conn, void mark_bridge_list(void); void sweep_bridge_list(void); void mark_transport_list(void); void sweep_transport_list(void); int routerinfo_is_a_configured_bridge(const routerinfo_t *ri); int node_is_a_configured_bridge(const node_t *node); Loading Loading @@ -151,21 +134,12 @@ void circuit_build_times_network_circ_success(circuit_build_times_t *cbt); /* DOCDOC circuit_build_times_get_bw_scale */ int circuit_build_times_get_bw_scale(networkstatus_t *ns); void clear_transport_list(void); int transport_add_from_config(const tor_addr_t *addr, uint16_t port, const char *name, int socks_ver); int transport_add(transport_t *t); void transport_free(transport_t *transport); transport_t *transport_new(const tor_addr_t *addr, uint16_t port, const char *name, int socks_ver); /* DOCDOC find_transport_name_by_bridge_addrport */ const char *find_transport_name_by_bridge_addrport(const tor_addr_t *addr, uint16_t port); typedef struct transport_t transport_t; int find_transport_by_bridge_addrport(const tor_addr_t *addr, uint16_t port, const transport_t **transport); transport_t *transport_get_by_name(const char *name); #endif
src/or/connection.c +1 −0 Changes for src/or/connection.c: 1 added line, 0 removed lines. Original line number Diff line number Diff line Loading @@ -34,6 +34,7 @@ #include "rendcommon.h" #include "rephist.h" #include "router.h" #include "transports.h" #include "routerparse.h" #ifdef USE_BUFFEREVENTS Loading
src/or/router.c +8 −0 Changes for src/or/router.c: 8 added lines, 0 removed lines. Original line number Diff line number Diff line Loading @@ -27,6 +27,7 @@ #include "router.h" #include "routerlist.h" #include "routerparse.h" #include "transports.h" /** * \file router.c Loading Loading @@ -2344,6 +2345,13 @@ extrainfo_dump_to_string(char **s_out, extrainfo_t *extrainfo, } } /* Add information about the pluggable transports we support. */ if (options->ServerTransportPlugin) { char *pluggable_transports = pt_get_extra_info_descriptor_string(); if (pluggable_transports) smartlist_add(chunks, pluggable_transports); } if (should_record_bridge_info(options) && write_stats_to_extrainfo) { const char *bridge_stats = geoip_get_bridge_stats_extrainfo(now); if (bridge_stats) { Loading