Loading changes/ticket31518 0 → 100644 +6 −0 Original line number Diff line number Diff line o Major features (proxy): - In addition to HTTP CONNECT, SOCKS4, and SOCKS5, Tor can make all OR connections through the HAProxy server. A new torrc option was added to specify the address/port of the server: TCPProxy <protocol> <host>:<port>. Currently the only supported protocol in the option is haproxy. Close ticket 31518. Patch done by Suphanat Chunhapanya (haxxpop). doc/tor.1.txt +16 −0 Original line number Diff line number Diff line Loading @@ -918,6 +918,22 @@ forward slash (/) in the configuration file and on the command line. log entries are marked with "Tor-__tag__". Can not be changed while tor is running. (Default: none) [[TCPProxy]] **TCPProxy** __protocol__ __host__:__port__:: Tor will use the given protocol to make all its OR (SSL) connections through a TCP proxy on host:port, rather than connecting directly to servers. You may want to set **FascistFirewall** to restrict the set of ports you might try to connect to, if your proxy only allows connecting to certain ports. There is no equivalent option for directory connections, because all Tor client versions that support this option download directory documents via OR connections. + + The only protocol supported right now 'haproxy'. This option is only for clients. (Default: none) + + The HAProxy version 1 proxy protocol is described in detail at https://www.haproxy.org/download/1.8/doc/proxy-protocol.txt + + Both source IP address and source port will be set to zero. [[TruncateLogFile]] **TruncateLogFile** **0**|**1**:: If 1, Tor will overwrite logs at startup and in response to a HUP signal, instead of appending to them. (Default: 0) Loading src/app/config/config.c +81 −8 Original line number Diff line number Diff line Loading @@ -538,6 +538,7 @@ static const config_var_t option_vars_[] = { V(Socks5Proxy, STRING, NULL), V(Socks5ProxyUsername, STRING, NULL), V(Socks5ProxyPassword, STRING, NULL), V(TCPProxy, STRING, NULL), VAR_IMMUTABLE("KeyDirectory", FILENAME, KeyDirectory_option, NULL), V(KeyDirectoryGroupReadable, AUTOBOOL, "auto"), VAR_D("HSLayer2Nodes", ROUTERSET, HSLayer2Nodes, NULL), Loading Loading @@ -3940,19 +3941,28 @@ options_validate_cb(const void *old_options_, void *options_, char **msg) } } if (options->TCPProxy) { int res = parse_tcp_proxy_line(options->TCPProxy, options, msg); if (res < 0) { return res; } } /* Check if more than one exclusive proxy type has been enabled. */ if (!!options->Socks4Proxy + !!options->Socks5Proxy + !!options->HTTPSProxy > 1) !!options->HTTPSProxy + !!options->TCPProxy > 1) REJECT("You have configured more than one proxy type. " "(Socks4Proxy|Socks5Proxy|HTTPSProxy)"); "(Socks4Proxy|Socks5Proxy|HTTPSProxy|TCPProxy)"); /* Check if the proxies will give surprising behavior. */ if (options->HTTPProxy && !(options->Socks4Proxy || options->Socks5Proxy || options->HTTPSProxy)) { log_warn(LD_CONFIG, "HTTPProxy configured, but no SOCKS proxy or " "HTTPS proxy configured. Watch out: this configuration will " "proxy unencrypted directory connections only."); options->HTTPSProxy || options->TCPProxy)) { log_warn(LD_CONFIG, "HTTPProxy configured, but no SOCKS proxy, " "HTTPS proxy, or any other TCP proxy configured. Watch out: " "this configuration will proxy unencrypted directory " "connections only."); } if (options->Socks5ProxyUsername) { Loading Loading @@ -5348,6 +5358,68 @@ parse_bridge_line(const char *line) return bridge_line; } /** Parse the contents of a TCPProxy line from <b>line</b> and put it * in <b>options</b>. Return 0 if the line is well-formed, and -1 if it * isn't. * * This will mutate only options->TCPProxyProtocol, options->TCPProxyAddr, * and options->TCPProxyPort. * * On error, tor_strdup an error explanation into *<b>msg</b>. */ STATIC int parse_tcp_proxy_line(const char *line, or_options_t *options, char **msg) { int ret = 0; tor_assert(line); tor_assert(options); tor_assert(msg); smartlist_t *sl = smartlist_new(); /* Split between the protocol and the address/port. */ smartlist_split_string(sl, line, " ", SPLIT_SKIP_SPACE|SPLIT_IGNORE_BLANK, 2); /* The address/port is not specified. */ if (smartlist_len(sl) < 2) { *msg = tor_strdup("TCPProxy has no address/port. Please fix."); goto err; } char *protocol_string = smartlist_get(sl, 0); char *addrport_string = smartlist_get(sl, 1); /* The only currently supported protocol is 'haproxy'. */ if (strcasecmp(protocol_string, "haproxy")) { *msg = tor_strdup("TCPProxy protocol is not supported. Currently " "the only supported protocol is 'haproxy'. " "Please fix."); goto err; } else { /* Otherwise, set the correct protocol. */ options->TCPProxyProtocol = TCP_PROXY_PROTOCOL_HAPROXY; } /* Parse the address/port. */ if (tor_addr_port_lookup(addrport_string, &options->TCPProxyAddr, &options->TCPProxyPort) < 0) { *msg = tor_strdup("TCPProxy address/port failed to parse or resolve. " "Please fix."); goto err; } /* Success. */ ret = 0; goto end; err: ret = -1; end: SMARTLIST_FOREACH(sl, char *, cp, tor_free(cp)); smartlist_free(sl); return ret; } /** Read the contents of a ClientTransportPlugin or ServerTransportPlugin * line from <b>line</b>, depending on the value of <b>server</b>. Return 0 * if the line is well-formed, and -1 if it isn't. Loading Loading @@ -5495,9 +5567,10 @@ pt_parse_transport_line(const or_options_t *options, /* ClientTransportPlugins connecting through a proxy is managed only. */ if (!server && (options->Socks4Proxy || options->Socks5Proxy || options->HTTPSProxy)) { options->HTTPSProxy || options->TCPProxy)) { log_warn(LD_CONFIG, "You have configured an external proxy with another " "proxy type. (Socks4Proxy|Socks5Proxy|HTTPSProxy)"); "proxy type. (Socks4Proxy|Socks5Proxy|HTTPSProxy|" "TCPProxy)"); goto err; } Loading src/app/config/config.h +2 −0 Original line number Diff line number Diff line Loading @@ -286,6 +286,8 @@ STATIC const struct config_mgr_t *get_options_mgr(void); STATIC void or_options_free_(or_options_t *options); STATIC int options_validate_single_onion(or_options_t *options, char **msg); STATIC int parse_tcp_proxy_line(const char *line, or_options_t *options, char **msg); STATIC int consider_adding_dir_servers(const or_options_t *options, const or_options_t *old_options); STATIC void add_default_trusted_dir_authorities(dirinfo_type_t type); Loading src/app/config/or_options_st.h +11 −0 Original line number Diff line number Diff line Loading @@ -27,6 +27,12 @@ typedef enum {OUTBOUND_ADDR_EXIT, OUTBOUND_ADDR_OR, OUTBOUND_ADDR_EXIT_AND_OR, OUTBOUND_ADDR_MAX} outbound_addr_t; /** Which protocol to use for TCPProxy. */ typedef enum { /** Use the HAProxy proxy protocol. */ TCP_PROXY_PROTOCOL_HAPROXY } tcp_proxy_protocol_t; /** Configuration options for a Tor process. */ struct or_options_t { uint32_t magic_; Loading Loading @@ -419,6 +425,11 @@ struct or_options_t { char *Socks5ProxyUsername; /**< Username for SOCKS5 authentication, if any */ char *Socks5ProxyPassword; /**< Password for SOCKS5 authentication, if any */ char *TCPProxy; /**< protocol and hostname:port to use as a proxy, if any. */ tcp_proxy_protocol_t TCPProxyProtocol; /**< Derived from TCPProxy. */ tor_addr_t TCPProxyAddr; /**< Derived from TCPProxy. */ uint16_t TCPProxyPort; /**< Derived from TCPProxy. */ /** List of configuration lines for replacement directory authorities. * If you just want to replace one class of authority at a time, * use the "Alternate*Authority" options below instead. */ Loading Loading
changes/ticket31518 0 → 100644 +6 −0 Original line number Diff line number Diff line o Major features (proxy): - In addition to HTTP CONNECT, SOCKS4, and SOCKS5, Tor can make all OR connections through the HAProxy server. A new torrc option was added to specify the address/port of the server: TCPProxy <protocol> <host>:<port>. Currently the only supported protocol in the option is haproxy. Close ticket 31518. Patch done by Suphanat Chunhapanya (haxxpop).
doc/tor.1.txt +16 −0 Original line number Diff line number Diff line Loading @@ -918,6 +918,22 @@ forward slash (/) in the configuration file and on the command line. log entries are marked with "Tor-__tag__". Can not be changed while tor is running. (Default: none) [[TCPProxy]] **TCPProxy** __protocol__ __host__:__port__:: Tor will use the given protocol to make all its OR (SSL) connections through a TCP proxy on host:port, rather than connecting directly to servers. You may want to set **FascistFirewall** to restrict the set of ports you might try to connect to, if your proxy only allows connecting to certain ports. There is no equivalent option for directory connections, because all Tor client versions that support this option download directory documents via OR connections. + + The only protocol supported right now 'haproxy'. This option is only for clients. (Default: none) + + The HAProxy version 1 proxy protocol is described in detail at https://www.haproxy.org/download/1.8/doc/proxy-protocol.txt + + Both source IP address and source port will be set to zero. [[TruncateLogFile]] **TruncateLogFile** **0**|**1**:: If 1, Tor will overwrite logs at startup and in response to a HUP signal, instead of appending to them. (Default: 0) Loading
src/app/config/config.c +81 −8 Original line number Diff line number Diff line Loading @@ -538,6 +538,7 @@ static const config_var_t option_vars_[] = { V(Socks5Proxy, STRING, NULL), V(Socks5ProxyUsername, STRING, NULL), V(Socks5ProxyPassword, STRING, NULL), V(TCPProxy, STRING, NULL), VAR_IMMUTABLE("KeyDirectory", FILENAME, KeyDirectory_option, NULL), V(KeyDirectoryGroupReadable, AUTOBOOL, "auto"), VAR_D("HSLayer2Nodes", ROUTERSET, HSLayer2Nodes, NULL), Loading Loading @@ -3940,19 +3941,28 @@ options_validate_cb(const void *old_options_, void *options_, char **msg) } } if (options->TCPProxy) { int res = parse_tcp_proxy_line(options->TCPProxy, options, msg); if (res < 0) { return res; } } /* Check if more than one exclusive proxy type has been enabled. */ if (!!options->Socks4Proxy + !!options->Socks5Proxy + !!options->HTTPSProxy > 1) !!options->HTTPSProxy + !!options->TCPProxy > 1) REJECT("You have configured more than one proxy type. " "(Socks4Proxy|Socks5Proxy|HTTPSProxy)"); "(Socks4Proxy|Socks5Proxy|HTTPSProxy|TCPProxy)"); /* Check if the proxies will give surprising behavior. */ if (options->HTTPProxy && !(options->Socks4Proxy || options->Socks5Proxy || options->HTTPSProxy)) { log_warn(LD_CONFIG, "HTTPProxy configured, but no SOCKS proxy or " "HTTPS proxy configured. Watch out: this configuration will " "proxy unencrypted directory connections only."); options->HTTPSProxy || options->TCPProxy)) { log_warn(LD_CONFIG, "HTTPProxy configured, but no SOCKS proxy, " "HTTPS proxy, or any other TCP proxy configured. Watch out: " "this configuration will proxy unencrypted directory " "connections only."); } if (options->Socks5ProxyUsername) { Loading Loading @@ -5348,6 +5358,68 @@ parse_bridge_line(const char *line) return bridge_line; } /** Parse the contents of a TCPProxy line from <b>line</b> and put it * in <b>options</b>. Return 0 if the line is well-formed, and -1 if it * isn't. * * This will mutate only options->TCPProxyProtocol, options->TCPProxyAddr, * and options->TCPProxyPort. * * On error, tor_strdup an error explanation into *<b>msg</b>. */ STATIC int parse_tcp_proxy_line(const char *line, or_options_t *options, char **msg) { int ret = 0; tor_assert(line); tor_assert(options); tor_assert(msg); smartlist_t *sl = smartlist_new(); /* Split between the protocol and the address/port. */ smartlist_split_string(sl, line, " ", SPLIT_SKIP_SPACE|SPLIT_IGNORE_BLANK, 2); /* The address/port is not specified. */ if (smartlist_len(sl) < 2) { *msg = tor_strdup("TCPProxy has no address/port. Please fix."); goto err; } char *protocol_string = smartlist_get(sl, 0); char *addrport_string = smartlist_get(sl, 1); /* The only currently supported protocol is 'haproxy'. */ if (strcasecmp(protocol_string, "haproxy")) { *msg = tor_strdup("TCPProxy protocol is not supported. Currently " "the only supported protocol is 'haproxy'. " "Please fix."); goto err; } else { /* Otherwise, set the correct protocol. */ options->TCPProxyProtocol = TCP_PROXY_PROTOCOL_HAPROXY; } /* Parse the address/port. */ if (tor_addr_port_lookup(addrport_string, &options->TCPProxyAddr, &options->TCPProxyPort) < 0) { *msg = tor_strdup("TCPProxy address/port failed to parse or resolve. " "Please fix."); goto err; } /* Success. */ ret = 0; goto end; err: ret = -1; end: SMARTLIST_FOREACH(sl, char *, cp, tor_free(cp)); smartlist_free(sl); return ret; } /** Read the contents of a ClientTransportPlugin or ServerTransportPlugin * line from <b>line</b>, depending on the value of <b>server</b>. Return 0 * if the line is well-formed, and -1 if it isn't. Loading Loading @@ -5495,9 +5567,10 @@ pt_parse_transport_line(const or_options_t *options, /* ClientTransportPlugins connecting through a proxy is managed only. */ if (!server && (options->Socks4Proxy || options->Socks5Proxy || options->HTTPSProxy)) { options->HTTPSProxy || options->TCPProxy)) { log_warn(LD_CONFIG, "You have configured an external proxy with another " "proxy type. (Socks4Proxy|Socks5Proxy|HTTPSProxy)"); "proxy type. (Socks4Proxy|Socks5Proxy|HTTPSProxy|" "TCPProxy)"); goto err; } Loading
src/app/config/config.h +2 −0 Original line number Diff line number Diff line Loading @@ -286,6 +286,8 @@ STATIC const struct config_mgr_t *get_options_mgr(void); STATIC void or_options_free_(or_options_t *options); STATIC int options_validate_single_onion(or_options_t *options, char **msg); STATIC int parse_tcp_proxy_line(const char *line, or_options_t *options, char **msg); STATIC int consider_adding_dir_servers(const or_options_t *options, const or_options_t *old_options); STATIC void add_default_trusted_dir_authorities(dirinfo_type_t type); Loading
src/app/config/or_options_st.h +11 −0 Original line number Diff line number Diff line Loading @@ -27,6 +27,12 @@ typedef enum {OUTBOUND_ADDR_EXIT, OUTBOUND_ADDR_OR, OUTBOUND_ADDR_EXIT_AND_OR, OUTBOUND_ADDR_MAX} outbound_addr_t; /** Which protocol to use for TCPProxy. */ typedef enum { /** Use the HAProxy proxy protocol. */ TCP_PROXY_PROTOCOL_HAPROXY } tcp_proxy_protocol_t; /** Configuration options for a Tor process. */ struct or_options_t { uint32_t magic_; Loading Loading @@ -419,6 +425,11 @@ struct or_options_t { char *Socks5ProxyUsername; /**< Username for SOCKS5 authentication, if any */ char *Socks5ProxyPassword; /**< Password for SOCKS5 authentication, if any */ char *TCPProxy; /**< protocol and hostname:port to use as a proxy, if any. */ tcp_proxy_protocol_t TCPProxyProtocol; /**< Derived from TCPProxy. */ tor_addr_t TCPProxyAddr; /**< Derived from TCPProxy. */ uint16_t TCPProxyPort; /**< Derived from TCPProxy. */ /** List of configuration lines for replacement directory authorities. * If you just want to replace one class of authority at a time, * use the "Alternate*Authority" options below instead. */ Loading