tor

The Tor anonymity network
git clone https://git.dasho.dev/tor.git
Log | Files | Refs | README | LICENSE

commit bb9707420e87a1efc016aeac1e59edbfc6be3f87
parent 66cd12e044a33870e5ce0732de21a1d7810d2469
Author: Daniel Pinto <danielpinto52@gmail.com>
Date:   Wed, 12 Aug 2020 00:24:30 +0100

Allow mutiple lines on configuration for ROUTERSET entries. #28361

Affected entries are: EntryNodes, ExcludeNodes, ExcludeExitNodes,
ExitNodes, MiddleNodes, HSLayer2Nodes and HSLayer3Nodes.

Diffstat:
Achanges/feature28361 | 5+++++
Mdoc/man/tor.1.txt | 25+++++++++++++++++++++++--
Msrc/feature/nodelist/routerset.c | 45++++++++++++++++++++++++++++++++++-----------
Msrc/feature/nodelist/routerset.h | 4++++
Asrc/test/conf_examples/bug_31495_1/expected | 2++
Asrc/test/conf_examples/bug_31495_1/expected_log | 2++
Asrc/test/conf_examples/bug_31495_1/torrc | 3+++
Asrc/test/conf_examples/bug_31495_2/error | 2++
Asrc/test/conf_examples/bug_31495_2/torrc | 4++++
Asrc/test/conf_examples/bug_31495_3/cmdline | 2++
Asrc/test/conf_examples/bug_31495_3/expected | 2++
Asrc/test/conf_examples/bug_31495_3/expected_log | 2++
Asrc/test/conf_examples/bug_31495_3/torrc | 4++++
Asrc/test/conf_examples/multiple_routerset_1/expected | 1+
Asrc/test/conf_examples/multiple_routerset_1/expected_log | 2++
Asrc/test/conf_examples/multiple_routerset_1/torrc | 3+++
Asrc/test/conf_examples/multiple_routerset_2/cmdline | 2++
Asrc/test/conf_examples/multiple_routerset_2/expected | 1+
Asrc/test/conf_examples/multiple_routerset_2/expected_log | 2++
Asrc/test/conf_examples/multiple_routerset_2/torrc | 3+++
Asrc/test/conf_examples/multiple_routerset_3/cmdline | 2++
Asrc/test/conf_examples/multiple_routerset_3/expected | 1+
Asrc/test/conf_examples/multiple_routerset_3/expected_log | 2++
Asrc/test/conf_examples/multiple_routerset_3/torrc | 3+++
Asrc/test/conf_examples/multiple_routerset_4/cmdline | 2++
Asrc/test/conf_examples/multiple_routerset_4/expected | 1+
Asrc/test/conf_examples/multiple_routerset_4/expected_log | 2++
Asrc/test/conf_examples/multiple_routerset_4/torrc | 4++++
28 files changed, 120 insertions(+), 13 deletions(-)

diff --git a/changes/feature28361 b/changes/feature28361 @@ -0,0 +1,5 @@ + o Minor feature (configuration): + - Allows configuration options EntryNodes, ExcludeNodes, + ExcludeExitNodes, ExitNodes, MiddleNodes, HSLayer2Nodes and + HSLayer3Nodes to be specified multiple times. Closes ticket + 28361. Patch by Daniel Pinto. diff --git a/doc/man/tor.1.txt b/doc/man/tor.1.txt @@ -1863,6 +1863,9 @@ different from other Tor clients: option overrides this option; if you have configured bridges and UseBridges is 1, the Bridges are used as your entry nodes. + + + This option can appear multiple times: the values from multiple lines are + spliced together. + + + The ExcludeNodes option overrides this option: any node listed in both EntryNodes and ExcludeNodes is treated as excluded. See <<ExcludeNodes,ExcludeNodes>> for more information on how to specify nodes. @@ -1875,6 +1878,9 @@ different from other Tor clients: (Example: ExcludeNodes ABCD1234CDEF5678ABCD1234CDEF5678ABCD1234, \{cc}, 255.254.0.0/8) + + + This option can appear multiple times: the values from multiple lines are + spliced together. + + + By default, this option is treated as a preference that Tor is allowed to override in order to keep working. For example, if you try to connect to a hidden service, @@ -1900,13 +1906,19 @@ different from other Tor clients: list too. See <<ExcludeNodes,ExcludeNodes>> for more information on how to specify nodes. See also the caveats on the <<ExitNodes,ExitNodes>> option below. - + + + This option can appear multiple times: the values from multiple lines are + spliced together. + + + [[ExitNodes]] **ExitNodes** __node__,__node__,__...__:: A list of identity fingerprints, country codes, and address patterns of nodes to use as exit node---that is, a node that delivers traffic for you *outside* the Tor network. See <<ExcludeNodes,ExcludeNodes>> for more information on how to specify nodes. + + + This option can appear multiple times: the values from multiple lines are + spliced together. + + + Note that if you list too few nodes here, or if you exclude too many exit nodes with ExcludeExitNodes, you can degrade functionality. For example, if none of the exits you list allows traffic on port 80 or 443, you won't @@ -1945,6 +1957,9 @@ different from other Tor clients: (Example: HSLayer2Nodes ABCD1234CDEF5678ABCD1234CDEF5678ABCD1234, \{cc}, 255.254.0.0/8) + + + This option can appear multiple times: the values from multiple lines are + spliced together. + + + When this is set, the resulting hidden service paths will look like: + @@ -2001,6 +2016,9 @@ different from other Tor clients: (Example: HSLayer3Nodes ABCD1234CDEF5678ABCD1234CDEF5678ABCD1234, \{cc}, 255.254.0.0/8) + + + This option can appear multiple times: the values from multiple lines are + spliced together. + + + When this is set by itself, the resulting hidden service paths will look like: + C - G - M - L3 - Rend + @@ -2048,7 +2066,10 @@ different from other Tor clients: to use for "middle" hops in your normal circuits. Normal circuits include all circuits except for direct connections to directory servers. Middle hops are all hops other than exit and entry. -+ + + + This option can appear multiple times: the values from multiple lines are + spliced together. + + + This is an **experimental** feature that is meant to be used by researchers and developers to test new features in the Tor network safely. Using it without care will strongly influence your anonymity. Other tor features may diff --git a/src/feature/nodelist/routerset.c b/src/feature/nodelist/routerset.c @@ -56,6 +56,7 @@ routerset_new(void) result->digests = digestmap_new(); result->policies = smartlist_new(); result->country_names = smartlist_new(); + result->fragile = 0; return result; } @@ -499,21 +500,32 @@ routerset_kv_parse(void *target, const config_line_t *line, char **errmsg, const void *params) { (void)params; - routerset_t **p = (routerset_t**)target; - routerset_free(*p); // clear the old value, if any. + routerset_t **lines = target; + + if (*lines && (*lines)->fragile) { + if (line->command == CONFIG_LINE_APPEND) { + (*lines)->fragile = 0; + } else { + routerset_free(*lines); // Represent empty sets as NULL + } + } + + int ret; routerset_t *rs = routerset_new(); if (routerset_parse(rs, line->value, line->key) < 0) { - routerset_free(rs); *errmsg = tor_strdup("Invalid router list."); - return -1; + ret = -1; } else { - if (routerset_is_empty(rs)) { - /* Represent empty sets as NULL. */ - routerset_free(rs); + if (!routerset_is_empty(rs)) { + if (!*lines) { + *lines = routerset_new(); + } + routerset_union(*lines, rs); } - *p = rs; - return 0; + ret = 0; } + routerset_free(rs); + return ret; } /** @@ -564,6 +576,15 @@ routerset_copy(void *dest, const void *src, const void *params) return 0; } +static void +routerset_mark_fragile(void *target, const void *params) +{ + (void)params; + routerset_t **ptr = (routerset_t **)target; + if (*ptr) + (*ptr)->fragile = 1; +} + /** * Function table to implement a routerset_t-based configuration type. **/ @@ -571,7 +592,8 @@ static const var_type_fns_t routerset_type_fns = { .kv_parse = routerset_kv_parse, .encode = routerset_encode, .clear = routerset_clear, - .copy = routerset_copy + .copy = routerset_copy, + .mark_fragile = routerset_mark_fragile, }; /** @@ -585,5 +607,6 @@ static const var_type_fns_t routerset_type_fns = { **/ const var_type_def_t ROUTERSET_type_defn = { .name = "RouterList", - .fns = &routerset_type_fns + .fns = &routerset_type_fns, + .flags = CFLG_NOREPLACE }; diff --git a/src/feature/nodelist/routerset.h b/src/feature/nodelist/routerset.h @@ -88,6 +88,10 @@ struct routerset_t { * routerset_refresh_countries() whenever the geoip country list is * reloaded. */ bitarray_t *countries; + /** If true, subsequent assignments to this routerset should replace + * it, not extend it. Set only on the first item in a routerset in an + * or_options_t. */ + unsigned int fragile:1; }; #endif /* defined(ROUTERSET_PRIVATE) */ #endif /* !defined(TOR_ROUTERSET_H) */ diff --git a/src/test/conf_examples/bug_31495_1/expected b/src/test/conf_examples/bug_31495_1/expected @@ -0,0 +1,2 @@ +Bridge 127.0.0.1:9050 +UseBridges 1 diff --git a/src/test/conf_examples/bug_31495_1/expected_log b/src/test/conf_examples/bug_31495_1/expected_log @@ -0,0 +1 @@ +Configuration was valid +\ No newline at end of file diff --git a/src/test/conf_examples/bug_31495_1/torrc b/src/test/conf_examples/bug_31495_1/torrc @@ -0,0 +1,2 @@ +UseBridges 1 +Bridge 127.0.0.1:9050 +\ No newline at end of file diff --git a/src/test/conf_examples/bug_31495_2/error b/src/test/conf_examples/bug_31495_2/error @@ -0,0 +1 @@ +Failed to parse/validate config: You cannot set both UseBridges and EntryNodes. +\ No newline at end of file diff --git a/src/test/conf_examples/bug_31495_2/torrc b/src/test/conf_examples/bug_31495_2/torrc @@ -0,0 +1,3 @@ +UseBridges 1 +Bridge 127.0.0.1:9050 +EntryNodes 127.0.0.1 +\ No newline at end of file diff --git a/src/test/conf_examples/bug_31495_3/cmdline b/src/test/conf_examples/bug_31495_3/cmdline @@ -0,0 +1 @@ +/EntryNodes +\ No newline at end of file diff --git a/src/test/conf_examples/bug_31495_3/expected b/src/test/conf_examples/bug_31495_3/expected @@ -0,0 +1,2 @@ +Bridge 127.0.0.1:9050 +UseBridges 1 diff --git a/src/test/conf_examples/bug_31495_3/expected_log b/src/test/conf_examples/bug_31495_3/expected_log @@ -0,0 +1 @@ +Configuration was valid +\ No newline at end of file diff --git a/src/test/conf_examples/bug_31495_3/torrc b/src/test/conf_examples/bug_31495_3/torrc @@ -0,0 +1,3 @@ +UseBridges 1 +Bridge 127.0.0.1:9050 +EntryNodes 127.0.0.1 +\ No newline at end of file diff --git a/src/test/conf_examples/multiple_routerset_1/expected b/src/test/conf_examples/multiple_routerset_1/expected @@ -0,0 +1 @@ +EntryNodes 127.0.0.1,127.0.0.2,127.0.0.3 diff --git a/src/test/conf_examples/multiple_routerset_1/expected_log b/src/test/conf_examples/multiple_routerset_1/expected_log @@ -0,0 +1 @@ +Configuration was valid +\ No newline at end of file diff --git a/src/test/conf_examples/multiple_routerset_1/torrc b/src/test/conf_examples/multiple_routerset_1/torrc @@ -0,0 +1,2 @@ +EntryNodes 127.0.0.1 +EntryNodes 127.0.0.2,127.0.0.3 +\ No newline at end of file diff --git a/src/test/conf_examples/multiple_routerset_2/cmdline b/src/test/conf_examples/multiple_routerset_2/cmdline @@ -0,0 +1 @@ +EntryNodes 127.0.0.4 +\ No newline at end of file diff --git a/src/test/conf_examples/multiple_routerset_2/expected b/src/test/conf_examples/multiple_routerset_2/expected @@ -0,0 +1 @@ +EntryNodes 127.0.0.4 diff --git a/src/test/conf_examples/multiple_routerset_2/expected_log b/src/test/conf_examples/multiple_routerset_2/expected_log @@ -0,0 +1 @@ +Configuration was valid +\ No newline at end of file diff --git a/src/test/conf_examples/multiple_routerset_2/torrc b/src/test/conf_examples/multiple_routerset_2/torrc @@ -0,0 +1,2 @@ +EntryNodes 127.0.0.1 +EntryNodes 127.0.0.2,127.0.0.3 +\ No newline at end of file diff --git a/src/test/conf_examples/multiple_routerset_3/cmdline b/src/test/conf_examples/multiple_routerset_3/cmdline @@ -0,0 +1 @@ ++EntryNodes 127.0.0.4 +\ No newline at end of file diff --git a/src/test/conf_examples/multiple_routerset_3/expected b/src/test/conf_examples/multiple_routerset_3/expected @@ -0,0 +1 @@ +EntryNodes 127.0.0.1,127.0.0.2,127.0.0.3,127.0.0.4 diff --git a/src/test/conf_examples/multiple_routerset_3/expected_log b/src/test/conf_examples/multiple_routerset_3/expected_log @@ -0,0 +1 @@ +Configuration was valid +\ No newline at end of file diff --git a/src/test/conf_examples/multiple_routerset_3/torrc b/src/test/conf_examples/multiple_routerset_3/torrc @@ -0,0 +1,2 @@ +EntryNodes 127.0.0.1 +EntryNodes 127.0.0.2,127.0.0.3 +\ No newline at end of file diff --git a/src/test/conf_examples/multiple_routerset_4/cmdline b/src/test/conf_examples/multiple_routerset_4/cmdline @@ -0,0 +1 @@ +/EntryNodes +\ No newline at end of file diff --git a/src/test/conf_examples/multiple_routerset_4/expected b/src/test/conf_examples/multiple_routerset_4/expected @@ -0,0 +1 @@ +ControlSocket 1234 diff --git a/src/test/conf_examples/multiple_routerset_4/expected_log b/src/test/conf_examples/multiple_routerset_4/expected_log @@ -0,0 +1 @@ +Configuration was valid +\ No newline at end of file diff --git a/src/test/conf_examples/multiple_routerset_4/torrc b/src/test/conf_examples/multiple_routerset_4/torrc @@ -0,0 +1,3 @@ +ControlSocket 1234 # dummy to prevent empty output +EntryNodes 127.0.0.1 +EntryNodes 127.0.0.2,127.0.0.3 +\ No newline at end of file