tor-commits
Threads by month
- ----- 2025 -----
- June
- May
- April
- March
- February
- January
- ----- 2024 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2023 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2022 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2021 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2020 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2019 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2018 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2017 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2016 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2015 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2014 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2013 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2012 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2011 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
February 2011
- 14 participants
- 290 discussions

22 Feb '11
commit 7736f44698798111be413ca3285a77ce1e4d6b0c
Author: Sebastian Hahn <sebastian(a)torproject.org>
Date: Sun Feb 6 00:25:33 2011 +0100
Don't tell Tor client users about missing geoip
They don't need the geoip file for stats, so a missing geoipfile is not
a big issue. Also make the log message a bit friendlier. Fixes bug 2496.
---
src/or/config.c | 14 ++++++++------
1 files changed, 8 insertions(+), 6 deletions(-)
diff --git a/src/or/config.c b/src/or/config.c
index 1fa8466..1dc042d 100644
--- a/src/or/config.c
+++ b/src/or/config.c
@@ -1386,10 +1386,12 @@ options_act(or_options_t *old_options)
print_notice = 1;
} else {
options->DirReqStatistics = 0;
- log_notice(LD_CONFIG, "Configured to measure directory request "
- "statistics, but no GeoIP database found! "
- "Please specify a GeoIP database using the "
- "GeoIPFile option!");
+ /* Don't warn Tor clients, they don't use statistics */
+ if (options->ORPort)
+ log_notice(LD_CONFIG, "Configured to measure directory request "
+ "statistics, but no GeoIP database found. "
+ "Please specify a GeoIP database using the "
+ "GeoIPFile option.");
}
}
if ((!old_options || !old_options->EntryStatistics) &&
@@ -1400,9 +1402,9 @@ options_act(or_options_t *old_options)
} else {
options->EntryStatistics = 0;
log_notice(LD_CONFIG, "Configured to measure entry node "
- "statistics, but no GeoIP database found! "
+ "statistics, but no GeoIP database found. "
"Please specify a GeoIP database using the "
- "GeoIPFile option!");
+ "GeoIPFile option.");
}
}
if ((!old_options || !old_options->ExitPortStatistics) &&
1
0
commit b7f201f74606aff1f77551449bebe8783a59733a
Merge: 46b0746 cdc59c1
Author: Nick Mathewson <nickm(a)torproject.org>
Date: Tue Feb 22 14:10:42 2011 -0500
Merge remote branch 'origin/maint-0.2.2'
Conflicts:
src/or/policies.c
src/or/policies.h
changes/bug2366 | 8 ++++++++
src/or/policies.c | 8 ++++++++
src/or/policies.h | 1 +
src/or/router.c | 15 +++++++++------
4 files changed, 26 insertions(+), 6 deletions(-)
diff --combined src/or/policies.c
index d0406d3,38c2f7c..2cf9982
--- a/src/or/policies.c
+++ b/src/or/policies.c
@@@ -11,7 -11,6 +11,7 @@@
#include "or.h"
#include "config.h"
#include "dirserv.h"
+#include "nodelist.h"
#include "policies.h"
#include "routerparse.h"
#include "ht.h"
@@@ -262,7 -261,7 +262,7 @@@ fascist_firewall_allows_address_or(cons
/** Return true iff we think our firewall will let us make an OR connection to
* <b>ri</b>. */
int
-fascist_firewall_allows_or(routerinfo_t *ri)
+fascist_firewall_allows_or(const routerinfo_t *ri)
{
/* XXXX proposal 118 */
tor_addr_t addr;
@@@ -270,22 -269,6 +270,22 @@@
return fascist_firewall_allows_address_or(&addr, ri->or_port);
}
+/** Return true iff we think our firewall will let us make an OR connection to
+ * <b>node</b>. */
+int
+fascist_firewall_allows_node(const node_t *node)
+{
+ if (node->ri) {
+ return fascist_firewall_allows_or(node->ri);
+ } else if (node->rs) {
+ tor_addr_t addr;
+ tor_addr_from_ipv4h(&addr, node->rs->addr);
+ return fascist_firewall_allows_address_or(&addr, node->rs->or_port);
+ } else {
+ return 1;
+ }
+}
+
/** Return true iff we think our firewall will let us make a directory
* connection to addr:port. */
int
@@@ -875,11 -858,23 +875,19 @@@ policies_parse_exit_policy(config_line_
return 0;
}
+ /** Add "reject *:*" to the end of the policy in *<b>dest</b>, allocating
+ * *<b>dest</b> as needed. */
+ void
+ policies_exit_policy_append_reject_star(smartlist_t **dest)
+ {
+ append_exit_policy_string(dest, "reject *:*");
+ }
+
-/** Replace the exit policy of <b>r</b> with reject *:*. */
+/** Replace the exit policy of <b>node</b> with reject *:* */
void
-policies_set_router_exitpolicy_to_reject_all(routerinfo_t *r)
+policies_set_node_exitpolicy_to_reject_all(node_t *node)
{
- addr_policy_t *item;
- addr_policy_list_free(r->exit_policy);
- r->exit_policy = smartlist_create();
- item = router_parse_addr_policy_item_from_string("reject *:*", -1);
- smartlist_add(r->exit_policy, item);
+ node->rejects_all = 1;
}
/** Return 1 if there is at least one /8 subnet in <b>policy</b> that
@@@ -1088,7 -1083,7 +1096,7 @@@ policy_summary_split(smartlist_t *summa
int start_at_index;
int i = 0;
- /* XXXX Do a binary search if run time matters */
+
while (AT(i)->prt_max < prt_min)
i++;
if (AT(i)->prt_min != prt_min) {
@@@ -1301,195 -1296,6 +1309,195 @@@ policy_summarize(smartlist_t *policy
return result;
}
+/** Convert a summarized policy string into a short_policy_t. Return NULL
+ * if the string is not well-formed. */
+short_policy_t *
+parse_short_policy(const char *summary)
+{
+ const char *orig_summary = summary;
+ short_policy_t *result;
+ int is_accept;
+ int n_entries;
+ short_policy_entry_t entries[MAX_EXITPOLICY_SUMMARY_LEN]; /* overkill */
+ const char *next;
+
+ if (!strcmpstart(summary, "accept ")) {
+ is_accept = 1;
+ summary += strlen("accept ");
+ } else if (!strcmpstart(summary, "reject ")) {
+ is_accept = 0;
+ summary += strlen("reject ");
+ } else {
+ log_fn(LOG_PROTOCOL_WARN, LD_DIR, "Unrecognized policy summary keyword");
+ return NULL;
+ }
+
+ n_entries = 0;
+ for ( ; *summary; summary = next) {
+ const char *comma = strchr(summary, ',');
+ unsigned low, high;
+ char dummy;
+ char ent_buf[32];
+
+ next = comma ? comma+1 : strchr(summary, '\0');
+
+ if (n_entries == MAX_EXITPOLICY_SUMMARY_LEN) {
+ log_fn(LOG_PROTOCOL_WARN, LD_DIR, "Impossibly long policy summary %s",
+ escaped(orig_summary));
+ return NULL;
+ }
+
+ if (! TOR_ISDIGIT(*summary) || next-summary > (int)(sizeof(ent_buf)-1)) {
+ /* unrecognized entry format. skip it. */
+ continue;
+ }
+ if (next-summary < 2) {
+ /* empty; skip it. */
+ continue;
+ }
+
+ memcpy(ent_buf, summary, next-summary-1);
+ ent_buf[next-summary-1] = '\0';
+
+ if (tor_sscanf(ent_buf, "%u-%u%c", &low, &high, &dummy) == 2) {
+ if (low<1 || low>65535 || high<1 || high>65535) {
+ log_fn(LOG_PROTOCOL_WARN, LD_DIR,
+ "Found bad entry in policy summary %s", escaped(orig_summary));
+ return NULL;
+ }
+ } else if (tor_sscanf(ent_buf, "%u%c", &low, &dummy) == 1) {
+ if (low<1 || low>65535) {
+ log_fn(LOG_PROTOCOL_WARN, LD_DIR,
+ "Found bad entry in policy summary %s", escaped(orig_summary));
+ return NULL;
+ }
+ high = low;
+ } else {
+ log_fn(LOG_PROTOCOL_WARN, LD_DIR,"Found bad entry in policy summary %s",
+ escaped(orig_summary));
+ return NULL;
+ }
+
+ entries[n_entries].min_port = low;
+ entries[n_entries].max_port = high;
+ n_entries++;
+ }
+
+ if (n_entries == 0) {
+ log_fn(LOG_PROTOCOL_WARN, LD_DIR,
+ "Found no port-range entries in summary %s", escaped(orig_summary));
+ return NULL;
+ }
+
+ {
+ size_t size = STRUCT_OFFSET(short_policy_t, entries) +
+ sizeof(short_policy_entry_t)*(n_entries);
+ result = tor_malloc_zero(size);
+
+ tor_assert( (char*)&result->entries[n_entries-1] < ((char*)result)+size);
+ }
+
+ result->is_accept = is_accept;
+ result->n_entries = n_entries;
+ memcpy(result->entries, entries, sizeof(short_policy_entry_t)*n_entries);
+ return result;
+}
+
+/** Release all storage held in <b>policy</b>. */
+void
+short_policy_free(short_policy_t *policy)
+{
+ tor_free(policy);
+}
+
+/** See whether the <b>addr</b>:<b>port</b> address is likely to be accepted
+ * or rejected by the summarized policy <b>policy</b>. Return values are as
+ * for compare_tor_addr_to_addr_policy. Unlike the regular addr_policy
+ * functions, requires the <b>port</b> be specified. */
+addr_policy_result_t
+compare_tor_addr_to_short_policy(const tor_addr_t *addr, uint16_t port,
+ const short_policy_t *policy)
+{
+ int i;
+ int found_match = 0;
+ int accept;
+ (void)addr;
+
+ tor_assert(port != 0);
+
+ if (addr && (tor_addr_is_internal(addr, 0) ||
+ tor_addr_is_null(addr) ||
+ tor_addr_is_loopback(addr)))
+ return ADDR_POLICY_REJECTED;
+
+ for (i=0; i < policy->n_entries; ++i) {
+ const short_policy_entry_t *e = &policy->entries[i];
+ if (e->min_port <= port && port <= e->max_port) {
+ found_match = 1;
+ break;
+ }
+ }
+
+ if (found_match)
+ accept = policy->is_accept;
+ else
+ accept = ! policy->is_accept;
+
+ /* ???? are these right? */
+ if (accept)
+ return ADDR_POLICY_PROBABLY_ACCEPTED;
+ else
+ return ADDR_POLICY_REJECTED;
+}
+
+/** Return true iff <b>policy</b> seems reject all ports */
+int
+short_policy_is_reject_star(const short_policy_t *policy)
+{
+ /* This doesn't need to be as much on the lookout as policy_is_reject_star,
+ * since policy summaries are from the consensus or from consensus
+ * microdescs.
+ */
+ tor_assert(policy);
+ /* Check for an exact match of "reject 1-65535". */
+ return (policy->is_accept == 0 && policy->n_entries == 1 &&
+ policy->entries[0].min_port == 1 &&
+ policy->entries[0].max_port == 65535);
+}
+
+/** Decides whether addr:port is probably or definitely accepted or rejcted by
+ * <b>node</b>. See compare_tor_addr_to_addr_policy for details on addr/port
+ * interpretation. */
+addr_policy_result_t
+compare_addr_to_node_policy(uint32_t addr, uint16_t port, const node_t *node)
+{
+ tor_addr_t a;
+ tor_addr_from_ipv4h(&a, addr);
+ return compare_tor_addr_to_node_policy(&a, port, node);
+}
+
+/** Decides whether addr:port is probably or definitely accepted or rejcted by
+ * <b>node</b>. See compare_tor_addr_to_addr_policy for details on addr/port
+ * interpretation. */
+addr_policy_result_t
+compare_tor_addr_to_node_policy(const tor_addr_t *addr, uint16_t port,
+ const node_t *node)
+{
+ if (node->rejects_all)
+ return ADDR_POLICY_REJECTED;
+
+ if (node->ri)
+ return compare_tor_addr_to_addr_policy(addr, port, node->ri->exit_policy);
+ else if (node->md && node->md) {
+ if (node->md->exit_policy == NULL)
+ return ADDR_POLICY_REJECTED;
+ else
+ return compare_tor_addr_to_short_policy(addr, port,
+ node->md->exit_policy);
+ } else
+ return ADDR_POLICY_PROBABLY_REJECTED;
+}
+
/** Implementation for GETINFO control command: knows the answer for questions
* about "exit-policy/..." */
int
diff --combined src/or/policies.h
index 371123c,b2947c6..ee1162c
--- a/src/or/policies.h
+++ b/src/or/policies.h
@@@ -19,8 -19,7 +19,8 @@@
int firewall_is_fascist_or(void);
int fascist_firewall_allows_address_or(const tor_addr_t *addr, uint16_t port);
-int fascist_firewall_allows_or(routerinfo_t *ri);
+int fascist_firewall_allows_or(const routerinfo_t *ri);
+int fascist_firewall_allows_node(const node_t *node);
int fascist_firewall_allows_address_dir(const tor_addr_t *addr, uint16_t port);
int dir_policy_permits_address(const tor_addr_t *addr);
int socks_policy_permits_address(const tor_addr_t *addr);
@@@ -39,16 -38,11 +39,17 @@@ addr_policy_result_t compare_tor_addr_t
uint16_t port, const smartlist_t *policy);
addr_policy_result_t compare_addr_to_addr_policy(uint32_t addr,
uint16_t port, const smartlist_t *policy);
+
+addr_policy_result_t compare_addr_to_node_policy(uint32_t addr,
+ uint16_t port, const node_t *node);
+addr_policy_result_t compare_tor_addr_to_node_policy(const tor_addr_t *addr,
+ uint16_t port, const node_t *node);
+
int policies_parse_exit_policy(config_line_t *cfg, smartlist_t **dest,
int rejectprivate, const char *local_address,
int add_default_policy);
+ void policies_exit_policy_append_reject_star(smartlist_t **dest);
-void policies_set_router_exitpolicy_to_reject_all(routerinfo_t *exitrouter);
+void policies_set_node_exitpolicy_to_reject_all(node_t *exitrouter);
int exit_policy_is_general_exit(smartlist_t *policy);
int policy_is_reject_star(const smartlist_t *policy);
int getinfo_helper_policies(control_connection_t *conn,
@@@ -63,12 -57,5 +64,12 @@@ void policies_free_all(void)
char *policy_summarize(smartlist_t *policy);
+short_policy_t *parse_short_policy(const char *summary);
+void short_policy_free(short_policy_t *policy);
+int short_policy_is_reject_star(const short_policy_t *policy);
+addr_policy_result_t compare_tor_addr_to_short_policy(
+ const tor_addr_t *addr, uint16_t port,
+ const short_policy_t *policy);
+
#endif
diff --combined src/or/router.c
index ed998e4,4c5eb7a..3f1a0a0
--- a/src/or/router.c
+++ b/src/or/router.c
@@@ -7,7 -7,6 +7,7 @@@
#define ROUTER_PRIVATE
#include "or.h"
+#include "circuitbuild.h"
#include "circuitlist.h"
#include "circuituse.h"
#include "config.h"
@@@ -20,7 -19,6 +20,7 @@@
#include "hibernate.h"
#include "main.h"
#include "networkstatus.h"
+#include "nodelist.h"
#include "policies.h"
#include "relay.h"
#include "rephist.h"
@@@ -152,8 -150,8 +152,8 @@@ assert_identity_keys_ok(void
} else {
/* assert that we have set the client and server keys to be unequal */
if (server_identitykey)
- tor_assert(0!=crypto_pk_cmp_keys(client_identitykey,
- server_identitykey));
+ tor_assert(0!=crypto_pk_cmp_keys(client_identitykey,
+ server_identitykey));
}
}
@@@ -849,21 -847,18 +849,21 @@@ decide_to_advertise_dirport(or_options_
void
consider_testing_reachability(int test_or, int test_dir)
{
- routerinfo_t *me = router_get_my_routerinfo();
+ const routerinfo_t *me = router_get_my_routerinfo();
int orport_reachable = check_whether_orport_reachable();
tor_addr_t addr;
if (!me)
return;
if (test_or && (!orport_reachable || !circuit_enough_testing_circs())) {
+ extend_info_t *ei;
log_info(LD_CIRC, "Testing %s of my ORPort: %s:%d.",
!orport_reachable ? "reachability" : "bandwidth",
me->address, me->or_port);
- circuit_launch_by_router(CIRCUIT_PURPOSE_TESTING, me,
- CIRCLAUNCH_NEED_CAPACITY|CIRCLAUNCH_IS_INTERNAL);
+ ei = extend_info_from_router(me);
+ circuit_launch_by_extend_info(CIRCUIT_PURPOSE_TESTING, ei,
+ CIRCLAUNCH_NEED_CAPACITY|CIRCLAUNCH_IS_INTERNAL);
+ extend_info_free(ei);
}
tor_addr_from_ipv4h(&addr, me->addr);
@@@ -887,7 -882,7 +887,7 @@@ voi
router_orport_found_reachable(void)
{
if (!can_reach_or_port) {
- routerinfo_t *me = router_get_my_routerinfo();
+ const routerinfo_t *me = router_get_my_routerinfo();
log_notice(LD_OR,"Self-testing indicates your ORPort is reachable from "
"the outside. Excellent.%s",
get_options()->_PublishServerDescriptor != NO_AUTHORITY ?
@@@ -910,7 -905,7 +910,7 @@@ voi
router_dirport_found_reachable(void)
{
if (!can_reach_dir_port) {
- routerinfo_t *me = router_get_my_routerinfo();
+ const routerinfo_t *me = router_get_my_routerinfo();
log_notice(LD_DIRSERV,"Self-testing indicates your DirPort is reachable "
"from the outside. Excellent.");
can_reach_dir_port = 1;
@@@ -1181,7 -1176,7 +1181,7 @@@ static int desc_needs_upload = 0
void
router_upload_dir_desc_to_dirservers(int force)
{
- routerinfo_t *ri;
+ const routerinfo_t *ri;
extrainfo_t *ei;
char *msg;
size_t desc_len, extra_len = 0, total_len;
@@@ -1275,7 -1270,7 +1275,7 @@@ router_extrainfo_digest_is_me(const cha
/** A wrapper around router_digest_is_me(). */
int
-router_is_me(routerinfo_t *router)
+router_is_me(const routerinfo_t *router)
{
return router_digest_is_me(router->cache_info.identity_digest);
}
@@@ -1294,7 -1289,7 +1294,7 @@@ router_fingerprint_is_me(const char *fp
/** Return a routerinfo for this OR, rebuilding a fresh one if
* necessary. Return NULL on error, or if called on an OP. */
-routerinfo_t *
+const routerinfo_t *
router_get_my_routerinfo(void)
{
if (!server_mode(get_options()))
@@@ -1346,6 -1341,8 +1346,6 @@@ static int router_guess_address_from_di
int
router_pick_published_address(or_options_t *options, uint32_t *addr)
{
- char buf[INET_NTOA_BUF_LEN];
- struct in_addr a;
if (resolve_my_address(LOG_INFO, options, addr, NULL) < 0) {
log_info(LD_CONFIG, "Could not determine our address locally. "
"Checking if directory headers provide any hints.");
@@@ -1355,7 -1352,9 +1355,7 @@@
return -1;
}
}
- a.s_addr = htonl(*addr);
- tor_inet_ntoa(&a, buf, sizeof(buf));
- log_info(LD_CONFIG,"Success: chose address '%s'.", buf);
+ log_info(LD_CONFIG,"Success: chose address '%s'.", fmt_addr32(*addr));
return 0;
}
@@@ -1411,18 -1410,24 +1411,23 @@@ router_rebuild_descriptor(int force
ri->bandwidthcapacity = hibernating ? 0 : rep_hist_bandwidth_assess();
- policies_parse_exit_policy(options->ExitPolicy, &ri->exit_policy,
- options->ExitPolicyRejectPrivate,
- ri->address, !options->BridgeRelay);
+ if (dns_seems_to_be_broken() || has_dns_init_failed()) {
+ /* DNS is screwed up; don't claim to be an exit. */
+ policies_exit_policy_append_reject_star(&ri->exit_policy);
+ } else {
+ policies_parse_exit_policy(options->ExitPolicy, &ri->exit_policy,
+ options->ExitPolicyRejectPrivate,
+ ri->address, !options->BridgeRelay);
+ }
ri->policy_is_reject_star =
policy_is_reject_star(ri->exit_policy);
- if (desc_routerinfo) { /* inherit values */
- ri->is_valid = desc_routerinfo->is_valid;
- ri->is_running = desc_routerinfo->is_running;
- ri->is_named = desc_routerinfo->is_named;
- }
+#if 0
+ /* XXXX NM NM I belive this is safe to remove */
if (authdir_mode(options))
ri->is_valid = ri->is_named = 1; /* believe in yourself */
+#endif
+
if (options->MyFamily) {
smartlist_t *family;
if (!warned_nonexistent_family)
@@@ -1431,12 -1436,13 +1436,12 @@@
ri->declared_family = smartlist_create();
smartlist_split_string(family, options->MyFamily, ",",
SPLIT_SKIP_SPACE|SPLIT_SKIP_SPACE|SPLIT_IGNORE_BLANK, 0);
- SMARTLIST_FOREACH(family, char *, name,
- {
- routerinfo_t *member;
+ SMARTLIST_FOREACH_BEGIN(family, char *, name) {
+ const node_t *member;
if (!strcasecmp(name, options->Nickname))
- member = ri;
+ goto skip; /* Don't list ourself, that's redundant */
else
- member = router_get_by_nickname(name, 1);
+ member = node_get_by_nickname(name, 1);
if (!member) {
int is_legal = is_legal_nickname_or_hexdigest(name);
if (!smartlist_string_isin(warned_nonexistent_family, name) &&
@@@ -1456,21 -1462,19 +1461,21 @@@
smartlist_add(ri->declared_family, name);
name = NULL;
}
- } else if (router_is_me(member)) {
+ } else if (router_digest_is_me(member->identity)) {
/* Don't list ourself in our own family; that's redundant */
+ /* XXX shouldn't be possible */
} else {
char *fp = tor_malloc(HEX_DIGEST_LEN+2);
fp[0] = '$';
base16_encode(fp+1,HEX_DIGEST_LEN+1,
- member->cache_info.identity_digest, DIGEST_LEN);
+ member->identity, DIGEST_LEN);
smartlist_add(ri->declared_family, fp);
if (smartlist_string_isin(warned_nonexistent_family, name))
smartlist_string_remove(warned_nonexistent_family, name);
}
+ skip:
tor_free(name);
- });
+ } SMARTLIST_FOREACH_END(name);
/* remove duplicates from the list */
smartlist_sort_strings(ri->declared_family);
@@@ -1531,6 -1535,8 +1536,6 @@@
strlen(ri->cache_info.signed_descriptor_body),
ri->cache_info.signed_descriptor_digest);
- routerinfo_set_country(ri);
-
if (ei) {
tor_assert(! routerinfo_incompatible_with_extrainfo(ri, ei, NULL, NULL));
}
@@@ -1865,9 -1871,7 +1870,7 @@@ router_dump_router_to_string(char *s, s
}
/* Write the exit policy to the end of 's'. */
- if (dns_seems_to_be_broken() || has_dns_init_failed() ||
- !router->exit_policy || !smartlist_len(router->exit_policy)) {
- /* DNS is screwed up; don't claim to be an exit. */
+ if (!router->exit_policy || !smartlist_len(router->exit_policy)) {
strlcat(s+written, "reject *:*\n", maxlen-written);
written += strlen("reject *:*\n");
tmpe = NULL;
@@@ -2023,12 -2027,6 +2026,12 @@@ extrainfo_dump_to_string(char **s_out,
tor_free(bandwidth_usage);
smartlist_add(chunks, pre);
+ if (geoip_is_loaded()) {
+ char *chunk=NULL;
+ tor_asprintf(&chunk, "geoip-db-digest %s\n", geoip_db_digest());
+ smartlist_add(chunks, chunk);
+ }
+
if (options->ExtraInfoStatistics && write_stats_to_extrainfo) {
log_info(LD_GENERAL, "Adding stats to extra-info descriptor.");
if (options->DirReqStatistics &&
@@@ -2051,11 -2049,6 +2054,11 @@@
"exit-stats-end", now, &contents) > 0) {
smartlist_add(chunks, contents);
}
+ if (options->ConnDirectionStatistics &&
+ load_stats_file("stats"PATH_SEPARATOR"conn-stats",
+ "conn-bi-direct", now, &contents) > 0) {
+ smartlist_add(chunks, contents);
+ }
}
if (should_record_bridge_info(options) && write_stats_to_extrainfo) {
@@@ -2194,15 -2187,10 +2197,15 @@@ is_legal_hexdigest(const char *s
void
router_get_verbose_nickname(char *buf, const routerinfo_t *router)
{
+ const char *good_digest = networkstatus_get_router_digest_by_nickname(
+ router->nickname);
+ int is_named = good_digest && !memcmp(good_digest,
+ router->cache_info.identity_digest,
+ DIGEST_LEN);
buf[0] = '$';
base16_encode(buf+1, HEX_DIGEST_LEN+1, router->cache_info.identity_digest,
DIGEST_LEN);
- buf[1+HEX_DIGEST_LEN] = router->is_named ? '=' : '~';
+ buf[1+HEX_DIGEST_LEN] = is_named ? '=' : '~';
strlcpy(buf+1+HEX_DIGEST_LEN+1, router->nickname, MAX_NICKNAME_LEN+1);
}
1
0

[tor/master] Don't let bad DNS make exit policy and declared exit policy get out of sync
by nickm@torproject.org 22 Feb '11
by nickm@torproject.org 22 Feb '11
22 Feb '11
commit cdc59c198a15195a113d68b2c4fbb270792da533
Author: Nick Mathewson <nickm(a)torproject.org>
Date: Tue Feb 22 14:06:28 2011 -0500
Don't let bad DNS make exit policy and declared exit policy get out of sync
Patch from "postman" on trac. Fixes bg 2366. Bug on 0.1.2.5-alpha.
---
changes/bug2366 | 8 ++++++++
src/or/policies.c | 8 ++++++++
src/or/policies.h | 1 +
src/or/router.c | 15 +++++++++------
4 files changed, 26 insertions(+), 6 deletions(-)
diff --git a/changes/bug2366 b/changes/bug2366
new file mode 100644
index 0000000..d171be4
--- /dev/null
+++ b/changes/bug2366
@@ -0,0 +1,8 @@
+ o Minor bugfixes
+ - When a relay decides that its DNS is too broken for it to serve
+ as an exit server, it advertised itself as a non-exit, but
+ continued to act as an exit. This could create accidental
+ partitioning opportunities for users. Instead, if a relay is
+ going to advertise reject *:* as its exit policy, it should
+ really act with exit policy "reject *:*". Fixes bug 2366.
+ Bugfix on Tor 0.1.2.5-alpha. Bugfix by user "postman" on trac.
diff --git a/src/or/policies.c b/src/or/policies.c
index 62e048c..38c2f7c 100644
--- a/src/or/policies.c
+++ b/src/or/policies.c
@@ -858,6 +858,14 @@ policies_parse_exit_policy(config_line_t *cfg, smartlist_t **dest,
return 0;
}
+/** Add "reject *:*" to the end of the policy in *<b>dest</b>, allocating
+ * *<b>dest</b> as needed. */
+void
+policies_exit_policy_append_reject_star(smartlist_t **dest)
+{
+ append_exit_policy_string(dest, "reject *:*");
+}
+
/** Replace the exit policy of <b>r</b> with reject *:*. */
void
policies_set_router_exitpolicy_to_reject_all(routerinfo_t *r)
diff --git a/src/or/policies.h b/src/or/policies.h
index a954ac4..b2947c6 100644
--- a/src/or/policies.h
+++ b/src/or/policies.h
@@ -41,6 +41,7 @@ addr_policy_result_t compare_addr_to_addr_policy(uint32_t addr,
int policies_parse_exit_policy(config_line_t *cfg, smartlist_t **dest,
int rejectprivate, const char *local_address,
int add_default_policy);
+void policies_exit_policy_append_reject_star(smartlist_t **dest);
void policies_set_router_exitpolicy_to_reject_all(routerinfo_t *exitrouter);
int exit_policy_is_general_exit(smartlist_t *policy);
int policy_is_reject_star(const smartlist_t *policy);
diff --git a/src/or/router.c b/src/or/router.c
index 59276ba..4c5eb7a 100644
--- a/src/or/router.c
+++ b/src/or/router.c
@@ -1410,9 +1410,14 @@ router_rebuild_descriptor(int force)
ri->bandwidthcapacity = hibernating ? 0 : rep_hist_bandwidth_assess();
- policies_parse_exit_policy(options->ExitPolicy, &ri->exit_policy,
- options->ExitPolicyRejectPrivate,
- ri->address, !options->BridgeRelay);
+ if (dns_seems_to_be_broken() || has_dns_init_failed()) {
+ /* DNS is screwed up; don't claim to be an exit. */
+ policies_exit_policy_append_reject_star(&ri->exit_policy);
+ } else {
+ policies_parse_exit_policy(options->ExitPolicy, &ri->exit_policy,
+ options->ExitPolicyRejectPrivate,
+ ri->address, !options->BridgeRelay);
+ }
ri->policy_is_reject_star =
policy_is_reject_star(ri->exit_policy);
@@ -1866,9 +1871,7 @@ router_dump_router_to_string(char *s, size_t maxlen, routerinfo_t *router,
}
/* Write the exit policy to the end of 's'. */
- if (dns_seems_to_be_broken() || has_dns_init_failed() ||
- !router->exit_policy || !smartlist_len(router->exit_policy)) {
- /* DNS is screwed up; don't claim to be an exit. */
+ if (!router->exit_policy || !smartlist_len(router->exit_policy)) {
strlcat(s+written, "reject *:*\n", maxlen-written);
written += strlen("reject *:*\n");
tmpe = NULL;
1
0

[tor/maint-0.2.2] Don't let bad DNS make exit policy and declared exit policy get out of sync
by nickm@torproject.org 22 Feb '11
by nickm@torproject.org 22 Feb '11
22 Feb '11
commit cdc59c198a15195a113d68b2c4fbb270792da533
Author: Nick Mathewson <nickm(a)torproject.org>
Date: Tue Feb 22 14:06:28 2011 -0500
Don't let bad DNS make exit policy and declared exit policy get out of sync
Patch from "postman" on trac. Fixes bg 2366. Bug on 0.1.2.5-alpha.
---
changes/bug2366 | 8 ++++++++
src/or/policies.c | 8 ++++++++
src/or/policies.h | 1 +
src/or/router.c | 15 +++++++++------
4 files changed, 26 insertions(+), 6 deletions(-)
diff --git a/changes/bug2366 b/changes/bug2366
new file mode 100644
index 0000000..d171be4
--- /dev/null
+++ b/changes/bug2366
@@ -0,0 +1,8 @@
+ o Minor bugfixes
+ - When a relay decides that its DNS is too broken for it to serve
+ as an exit server, it advertised itself as a non-exit, but
+ continued to act as an exit. This could create accidental
+ partitioning opportunities for users. Instead, if a relay is
+ going to advertise reject *:* as its exit policy, it should
+ really act with exit policy "reject *:*". Fixes bug 2366.
+ Bugfix on Tor 0.1.2.5-alpha. Bugfix by user "postman" on trac.
diff --git a/src/or/policies.c b/src/or/policies.c
index 62e048c..38c2f7c 100644
--- a/src/or/policies.c
+++ b/src/or/policies.c
@@ -858,6 +858,14 @@ policies_parse_exit_policy(config_line_t *cfg, smartlist_t **dest,
return 0;
}
+/** Add "reject *:*" to the end of the policy in *<b>dest</b>, allocating
+ * *<b>dest</b> as needed. */
+void
+policies_exit_policy_append_reject_star(smartlist_t **dest)
+{
+ append_exit_policy_string(dest, "reject *:*");
+}
+
/** Replace the exit policy of <b>r</b> with reject *:*. */
void
policies_set_router_exitpolicy_to_reject_all(routerinfo_t *r)
diff --git a/src/or/policies.h b/src/or/policies.h
index a954ac4..b2947c6 100644
--- a/src/or/policies.h
+++ b/src/or/policies.h
@@ -41,6 +41,7 @@ addr_policy_result_t compare_addr_to_addr_policy(uint32_t addr,
int policies_parse_exit_policy(config_line_t *cfg, smartlist_t **dest,
int rejectprivate, const char *local_address,
int add_default_policy);
+void policies_exit_policy_append_reject_star(smartlist_t **dest);
void policies_set_router_exitpolicy_to_reject_all(routerinfo_t *exitrouter);
int exit_policy_is_general_exit(smartlist_t *policy);
int policy_is_reject_star(const smartlist_t *policy);
diff --git a/src/or/router.c b/src/or/router.c
index 59276ba..4c5eb7a 100644
--- a/src/or/router.c
+++ b/src/or/router.c
@@ -1410,9 +1410,14 @@ router_rebuild_descriptor(int force)
ri->bandwidthcapacity = hibernating ? 0 : rep_hist_bandwidth_assess();
- policies_parse_exit_policy(options->ExitPolicy, &ri->exit_policy,
- options->ExitPolicyRejectPrivate,
- ri->address, !options->BridgeRelay);
+ if (dns_seems_to_be_broken() || has_dns_init_failed()) {
+ /* DNS is screwed up; don't claim to be an exit. */
+ policies_exit_policy_append_reject_star(&ri->exit_policy);
+ } else {
+ policies_parse_exit_policy(options->ExitPolicy, &ri->exit_policy,
+ options->ExitPolicyRejectPrivate,
+ ri->address, !options->BridgeRelay);
+ }
ri->policy_is_reject_star =
policy_is_reject_star(ri->exit_policy);
@@ -1866,9 +1871,7 @@ router_dump_router_to_string(char *s, size_t maxlen, routerinfo_t *router,
}
/* Write the exit policy to the end of 's'. */
- if (dns_seems_to_be_broken() || has_dns_init_failed() ||
- !router->exit_policy || !smartlist_len(router->exit_policy)) {
- /* DNS is screwed up; don't claim to be an exit. */
+ if (!router->exit_policy || !smartlist_len(router->exit_policy)) {
strlcat(s+written, "reject *:*\n", maxlen-written);
written += strlen("reject *:*\n");
tmpe = NULL;
1
0

22 Feb '11
commit 9d5873cdaedf5bbae50bec08bb0719a1a5be403d
Merge: 613073e ce149c1
Author: Nick Mathewson <nickm(a)torproject.org>
Date: Tue Feb 22 13:01:02 2011 -0500
Merge branch 'log_domains' into maint-0.2.2
changes/log_domains | 12 +++++++
doc/tor.1.txt | 28 +++++++++++++++
src/common/log.c | 92 ++++++++++++++++++++++++++++++++++++++++++--------
src/common/torlog.h | 1 +
src/or/config.c | 7 +++-
src/or/or.h | 3 ++
6 files changed, 127 insertions(+), 16 deletions(-)
diff --combined doc/tor.1.txt
index e5dae8c,a4ab0d9..033f0a2
--- a/doc/tor.1.txt
+++ b/doc/tor.1.txt
@@@ -323,6 -323,34 +323,34 @@@ Other options can be specified either o
Messages are sent to all the logs that match their severity
level.
+ **Log** **[**__domain__,...**]**__minSeverity__[-__maxSeverity__] ... **file** __FILENAME__ +
+
+ **Log** **[**__domain__,...**]**__minSeverity__[-__maxSeverity__] ... **stderr**|**stdout**|**syslog** ::
+ As above, but select messages by range of log severity __and__ by a
+ set of "logging domains". Each logging domain corresponds to an area of
+ functionality inside Tor. You can specify any number of severity ranges
+ for a single log statement, each of them prefixed by a comma-separated
+ list of logging domains. You can prefix a domain with ~ to indicate
+ negation, and use * to indicate "all domains". If you specify a severity
+ range without a list of domains, it matches all domains. +
+ +
+ This is an advanced feature which is most useful for debugging one or two
+ of Tor's subsystems at a time. +
+ +
+ The currently recognized domains are: general, crypto, net, config, fs,
+ protocol, mm, http, app, control, circ, rend, bug, dir, dirserv, or, edge,
+ acct, hist, and handshake. Domain names are case-insensitive. +
+ +
+ For example, "`Log [handshake]debug [~net,~mm]info notice stdout`" sends
+ to stdout: all handshake messages of any severity, all info-and-higher
+ messages from domains other than networking and memory management, and all
+ messages of severity notice or higher.
+
+ **LogMessageDomains** **0**|**1**::
+ If 1, Tor includes message domains with each log message. Every log
+ message currently has at least one domain; most currently have exactly
+ one. This doesn't affect controller log messages. (Default: 0)
+
**OutboundBindAddress** __IP__::
Make all outbound connections originate from the IP address specified. This
is only useful when you have multiple network interfaces, and you want all
@@@ -471,7 -499,7 +499,7 @@@ The following options are useful only f
list.
**EntryNodes** __node__,__node__,__...__::
- A list of identity fingerprints, nicknames, country codes and address
+ A list of identity fingerprints, nicknames and address
patterns of nodes to use for the first hop in normal circuits. These are
treated only as preferences unless StrictNodes (see below) is also set.
@@@ -654,9 -682,8 +682,9 @@@
can leak your location to attackers. (Default: 1)
**VirtualAddrNetwork** __Address__/__bits__::
- When a controller asks for a virtual (unused) address with the MAPADDRESS
- command, Tor picks an unassigned address from this range. (Default:
+ When Tor needs to assign a virtual (unused) address because of a MAPADDRESS
+ command from the controller or the AutomapHostsOnResolve feature, Tor
+ picks an unassigned address from this range. (Default:
127.192.0.0/10) +
+
When providing proxy server service to a network of computers using a tool
@@@ -732,12 -759,6 +760,12 @@@
192.168.0.1). This option prevents certain browser-based attacks; don't
turn it off unless you know what you're doing. (Default: 1).
+**ClientRejectInternalAddresses** **0**|**1**::
+ If true, Tor does not try to fulfill requests to connect to an internal
+ address (like 127.0.0.1 or 192.168.0.1) __unless a exit node is
+ specifically requested__ (for example, via a .exit hostname, or a
+ controller request). (Default: 1).
+
**DownloadExtraInfo** **0**|**1**::
If true, Tor downloads and caches "extra-info" documents. These documents
contain information about servers other than the information in their
@@@ -882,9 -903,9 +910,9 @@@ is non-zero)
specified in ORPort. (Default: 0.0.0.0) This directive can be specified
multiple times to bind to multiple addresses/ports.
-**PublishServerDescriptor** **0**|**1**|**v1**|**v2**|**v3**|**bridge**|**hidserv**,**...**::
+**PublishServerDescriptor** **0**|**1**|**v1**|**v2**|**v3**|**bridge**,**...**::
This option specifies which descriptors Tor will publish when acting as
- a relay or hidden service. You can
+ a relay. You can
choose multiple arguments, separated by commas.
+
If this option is set to 0, Tor will not publish its
@@@ -892,7 -913,7 +920,7 @@@
out your server, or if you're using a Tor controller that handles directory
publishing for you.) Otherwise, Tor will publish its descriptors of all
type(s) specified. The default is "1",
- which means "if running as a server or a hidden service, publish the
+ which means "if running as a server, publish the
appropriate descriptors to the authorities".
**ShutdownWaitLength** __NUM__::
@@@ -907,9 -928,7 +935,9 @@@
period, or receive more than that number in the period. For example, with
AccountingMax set to 1 GB, a server could send 900 MB and receive 800 MB
and continue running. It will only hibernate once one of the two reaches 1
- GB. When the number of bytes is exhausted, Tor will hibernate until some
+ GB. When the number of bytes gets low, Tor will stop accepting new
+ connections and circuits. When the number of bytes
+ is exhausted, Tor will hibernate until some
time in the next accounting period. To prevent all servers from waking at
the same time, Tor will also wait until a random point in each period
before waking up. If you have bandwidth cost issues, enabling hibernation
@@@ -1069,8 -1088,7 +1097,8 @@@ if DirPort is non-zero)
**HSAuthoritativeDir** **0**|**1**::
When this option is set in addition to **AuthoritativeDirectory**, Tor also
- accepts and serves hidden service descriptors. (Default: 0)
+ accepts and serves v0 hidden service descriptors,
+ which are produced and used by Tor 0.2.1.x and older. (Default: 0)
**HidServDirectoryV2** **0**|**1**::
When this option is set, Tor accepts and serves v2 hidden service
@@@ -1277,7 -1295,6 +1305,7 @@@ The following options are used for runn
AuthDirMaxServersPerAddr 0
AuthDirMaxServersPerAuthAddr 0
ClientDNSRejectInternalAddresses 0
+ ClientRejectInternalAddresses 0
ExitPolicyRejectPrivate 0
V3AuthVotingInterval 5 minutes
V3AuthVoteDelay 20 seconds
diff --combined src/or/config.c
index ec86dbc,5600ac5..178ed1e
--- a/src/or/config.c
+++ b/src/or/config.c
@@@ -195,7 -195,6 +195,7 @@@ static config_var_t _option_vars[] =
V(CircuitStreamTimeout, INTERVAL, "0"),
V(CircuitPriorityHalflife, DOUBLE, "-100.0"), /*negative:'Use default'*/
V(ClientDNSRejectInternalAddresses, BOOL,"1"),
+ V(ClientRejectInternalAddresses, BOOL, "1"),
V(ClientOnly, BOOL, "0"),
V(ConsensusParams, STRING, NULL),
V(ConnLimit, UINT, "1000"),
@@@ -288,6 -287,7 +288,7 @@@
OBSOLETE("IgnoreVersion"),
V(KeepalivePeriod, INTERVAL, "5 minutes"),
VAR("Log", LINELIST, Logs, NULL),
+ V(LogMessageDomains, BOOL, "0"),
OBSOLETE("LinkPadding"),
OBSOLETE("LogLevel"),
OBSOLETE("LogFile"),
@@@ -406,7 -406,6 +407,7 @@@ static config_var_t testing_tor_network
V(AuthDirMaxServersPerAddr, UINT, "0"),
V(AuthDirMaxServersPerAuthAddr,UINT, "0"),
V(ClientDNSRejectInternalAddresses, BOOL,"0"),
+ V(ClientRejectInternalAddresses, BOOL, "0"),
V(ExitPolicyRejectPrivate, BOOL, "0"),
V(V3AuthVotingInterval, INTERVAL, "5 minutes"),
V(V3AuthVoteDelay, INTERVAL, "20 seconds"),
@@@ -2841,9 -2840,7 +2842,9 @@@ compute_publishserverdescriptor(or_opti
else if (!strcasecmp(string, "bridge"))
*auth |= BRIDGE_AUTHORITY;
else if (!strcasecmp(string, "hidserv"))
- *auth |= HIDSERV_AUTHORITY;
+ log_warn(LD_CONFIG,
+ "PublishServerDescriptor hidserv is invalid. See "
+ "PublishHidServDescriptors.");
else if (!strcasecmp(string, "") || !strcmp(string, "0"))
/* no authority */;
else
@@@ -3347,11 -3344,6 +3348,11 @@@ options_validate(or_options_t *old_opti
"PerConnBWBurst", msg) < 0)
return -1;
+ if (options->RelayBandwidthRate && !options->RelayBandwidthBurst)
+ options->RelayBandwidthBurst = options->RelayBandwidthRate;
+ if (options->RelayBandwidthBurst && !options->RelayBandwidthRate)
+ options->RelayBandwidthRate = options->RelayBandwidthBurst;
+
if (server_mode(options)) {
if (options->BandwidthRate < ROUTER_REQUIRED_MIN_BANDWIDTH) {
tor_asprintf(msg,
@@@ -3380,6 -3372,9 +3381,6 @@@
}
}
- if (options->RelayBandwidthRate && !options->RelayBandwidthBurst)
- options->RelayBandwidthBurst = options->RelayBandwidthRate;
-
if (options->RelayBandwidthRate > options->RelayBandwidthBurst)
REJECT("RelayBandwidthBurst must be at least equal "
"to RelayBandwidthRate.");
@@@ -3817,7 -3812,8 +3818,8 @@@ options_transition_affects_workers(or_o
old_options->SafeLogging != new_options->SafeLogging ||
old_options->ClientOnly != new_options->ClientOnly ||
public_server_mode(old_options) != public_server_mode(new_options) ||
- !config_lines_eq(old_options->Logs, new_options->Logs))
+ !config_lines_eq(old_options->Logs, new_options->Logs) ||
+ old_options->LogMessageDomains != new_options->LogMessageDomains)
return 1;
/* Check whether log options match. */
@@@ -4393,6 -4389,9 +4395,9 @@@ options_init_logs(or_options_t *options
}
smartlist_free(elts);
+ if (ok && !validate_only)
+ logs_set_domain_logging(options->LogMessageDomains);
+
return ok?0:-1;
}
diff --combined src/or/or.h
index 752de21,7bccf83..2a55668
--- a/src/or/or.h
+++ b/src/or/or.h
@@@ -583,9 -583,6 +583,9 @@@ typedef enum
/** This is a connection on the NATD port, and the destination IP:Port was
* either ill-formed or out-of-range. */
#define END_STREAM_REASON_INVALID_NATD_DEST 261
+/** The target address is in a private network (like 127.0.0.1 or 10.0.0.1);
+ * you don't want to do that over a randomly chosen exit */
+#define END_STREAM_REASON_PRIVATE_ADDR 262
/** Bitwise-and this value with endreason to mask out all flags. */
#define END_STREAM_REASON_MASK 511
@@@ -1173,10 -1170,6 +1173,10 @@@ typedef struct edge_connection_t
* zero, abandon the associated mapaddress. */
unsigned int chosen_exit_retries:3;
+ /** True iff this is an AP connection that came from a transparent or
+ * NATd connection */
+ unsigned int is_transparent_ap:1;
+
/** If this is a DNSPort connection, this field holds the pending DNS
* request that we're going to try to answer. */
struct evdns_server_request *dns_server_request;
@@@ -2345,6 -2338,9 +2345,9 @@@ typedef struct
config_line_t *Logs; /**< New-style list of configuration lines
* for logs */
+ int LogMessageDomains; /**< Boolean: Should we log the domain(s) in which
+ * each log message occurs? */
+
char *DebugLogFile; /**< Where to send verbose log messages. */
char *DataDirectory; /**< OR only: where to store long-term data. */
char *Nickname; /**< OR only: nickname of this onion router. */
@@@ -2756,10 -2752,6 +2759,10 @@@
* Helps avoid some cross-site attacks. */
int ClientDNSRejectInternalAddresses;
+ /** If true, do not accept any requests to connect to internal addresses
+ * over randomly chosen exits. */
+ int ClientRejectInternalAddresses;
+
/** The length of time that we think a consensus should be fresh. */
int V3AuthVotingInterval;
/** The length of time we think it will take to distribute votes. */
1
0
commit 46b07462ae636eae1e241d5596b3a1d80c82d7ef
Merge: 933ffd5 9d5873c
Author: Nick Mathewson <nickm(a)torproject.org>
Date: Tue Feb 22 13:02:42 2011 -0500
Merge remote branch 'origin/maint-0.2.2'
changes/log_domains | 12 +++++++
doc/tor.1.txt | 28 +++++++++++++++
src/common/log.c | 92 ++++++++++++++++++++++++++++++++++++++++++--------
src/common/torlog.h | 1 +
src/or/config.c | 7 +++-
src/or/or.h | 3 ++
6 files changed, 127 insertions(+), 16 deletions(-)
diff --combined doc/tor.1.txt
index 7ba5302,033f0a2..19454a7
--- a/doc/tor.1.txt
+++ b/doc/tor.1.txt
@@@ -323,6 -323,34 +323,34 @@@ Other options can be specified either o
Messages are sent to all the logs that match their severity
level.
+ **Log** **[**__domain__,...**]**__minSeverity__[-__maxSeverity__] ... **file** __FILENAME__ +
+
+ **Log** **[**__domain__,...**]**__minSeverity__[-__maxSeverity__] ... **stderr**|**stdout**|**syslog** ::
+ As above, but select messages by range of log severity __and__ by a
+ set of "logging domains". Each logging domain corresponds to an area of
+ functionality inside Tor. You can specify any number of severity ranges
+ for a single log statement, each of them prefixed by a comma-separated
+ list of logging domains. You can prefix a domain with ~ to indicate
+ negation, and use * to indicate "all domains". If you specify a severity
+ range without a list of domains, it matches all domains. +
+ +
+ This is an advanced feature which is most useful for debugging one or two
+ of Tor's subsystems at a time. +
+ +
+ The currently recognized domains are: general, crypto, net, config, fs,
+ protocol, mm, http, app, control, circ, rend, bug, dir, dirserv, or, edge,
+ acct, hist, and handshake. Domain names are case-insensitive. +
+ +
+ For example, "`Log [handshake]debug [~net,~mm]info notice stdout`" sends
+ to stdout: all handshake messages of any severity, all info-and-higher
+ messages from domains other than networking and memory management, and all
+ messages of severity notice or higher.
+
+ **LogMessageDomains** **0**|**1**::
+ If 1, Tor includes message domains with each log message. Every log
+ message currently has at least one domain; most currently have exactly
+ one. This doesn't affect controller log messages. (Default: 0)
+
**OutboundBindAddress** __IP__::
Make all outbound connections originate from the IP address specified. This
is only useful when you have multiple network interfaces, and you want all
@@@ -343,13 -371,6 +371,13 @@@
on Windows; instead you should use the --service command-line option.
(Default: 0)
+**LogTimeGranularity** __NUM__::
+ Set the resolution of timestamps in Tor's logs to NUM milliseconds.
+ NUM must be positive and either a divisor or a multiple of 1 second.
+ Note that this option only controls the granularity written by Tor to
+ a file or console log. Tor does not (for example) "batch up" log
+ messages to affect times logged by a controller, times attached to
+ syslog messages, or the mtime fields on log files. (Default: 1 second)
**SafeLogging** **0**|**1**|**relay**::
Tor can scrub potentially sensitive strings from log messages (e.g.
@@@ -404,11 -425,6 +432,11 @@@
networkstatus. This is an advanced option; you generally shouldn't have
to mess with it. (Default: not set.)
+**DisableIOCP** **0**|**1**::
+ If Tor was built to use the Libevent's "bufferevents" networking code
+ and you're running on Windows, setting this option to 1 will tell Libevent
+ not to use the Windows IOCP networking API. (Default: 1)
+
CLIENT OPTIONS
--------------
@@@ -483,7 -499,7 +511,7 @@@ The following options are useful only f
list.
**EntryNodes** __node__,__node__,__...__::
- A list of identity fingerprints, nicknames and address
+ A list of identity fingerprints, nicknames, country codes and address
patterns of nodes to use for the first hop in normal circuits. These are
treated only as preferences unless StrictNodes (see below) is also set.
@@@ -580,8 -596,7 +608,8 @@@
constitute a "family" of similar or co-administered servers, so never use
any two of them in the same circuit. Defining a NodeFamily is only needed
when a server doesn't list the family itself (with MyFamily). This option
- can be used multiple times.
+ can be used multiple times. In addition to nodes, you can also list
+ IP address and ranges and country codes in {curly braces}.
**EnforceDistinctSubnets** **0**|**1**::
If 1, Tor will not put two servers whose IP addresses are "too close" on
@@@ -884,9 -899,7 +912,9 @@@ is non-zero)
characters inclusive, and must contain only the characters [a-zA-Z0-9].
**NumCPUs** __num__::
- How many processes to use at once for decrypting onionskins. (Default: 1)
+ How many processes to use at once for decrypting onionskins and other
+ parallelizable operations. If this is set to 0, Tor will try to detect
+ how many CPUs you have, defaulting to 1 if it can't tell. (Default: 0)
**ORPort** __PORT__::
Advertise this port to listen for connections from Tor clients and servers.
@@@ -897,18 -910,6 +925,18 @@@
specified in ORPort. (Default: 0.0.0.0) This directive can be specified
multiple times to bind to multiple addresses/ports.
+**PortForwarding** **0**|**1**::
+ Attempt to automatically forward the DirPort and ORPort on a NAT router
+ connecting this Tor server to the Internet. If set, Tor will try both
+ NAT-PMP (common on Apple routers) and UPnP (common on routers from other
+ manufacturers). (Default: 0)
+
+**PortForwardingHelper** __filename__|__pathname__::
+ If PortForwarding is set, use this executable to configure the forwarding.
+ If set to a filename, the system path will be searched for the executable.
+ If set to a path, only the specified path will be executed.
+ (Default: tor-fw-helper)
+
**PublishServerDescriptor** **0**|**1**|**v1**|**v2**|**v3**|**bridge**,**...**::
This option specifies which descriptors Tor will publish when acting as
a relay. You can
@@@ -928,11 -929,6 +956,11 @@@
seconds, we exit. If we get a second SIGINT, we exit immedi-
ately. (Default: 30 seconds)
+**HeartbeatPeriod** __N__ **minutes**|**hours**|**days**|**weeks**::
+ Log a heartbeat message every **HeartbeatPeriod** seconds. This is
+ a log level __info__ message, designed to let you know your Tor
+ server is still alive and doing useful things. Settings this
+ to 0 will disable the heartbeat. (Default: 6 hours)
**AccountingMax** __N__ **bytes**|**KB**|**MB**|**GB**|**TB**::
Never send more than the specified number of bytes in a given accounting
@@@ -1041,10 -1037,6 +1069,10 @@@
When this option is enabled, Tor writes statistics on the number of relayed
bytes and opened stream per exit port to disk every 24 hours. (Default: 0)
+**ConnDirectionStatistics** **0**|**1**::
+ When this option is enabled, Tor writes statistics on the bidirectional use
+ of connections to disk every 24 hours. (Default: 0)
+
**ExtraInfoStatistics** **0**|**1**::
When this option is enabled, Tor includes previously gathered statistics in
its extra-info documents that it uploads to the directory authorities.
diff --combined src/common/log.c
index ba84807,cfa0721..507f162
--- a/src/common/log.c
+++ b/src/common/log.c
@@@ -97,6 -97,9 +97,9 @@@ static int log_mutex_initialized = 0
/** Linked list of logfile_t. */
static logfile_t *logfiles = NULL;
+ /** Boolean: do we report logging domains? */
+ static int log_domains_are_logged = 0;
+
#ifdef HAVE_SYSLOG_H
/** The number of open syslog log handlers that we have. When this reaches 0,
* we can close our connection to the syslog facility. */
@@@ -126,6 -129,9 +129,9 @@@ int _log_global_min_severity = LOG_NOTI
static void delete_log(logfile_t *victim);
static void close_log(logfile_t *victim);
+ static char *domain_to_string(log_domain_mask_t domain,
+ char *buf, size_t buflen);
+
/** Name of the application: used to generate the message we write at the
* start of each new log. */
static char *appname = NULL;
@@@ -142,17 -148,6 +148,17 @@@ log_set_application_name(const char *na
appname = name ? tor_strdup(name) : NULL;
}
+/** Log time granularity in milliseconds. */
+static int log_time_granularity = 1;
+
+/** Define log time granularity for all logs to be <b>granularity_msec</b>
+ * milliseconds. */
+void
+set_log_time_granularity(int granularity_msec)
+{
+ log_time_granularity = granularity_msec;
+}
+
/** Helper: Write the standard prefix for log lines to a
* <b>buf_len</b> character buffer in <b>buf</b>.
*/
@@@ -163,22 -158,14 +169,22 @@@ _log_prefix(char *buf, size_t buf_len,
struct timeval now;
struct tm tm;
size_t n;
- int r;
+ int r, ms;
tor_gettimeofday(&now);
t = (time_t)now.tv_sec;
+ ms = (int)now.tv_usec / 1000;
+ if (log_time_granularity >= 1000) {
+ t -= t % (log_time_granularity / 1000);
+ ms = 0;
+ } else {
+ ms -= ((int)now.tv_usec / 1000) % log_time_granularity;
+ }
n = strftime(buf, buf_len, "%b %d %H:%M:%S", tor_localtime_r(&t, &tm));
- r = tor_snprintf(buf+n, buf_len-n, ".%.3i [%s] ",
- (int)now.tv_usec / 1000, sev_to_string(severity));
+ r = tor_snprintf(buf+n, buf_len-n, ".%.3i [%s] ", ms,
+ sev_to_string(severity));
+
if (r<0)
return buf_len-1;
else
@@@ -236,13 -223,34 +242,34 @@@ format_msg(char *buf, size_t buf_len
size_t n;
int r;
char *end_of_prefix;
+ char *buf_end;
- assert(buf_len >= 2); /* prevent integer underflow */
+ assert(buf_len >= 16); /* prevent integer underflow and general stupidity */
buf_len -= 2; /* subtract 2 characters so we have room for \n\0 */
+ buf_end = buf+buf_len; /* point *after* the last char we can write to */
n = _log_prefix(buf, buf_len, severity);
end_of_prefix = buf+n;
+ if (log_domains_are_logged) {
+ char *cp = buf+n;
+ if (cp == buf_end) goto format_msg_no_room_for_domains;
+ *cp++ = '{';
+ if (cp == buf_end) goto format_msg_no_room_for_domains;
+ cp = domain_to_string(domain, cp, (buf+buf_len-cp));
+ if (cp == buf_end) goto format_msg_no_room_for_domains;
+ *cp++ = '}';
+ if (cp == buf_end) goto format_msg_no_room_for_domains;
+ *cp++ = ' ';
+ if (cp == buf_end) goto format_msg_no_room_for_domains;
+ end_of_prefix = cp;
+ n = cp-buf;
+ format_msg_no_room_for_domains:
+ /* This will leave end_of_prefix and n unchanged, and thus cause
+ * whatever log domain string we had written to be clobbered. */
+ ;
+ }
+
if (funcname && should_log_function_name(domain, severity)) {
r = tor_snprintf(buf+n, buf_len-n, "%s(): ", funcname);
if (r<0)
@@@ -324,6 -332,7 +351,7 @@@ logv(int severity, log_domain_mask_t do
&msg_len);
formatted = 1;
}
+
if (lf->is_syslog) {
#ifdef HAVE_SYSLOG_H
char *m = end_of_prefix;
@@@ -582,8 -591,7 +610,7 @@@ add_stream_log_impl(const log_severity_
* to <b>fd</b>. Steals a reference to <b>severity</b>; the caller must
* not use it after calling this function. */
void
- add_stream_log(const log_severity_list_t *severity,
- const char *name, int fd)
+ add_stream_log(const log_severity_list_t *severity, const char *name, int fd)
{
LOCK_LOGS();
add_stream_log_impl(severity, name, fd);
@@@ -602,6 -610,16 +629,16 @@@ init_logging(void
pending_cb_messages = smartlist_create();
}
+ /** Set whether we report logging domains as a part of our log messages.
+ */
+ void
+ logs_set_domain_logging(int enabled)
+ {
+ LOCK_LOGS();
+ log_domains_are_logged = enabled;
+ UNLOCK_LOGS();
+ }
+
/** Add a log handler to receive messages during startup (before the real
* logs are initialized).
*/
@@@ -658,7 -676,7 +695,7 @@@ change_callback_log_severity(int loglev
UNLOCK_LOGS();
}
-/** If there are any log messages that were genered with LD_NOCB waiting to
+/** If there are any log messages that were generated with LD_NOCB waiting to
* be sent to callback-based loggers, send them now. */
void
flush_pending_log_callbacks(void)
@@@ -758,7 -776,7 +795,7 @@@ add_file_log(const log_severity_list_t
int fd;
logfile_t *lf;
- fd = open(filename, O_WRONLY|O_CREAT|O_APPEND, 0644);
+ fd = tor_open_cloexec(filename, O_WRONLY|O_CREAT|O_APPEND, 0644);
if (fd<0)
return -1;
if (tor_fd_seekend(fd)<0)
@@@ -794,7 -812,6 +831,6 @@@ add_syslog_log(const log_severity_list_
lf->fd = -1;
lf->severities = tor_memdup(severity, sizeof(log_severity_list_t));
lf->filename = tor_strdup("<syslog>");
-
lf->is_syslog = 1;
LOCK_LOGS();
@@@ -851,18 -868,41 +887,41 @@@ parse_log_domain(const char *domain
}
return 0;
}
- #if 0
- /** Translate a bitmask of log domains to a string, or NULL if the bitmask
- * is undecodable. */
- static const char *
- domain_to_string(log_domain_mask_t domain)
+
+ /** Translate a bitmask of log domains to a string. */
+ static char *
+ domain_to_string(log_domain_mask_t domain, char *buf, size_t buflen)
{
- int bit = tor_log2(domain);
- if ((bit == 0 && domain == 0) || bit >= N_LOGGING_DOMAINS)
- return NULL;
- return domain_list[bit];
+ char *cp = buf;
+ char *eos = buf+buflen;
+
+ buf[0] = '\0';
+ if (! domain)
+ return buf;
+ while (1) {
+ const char *d;
+ int bit = tor_log2(domain);
+ size_t n;
+ if (bit >= N_LOGGING_DOMAINS) {
+ tor_snprintf(buf, buflen, "<BUG:Unknown domain %lx>", (long)domain);
+ return buf+strlen(buf);
+ }
+ d = domain_list[bit];
+ n = strlcpy(cp, d, eos-cp);
+ if (n >= buflen) {
+ tor_snprintf(buf, buflen, "<BUG:Truncating domain %lx>", (long)domain);
+ return buf+strlen(buf);
+ }
+ cp += n;
+ domain &= ~(1<<bit);
+
+ if (domain == 0 || (eos-cp) < 2)
+ return cp;
+
+ memcpy(cp, ",", 2); /*Nul-terminated ,"*/
+ cp++;
+ }
}
- #endif
/** Parse a log severity pattern in *<b>cfg_ptr</b>. Advance cfg_ptr after
* the end of the severityPattern. Set the value of <b>severity_out</b> to
@@@ -938,7 -978,10 +997,10 @@@ parse_log_severity_config(const char **
smartlist_free(domains_list);
if (err)
return -1;
- domains &= ~neg_domains;
+ if (domains == 0 && neg_domains)
+ domains = ~neg_domains;
+ else
+ domains &= ~neg_domains;
cfg = eat_whitespace(closebracket+1);
} else {
++got_an_unqualified_range;
diff --combined src/common/torlog.h
index 4192a88,791e363..add2349
--- a/src/common/torlog.h
+++ b/src/common/torlog.h
@@@ -92,10 -92,8 +92,10 @@@
#define LD_HIST (1u<<18)
/** OR handshaking */
#define LD_HANDSHAKE (1u<<19)
+/** Heartbeat messages */
+#define LD_HEARTBEAT (1u<<20)
/** Number of logging domains in the code. */
-#define N_LOGGING_DOMAINS 20
+#define N_LOGGING_DOMAINS 21
/** This log message is not safe to send to a callback-based logger
* immediately. Used as a flag, not a log domain. */
@@@ -134,6 -132,7 +134,7 @@@ int add_file_log(const log_severity_lis
int add_syslog_log(const log_severity_list_t *severity);
#endif
int add_callback_log(const log_severity_list_t *severity, log_callback cb);
+ void logs_set_domain_logging(int enabled);
int get_min_log_level(void);
void switch_logs_debug(void);
void logs_free_all(void);
@@@ -145,7 -144,6 +146,7 @@@ void change_callback_log_severity(int l
log_callback cb);
void flush_pending_log_callbacks(void);
void log_set_application_name(const char *name);
+void set_log_time_granularity(int granularity_msec);
/* Outputs a message to stdout */
void tor_log(int severity, log_domain_mask_t domain, const char *format, ...)
diff --combined src/or/config.c
index 8bf4842,178ed1e..97a2b32
--- a/src/or/config.c
+++ b/src/or/config.c
@@@ -44,8 -44,6 +44,8 @@@ typedef enum config_type_t
CONFIG_TYPE_FILENAME, /**< A filename: some prefixes get expanded. */
CONFIG_TYPE_UINT, /**< A non-negative integer less than MAX_INT */
CONFIG_TYPE_INTERVAL, /**< A number of seconds, with optional units*/
+ CONFIG_TYPE_MSEC_INTERVAL,/**< A number of milliseconds, with optional
+ * units */
CONFIG_TYPE_MEMUNIT, /**< A number of bytes, with optional units*/
CONFIG_TYPE_DOUBLE, /**< A floating-point value */
CONFIG_TYPE_BOOL, /**< A boolean value, expressed as 0 or 1. */
@@@ -201,7 -199,6 +201,7 @@@ static config_var_t _option_vars[] =
V(ClientOnly, BOOL, "0"),
V(ConsensusParams, STRING, NULL),
V(ConnLimit, UINT, "1000"),
+ V(ConnDirectionStatistics, BOOL, "0"),
V(ConstrainedSockets, BOOL, "0"),
V(ConstrainedSockSize, MEMUNIT, "8192"),
V(ContactInfo, STRING, NULL),
@@@ -225,10 -222,9 +225,10 @@@
OBSOLETE("DirRecordUsageGranularity"),
OBSOLETE("DirRecordUsageRetainIPs"),
OBSOLETE("DirRecordUsageSaveInterval"),
- V(DirReqStatistics, BOOL, "0"),
+ V(DirReqStatistics, BOOL, "1"),
VAR("DirServer", LINELIST, DirServers, NULL),
V(DisableAllSwap, BOOL, "0"),
+ V(DisableIOCP, BOOL, "1"),
V(DNSPort, UINT, "0"),
V(DNSListenAddress, LINELIST, NULL),
V(DownloadExtraInfo, BOOL, "0"),
@@@ -243,7 -239,7 +243,7 @@@
V(ExitPolicy, LINELIST, NULL),
V(ExitPolicyRejectPrivate, BOOL, "1"),
V(ExitPortStatistics, BOOL, "0"),
- V(ExtraInfoStatistics, BOOL, "0"),
+ V(ExtraInfoStatistics, BOOL, "1"),
#if defined (WINCE)
V(FallbackNetworkstatusFile, FILENAME, "fallback-consensus"),
@@@ -267,7 -263,6 +267,7 @@@
#endif
OBSOLETE("Group"),
V(HardwareAccel, BOOL, "0"),
+ V(HeartbeatPeriod, INTERVAL, "6 hours"),
V(AccelName, STRING, NULL),
V(AccelDir, FILENAME, NULL),
V(HashedControlPassword, LINELIST, NULL),
@@@ -293,10 -288,10 +293,11 @@@
OBSOLETE("IgnoreVersion"),
V(KeepalivePeriod, INTERVAL, "5 minutes"),
VAR("Log", LINELIST, Logs, NULL),
+ V(LogMessageDomains, BOOL, "0"),
OBSOLETE("LinkPadding"),
OBSOLETE("LogLevel"),
OBSOLETE("LogFile"),
+ V(LogTimeGranularity, MSEC_INTERVAL, "1 second"),
V(LongLivedPorts, CSV,
"21,22,706,1863,5050,5190,5222,5223,6667,6697,8300"),
VAR("MapAddress", LINELIST, AddressMap, NULL),
@@@ -313,7 -308,7 +314,7 @@@
V(WarnUnsafeSocks, BOOL, "1"),
OBSOLETE("NoPublish"),
VAR("NodeFamily", LINELIST, NodeFamilies, NULL),
- V(NumCPUs, UINT, "1"),
+ V(NumCPUs, UINT, "0"),
V(NumEntryGuards, UINT, "3"),
V(ORListenAddress, LINELIST, NULL),
V(ORPort, UINT, "0"),
@@@ -323,8 -318,6 +324,8 @@@
V(PerConnBWRate, MEMUNIT, "0"),
V(PidFile, STRING, NULL),
V(TestingTorNetwork, BOOL, "0"),
+ V(PortForwarding, BOOL, "0"),
+ V(PortForwardingHelper, FILENAME, "tor-fw-helper"),
V(PreferTunneledDirConns, BOOL, "1"),
V(ProtocolWarnings, BOOL, "0"),
V(PublishServerDescriptor, CSV, "1"),
@@@ -393,7 -386,6 +394,7 @@@
VAR("VersioningAuthoritativeDirectory",BOOL,VersioningAuthoritativeDir, "0"),
V(VirtualAddrNetwork, STRING, "127.192.0.0/10"),
V(WarnPlaintextPorts, CSV, "23,109,110,143"),
+ V(_UseFilteringSSLBufferevents, BOOL, "0"),
VAR("__ReloadTorrcOnSIGHUP", BOOL, ReloadTorrcOnSIGHUP, "1"),
VAR("__AllDirActionsPrivate", BOOL, AllDirActionsPrivate, "0"),
VAR("__DisablePredictedCircuits",BOOL,DisablePredictedCircuits, "0"),
@@@ -566,9 -558,8 +567,9 @@@ static int is_listening_on_low_port(uin
const config_line_t *listen_options);
static uint64_t config_parse_memunit(const char *s, int *ok);
+static int config_parse_msec_interval(const char *s, int *ok);
static int config_parse_interval(const char *s, int *ok);
-static void init_libevent(void);
+static void init_libevent(const or_options_t *options);
static int opt_streq(const char *s1, const char *s2);
/** Magic value for or_options_t. */
@@@ -702,11 -693,6 +703,11 @@@ or_options_free(or_options_t *options
return;
routerset_free(options->_ExcludeExitNodesUnion);
+ if (options->NodeFamilySets) {
+ SMARTLIST_FOREACH(options->NodeFamilySets, routerset_t *,
+ rs, routerset_free(rs));
+ smartlist_free(options->NodeFamilySets);
+ }
config_free(&options_format, options);
}
@@@ -974,7 -960,7 +975,7 @@@ options_act_reversible(or_options_t *ol
/* Set up libevent. (We need to do this before we can register the
* listeners as listeners.) */
if (running_tor && !libevent_initialized) {
- init_libevent();
+ init_libevent(options);
libevent_initialized = 1;
}
@@@ -1250,17 -1236,6 +1251,17 @@@ options_act(or_options_t *old_options
if (accounting_is_enabled(options))
configure_accounting(time(NULL));
+#ifdef USE_BUFFEREVENTS
+ /* If we're using the bufferevents implementation and our rate limits
+ * changed, we need to tell the rate-limiting system about it. */
+ if (!old_options ||
+ old_options->BandwidthRate != options->BandwidthRate ||
+ old_options->BandwidthBurst != options->BandwidthBurst ||
+ old_options->RelayBandwidthRate != options->RelayBandwidthRate ||
+ old_options->RelayBandwidthBurst != options->RelayBandwidthBurst)
+ connection_bucket_init();
+#endif
+
/* parse RefuseUnknownExits tristate */
if (!strcmp(options->RefuseUnknownExits, "0"))
options->RefuseUnknownExits_ = 0;
@@@ -1372,52 -1347,44 +1373,52 @@@
tor_free(actual_fname);
}
- if (options->DirReqStatistics && !geoip_is_loaded()) {
- /* Check if GeoIP database could be loaded. */
- log_warn(LD_CONFIG, "Configured to measure directory request "
- "statistics, but no GeoIP database found!");
- return -1;
- }
-
- if (options->EntryStatistics) {
- if (should_record_bridge_info(options)) {
- /* Don't allow measuring statistics on entry guards when configured
- * as bridge. */
- log_warn(LD_CONFIG, "Bridges cannot be configured to measure "
- "additional GeoIP statistics as entry guards.");
- return -1;
- } else if (!geoip_is_loaded()) {
- /* Check if GeoIP database could be loaded. */
- log_warn(LD_CONFIG, "Configured to measure entry node statistics, "
- "but no GeoIP database found!");
- return -1;
- }
- }
-
if (options->CellStatistics || options->DirReqStatistics ||
- options->EntryStatistics || options->ExitPortStatistics) {
+ options->EntryStatistics || options->ExitPortStatistics ||
+ options->ConnDirectionStatistics) {
time_t now = time(NULL);
+ int print_notice = 0;
if ((!old_options || !old_options->CellStatistics) &&
- options->CellStatistics)
+ options->CellStatistics) {
rep_hist_buffer_stats_init(now);
+ print_notice = 1;
+ }
if ((!old_options || !old_options->DirReqStatistics) &&
- options->DirReqStatistics)
- geoip_dirreq_stats_init(now);
+ options->DirReqStatistics) {
+ if (geoip_is_loaded()) {
+ geoip_dirreq_stats_init(now);
+ print_notice = 1;
+ } else {
+ options->DirReqStatistics = 0;
+ log_notice(LD_CONFIG, "Configured to measure directory request "
+ "statistics, but no GeoIP database found! "
+ "Please specify a GeoIP database using the "
+ "GeoIPFile option!");
+ }
+ }
if ((!old_options || !old_options->EntryStatistics) &&
- options->EntryStatistics)
- geoip_entry_stats_init(now);
+ options->EntryStatistics && !should_record_bridge_info(options)) {
+ if (geoip_is_loaded()) {
+ geoip_entry_stats_init(now);
+ print_notice = 1;
+ } else {
+ options->EntryStatistics = 0;
+ log_notice(LD_CONFIG, "Configured to measure entry node "
+ "statistics, but no GeoIP database found! "
+ "Please specify a GeoIP database using the "
+ "GeoIPFile option!");
+ }
+ }
if ((!old_options || !old_options->ExitPortStatistics) &&
- options->ExitPortStatistics)
+ options->ExitPortStatistics) {
rep_hist_exit_stats_init(now);
- if (!old_options)
+ print_notice = 1;
+ }
+ if ((!old_options || !old_options->ConnDirectionStatistics) &&
+ options->ConnDirectionStatistics) {
+ rep_hist_conn_stats_init(now);
+ }
+ if (print_notice)
log_notice(LD_CONFIG, "Configured to measure statistics. Look for "
"the *-stats files that will first be written to the "
"data directory in 24 hours from now.");
@@@ -1435,9 -1402,6 +1436,9 @@@
if (old_options && old_options->ExitPortStatistics &&
!options->ExitPortStatistics)
rep_hist_exit_stats_term();
+ if (old_options && old_options->ConnDirectionStatistics &&
+ !options->ConnDirectionStatistics)
+ rep_hist_conn_stats_term();
/* Check if we need to parse and add the EntryNodes config option. */
if (options->EntryNodes &&
@@@ -1743,18 -1707,6 +1744,18 @@@ config_assign_value(config_format_t *fm
break;
}
+ case CONFIG_TYPE_MSEC_INTERVAL: {
+ i = config_parse_msec_interval(c->value, &ok);
+ if (!ok) {
+ tor_asprintf(msg,
+ "Msec interval '%s %s' is malformed or out of bounds.",
+ c->key, c->value);
+ return -1;
+ }
+ *(int *)lvalue = i;
+ break;
+ }
+
case CONFIG_TYPE_MEMUNIT: {
uint64_t u64 = config_parse_memunit(c->value, &ok);
if (!ok) {
@@@ -2042,7 -1994,6 +2043,7 @@@ get_assigned_option(config_format_t *fm
escape_val = 0; /* Can't need escape. */
break;
case CONFIG_TYPE_INTERVAL:
+ case CONFIG_TYPE_MSEC_INTERVAL:
case CONFIG_TYPE_UINT:
/* This means every or_options_t uint or bool element
* needs to be an int. Not, say, a uint16_t or char. */
@@@ -2270,7 -2221,6 +2271,7 @@@ option_clear(config_format_t *fmt, or_o
*(time_t*)lvalue = 0;
break;
case CONFIG_TYPE_INTERVAL:
+ case CONFIG_TYPE_MSEC_INTERVAL:
case CONFIG_TYPE_UINT:
case CONFIG_TYPE_BOOL:
*(int*)lvalue = 0;
@@@ -2377,7 -2327,7 +2378,7 @@@ resolve_my_address(int warn_severity, o
int explicit_ip=1;
int explicit_hostname=1;
int from_interface=0;
- char tmpbuf[INET_NTOA_BUF_LEN];
+ char *addr_string = NULL;
const char *address = options->Address;
int notice_severity = warn_severity <= LOG_NOTICE ?
LOG_NOTICE : warn_severity;
@@@ -2419,43 -2369,48 +2420,43 @@@
return -1;
}
from_interface = 1;
- in.s_addr = htonl(interface_ip);
- tor_inet_ntoa(&in,tmpbuf,sizeof(tmpbuf));
+ addr = interface_ip;
log_fn(notice_severity, LD_CONFIG, "Learned IP address '%s' for "
- "local interface. Using that.", tmpbuf);
+ "local interface. Using that.", fmt_addr32(addr));
strlcpy(hostname, "<guessed from interfaces>", sizeof(hostname));
} else { /* resolved hostname into addr */
- in.s_addr = htonl(addr);
-
if (!explicit_hostname &&
- is_internal_IP(ntohl(in.s_addr), 0)) {
+ is_internal_IP(addr, 0)) {
uint32_t interface_ip;
- tor_inet_ntoa(&in,tmpbuf,sizeof(tmpbuf));
log_fn(notice_severity, LD_CONFIG, "Guessed local hostname '%s' "
- "resolves to a private IP address (%s). Trying something "
- "else.", hostname, tmpbuf);
+ "resolves to a private IP address (%s). Trying something "
+ "else.", hostname, fmt_addr32(addr));
if (get_interface_address(warn_severity, &interface_ip)) {
log_fn(warn_severity, LD_CONFIG,
"Could not get local interface IP address. Too bad.");
} else if (is_internal_IP(interface_ip, 0)) {
- struct in_addr in2;
- in2.s_addr = htonl(interface_ip);
- tor_inet_ntoa(&in2,tmpbuf,sizeof(tmpbuf));
log_fn(notice_severity, LD_CONFIG,
"Interface IP address '%s' is a private address too. "
- "Ignoring.", tmpbuf);
+ "Ignoring.", fmt_addr32(interface_ip));
} else {
from_interface = 1;
- in.s_addr = htonl(interface_ip);
- tor_inet_ntoa(&in,tmpbuf,sizeof(tmpbuf));
+ addr = interface_ip;
log_fn(notice_severity, LD_CONFIG,
"Learned IP address '%s' for local interface."
- " Using that.", tmpbuf);
+ " Using that.", fmt_addr32(addr));
strlcpy(hostname, "<guessed from interfaces>", sizeof(hostname));
}
}
}
+ } else {
+ addr = ntohl(in.s_addr); /* set addr so that addr_string is not
+ * illformed */
}
- tor_inet_ntoa(&in,tmpbuf,sizeof(tmpbuf));
- if (is_internal_IP(ntohl(in.s_addr), 0)) {
+ addr_string = tor_dup_ip(addr);
+ if (is_internal_IP(addr, 0)) {
/* make sure we're ok with publishing an internal IP */
if (!options->DirServers && !options->AlternateDirAuthority) {
/* if they are using the default dirservers, disallow internal IPs
@@@ -2463,8 -2418,7 +2464,8 @@@
log_fn(warn_severity, LD_CONFIG,
"Address '%s' resolves to private IP address '%s'. "
"Tor servers that use the default DirServers must have public "
- "IP addresses.", hostname, tmpbuf);
+ "IP addresses.", hostname, addr_string);
+ tor_free(addr_string);
return -1;
}
if (!explicit_ip) {
@@@ -2472,20 -2426,19 +2473,20 @@@
* they're using an internal address. */
log_fn(warn_severity, LD_CONFIG, "Address '%s' resolves to private "
"IP address '%s'. Please set the Address config option to be "
- "the IP address you want to use.", hostname, tmpbuf);
+ "the IP address you want to use.", hostname, addr_string);
+ tor_free(addr_string);
return -1;
}
}
- log_debug(LD_CONFIG, "Resolved Address to '%s'.", tmpbuf);
- *addr_out = ntohl(in.s_addr);
+ log_debug(LD_CONFIG, "Resolved Address to '%s'.", fmt_addr32(addr));
+ *addr_out = addr;
if (last_resolved_addr && last_resolved_addr != *addr_out) {
/* Leave this as a notice, regardless of the requested severity,
* at least until dynamic IP address support becomes bulletproof. */
log_notice(LD_NET,
"Your IP address seems to have changed to %s. Updating.",
- tmpbuf);
+ addr_string);
ip_address_changed(0);
}
if (last_resolved_addr != *addr_out) {
@@@ -2504,12 -2457,11 +2505,12 @@@
}
control_event_server_status(LOG_NOTICE,
"EXTERNAL_ADDRESS ADDRESS=%s METHOD=%s %s%s",
- tmpbuf, method, h?"HOSTNAME=":"", h);
+ addr_string, method, h?"HOSTNAME=":"", h);
}
last_resolved_addr = *addr_out;
if (hostname_out)
*hostname_out = tor_strdup(hostname);
+ tor_free(addr_string);
return 0;
}
@@@ -2916,10 -2868,6 +2917,10 @@@ compute_publishserverdescriptor(or_opti
* will generate too many circuits and potentially overload the network. */
#define MIN_CIRCUIT_STREAM_TIMEOUT 10
+/** Lowest allowable value for HeartbeatPeriod; if this is too low, we might
+ * expose more information than we're comfortable with. */
+#define MIN_HEARTBEAT_PERIOD (30*60)
+
/** Return 0 if every setting in <b>options</b> is reasonable, and a
* permissible transition from <b>old_options</b>. Else return -1.
* Should have no side effects, except for normalizing the contents of
@@@ -3120,24 -3068,17 +3121,24 @@@ options_validate(or_options_t *old_opti
routerset_union(options->_ExcludeExitNodesUnion,options->ExcludeNodes);
}
+ if (options->NodeFamilies) {
+ options->NodeFamilySets = smartlist_create();
+ for (cl = options->NodeFamilies; cl; cl = cl->next) {
+ routerset_t *rs = routerset_new();
+ if (routerset_parse(rs, cl->value, cl->key) == 0) {
+ smartlist_add(options->NodeFamilySets, rs);
+ } else {
+ routerset_free(rs);
+ }
+ }
+ }
+
if (options->ExcludeNodes && options->StrictNodes) {
COMPLAIN("You have asked to exclude certain relays from all positions "
"in your circuits. Expect hidden services and other Tor "
"features to be broken in unpredictable ways.");
}
- if (options->EntryNodes && !routerset_is_list(options->EntryNodes)) {
- /* XXXX fix this; see entry_guards_prepend_from_config(). */
- REJECT("IPs or countries are not yet supported in EntryNodes.");
- }
-
if (options->AuthoritativeDir) {
if (!options->ContactInfo && !options->TestingTorNetwork)
REJECT("Authoritative directory servers must set ContactInfo");
@@@ -3382,13 -3323,6 +3383,13 @@@
options->CircuitStreamTimeout = MIN_CIRCUIT_STREAM_TIMEOUT;
}
+ if (options->HeartbeatPeriod &&
+ options->HeartbeatPeriod < MIN_HEARTBEAT_PERIOD) {
+ log_warn(LD_CONFIG, "HeartbeatPeriod option is too short; "
+ "raising to %d seconds.", MIN_HEARTBEAT_PERIOD);
+ options->HeartbeatPeriod = MIN_HEARTBEAT_PERIOD;
+ }
+
if (options->KeepalivePeriod < 1)
REJECT("KeepalivePeriod option must be positive.");
@@@ -3607,12 -3541,8 +3608,12 @@@
if (check_nickname_list(options->MyFamily, "MyFamily", msg))
return -1;
for (cl = options->NodeFamilies; cl; cl = cl->next) {
- if (check_nickname_list(cl->value, "NodeFamily", msg))
+ routerset_t *rs = routerset_new();
+ if (routerset_parse(rs, cl->value, cl->key)) {
+ routerset_free(rs);
return -1;
+ }
+ routerset_free(rs);
}
if (validate_addr_policies(options, msg) < 0)
@@@ -3888,7 -3818,8 +3889,8 @@@ options_transition_affects_workers(or_o
old_options->SafeLogging != new_options->SafeLogging ||
old_options->ClientOnly != new_options->ClientOnly ||
public_server_mode(old_options) != public_server_mode(new_options) ||
- !config_lines_eq(old_options->Logs, new_options->Logs))
+ !config_lines_eq(old_options->Logs, new_options->Logs) ||
+ old_options->LogMessageDomains != new_options->LogMessageDomains)
return 1;
/* Check whether log options match. */
@@@ -4105,8 -4036,6 +4107,8 @@@ load_torrc_from_disk(int argc, char **a
"Unable to open configuration file \"%s\".", fname);
goto err;
}
+ } else {
+ log(LOG_NOTICE, LD_CONFIG, "Read configuration file \"%s\".", fname);
}
return cf;
@@@ -4395,35 -4324,6 +4397,35 @@@ options_init_logs(or_options_t *options
options->RunAsDaemon;
#endif
+ if (options->LogTimeGranularity <= 0) {
+ log_warn(LD_CONFIG, "Log time granularity '%d' has to be positive.",
+ options->LogTimeGranularity);
+ return -1;
+ } else if (1000 % options->LogTimeGranularity != 0 &&
+ options->LogTimeGranularity % 1000 != 0) {
+ int granularity = options->LogTimeGranularity;
+ if (granularity < 40) {
+ do granularity++;
+ while (1000 % granularity != 0);
+ } else if (granularity < 1000) {
+ granularity = 1000 / granularity;
+ while (1000 % granularity != 0)
+ granularity--;
+ granularity = 1000 / granularity;
+ } else {
+ granularity = 1000 * ((granularity / 1000) + 1);
+ }
+ log_warn(LD_CONFIG, "Log time granularity '%d' has to be either a "
+ "divisor or a multiple of 1 second. Changing to "
+ "'%d'.",
+ options->LogTimeGranularity, granularity);
+ if (!validate_only)
+ set_log_time_granularity(granularity);
+ } else {
+ if (!validate_only)
+ set_log_time_granularity(options->LogTimeGranularity);
+ }
+
ok = 1;
elts = smartlist_create();
@@@ -4495,6 -4395,9 +4497,9 @@@
}
smartlist_free(elts);
+ if (ok && !validate_only)
+ logs_set_domain_logging(options->LogMessageDomains);
+
return ok?0:-1;
}
@@@ -4912,26 -4815,6 +4917,26 @@@ static struct unit_table_t time_units[
{ NULL, 0 },
};
+/** Table to map the names of time units to the number of milliseconds
+ * they contain. */
+static struct unit_table_t time_msec_units[] = {
+ { "", 1 },
+ { "msec", 1 },
+ { "millisecond", 1 },
+ { "milliseconds", 1 },
+ { "second", 1000 },
+ { "seconds", 1000 },
+ { "minute", 60*1000 },
+ { "minutes", 60*1000 },
+ { "hour", 60*60*1000 },
+ { "hours", 60*60*1000 },
+ { "day", 24*60*60*1000 },
+ { "days", 24*60*60*1000 },
+ { "week", 7*24*60*60*1000 },
+ { "weeks", 7*24*60*60*1000 },
+ { NULL, 0 },
+};
+
/** Parse a string <b>val</b> containing a number, zero or more
* spaces, and an optional unit string. If the unit appears in the
* table <b>u</b>, then multiply the number by the unit multiplier.
@@@ -4995,25 -4878,6 +5000,25 @@@ config_parse_memunit(const char *s, in
return u;
}
+/** Parse a string in the format "number unit", where unit is a unit of
+ * time in milliseconds. On success, set *<b>ok</b> to true and return
+ * the number of milliseconds in the provided interval. Otherwise, set
+ * *<b>ok</b> to 0 and return -1. */
+static int
+config_parse_msec_interval(const char *s, int *ok)
+{
+ uint64_t r;
+ r = config_parse_units(s, time_msec_units, ok);
+ if (!ok)
+ return -1;
+ if (r > INT_MAX) {
+ log_warn(LD_CONFIG, "Msec interval '%s' is too long", s);
+ *ok = 0;
+ return -1;
+ }
+ return (int)r;
+}
+
/** Parse a string in the format "number unit", where unit is a unit of time.
* On success, set *<b>ok</b> to true and return the number of seconds in
* the provided interval. Otherwise, set *<b>ok</b> to 0 and return -1.
@@@ -5033,29 -4897,13 +5038,29 @@@ config_parse_interval(const char *s, in
return (int)r;
}
+/** Return the number of cpus configured in <b>options</b>. If we are
+ * told to auto-detect the number of cpus, return the auto-detected number. */
+int
+get_num_cpus(const or_options_t *options)
+{
+ if (options->NumCPUs == 0) {
+ int n = compute_num_cpus();
+ return (n >= 1) ? n : 1;
+ } else {
+ return options->NumCPUs;
+ }
+}
+
/**
* Initialize the libevent library.
*/
static void
-init_libevent(void)
+init_libevent(const or_options_t *options)
{
const char *badness=NULL;
+ tor_libevent_cfg cfg;
+
+ tor_assert(options);
configure_libevent_logging();
/* If the kernel complains that some method (say, epoll) doesn't
@@@ -5065,11 -4913,7 +5070,11 @@@
tor_check_libevent_header_compatibility();
- tor_libevent_initialize();
+ memset(&cfg, 0, sizeof(cfg));
+ cfg.disable_iocp = options->DisableIOCP;
+ cfg.num_cpus = get_num_cpus(options);
+
+ tor_libevent_initialize(&cfg);
suppress_libevent_log_msg(NULL);
@@@ -5410,7 -5254,6 +5415,7 @@@ getinfo_helper_config(control_connectio
case CONFIG_TYPE_FILENAME: type = "Filename"; break;
case CONFIG_TYPE_UINT: type = "Integer"; break;
case CONFIG_TYPE_INTERVAL: type = "TimeInterval"; break;
+ case CONFIG_TYPE_MSEC_INTERVAL: type = "TimeMsecInterval"; break;
case CONFIG_TYPE_MEMUNIT: type = "DataSize"; break;
case CONFIG_TYPE_DOUBLE: type = "Float"; break;
case CONFIG_TYPE_BOOL: type = "Boolean"; break;
diff --combined src/or/or.h
index 90f01e1,2a55668..1617d94
--- a/src/or/or.h
+++ b/src/or/or.h
@@@ -83,13 -83,6 +83,13 @@@
#define snprintf _snprintf
#endif
+#ifdef USE_BUFFEREVENTS
+#include <event2/bufferevent.h>
+#include <event2/buffer.h>
+#include <event2/util.h>
+#endif
+
+#include "crypto.h"
#include "tortls.h"
#include "../common/torlog.h"
#include "container.h"
@@@ -391,9 -384,7 +391,9 @@@ typedef enum
/** A connection to a hidden service directory server: download a v2 rendezvous
* descriptor. */
#define DIR_PURPOSE_FETCH_RENDDESC_V2 18
-#define _DIR_PURPOSE_MAX 18
+/** A connection to a directory server: download a microdescriptor. */
+#define DIR_PURPOSE_FETCH_MICRODESC 19
+#define _DIR_PURPOSE_MAX 19
/** True iff <b>p</b> is a purpose corresponding to uploading data to a
* directory server. */
@@@ -814,9 -805,6 +814,9 @@@ typedef enum
* Tor 0.1.2.x is obsolete, we can remove this. */
#define DEFAULT_CLIENT_NICKNAME "client"
+/** Name chosen by routers that don't configure nicknames */
+#define UNNAMED_ROUTER_NICKNAME "Unnamed"
+
/** Number of bytes in a SOCKS4 header. */
#define SOCKS4_NETWORK_LEN 8
@@@ -862,8 -850,8 +862,8 @@@ typedef struct cell_t
typedef struct var_cell_t {
uint8_t command;
circid_t circ_id;
- uint16_t payload_len;
- uint8_t payload[1];
+ uint16_t payload_len; /**< The actual length of <b>payload</b>. */
+ uint8_t payload[FLEXIBLE_ARRAY_MEMBER];
} var_cell_t;
/** A cell as packed for writing to the network. */
@@@ -980,7 -968,6 +980,7 @@@ typedef struct connection_t
/** Our socket; -1 if this connection is closed, or has no socket. */
evutil_socket_t s;
int conn_array_index; /**< Index into the global connection array. */
+
struct event *read_event; /**< Libevent event structure. */
struct event *write_event; /**< Libevent event structure. */
buf_t *inbuf; /**< Buffer holding data read over this connection. */
@@@ -991,11 -978,6 +991,11 @@@
* read? */
time_t timestamp_lastwritten; /**< When was the last time libevent said we
* could write? */
+
+#ifdef USE_BUFFEREVENTS
+ struct bufferevent *bufev; /**< A Libevent buffered IO structure. */
+#endif
+
time_t timestamp_created; /**< When was this connection_t created? */
/* XXXX_IP6 make this IPv6-capable */
@@@ -1095,16 -1077,10 +1095,16 @@@ typedef struct or_connection_t
/* bandwidth* and *_bucket only used by ORs in OPEN state: */
int bandwidthrate; /**< Bytes/s added to the bucket. (OPEN ORs only.) */
int bandwidthburst; /**< Max bucket size for this conn. (OPEN ORs only.) */
+#ifndef USE_BUFFEREVENTS
int read_bucket; /**< When this hits 0, stop receiving. Every second we
* add 'bandwidthrate' to this, capping it at
* bandwidthburst. (OPEN ORs only) */
int write_bucket; /**< When this hits 0, stop writing. Like read_bucket. */
+#else
+ /** DOCDOC */
+ /* XXXX we could share this among all connections. */
+ struct ev_token_bucket_cfg *bucket_cfg;
+#endif
int n_circuits; /**< How many circuits use this connection as p_conn or
* n_conn ? */
@@@ -1212,13 -1188,8 +1212,13 @@@ typedef struct edge_connection_t
typedef struct dir_connection_t {
connection_t _base;
- char *requested_resource; /**< Which 'resource' did we ask the directory
- * for? */
+ /** Which 'resource' did we ask the directory for? This is typically the part
+ * of the URL string that defines, relative to the directory conn purpose,
+ * what thing we want. For example, in router descriptor downloads by
+ * descriptor digest, it contains "d/", then one ore more +-separated
+ * fingerprints.
+ **/
+ char *requested_resource;
unsigned int dirconn_direct:1; /**< Is this dirconn direct, or via Tor? */
/* Used only for server sides of some dir connections, to implement
@@@ -1309,51 -1280,6 +1309,51 @@@ static INLINE control_connection_t *TO_
return DOWNCAST(control_connection_t, c);
}
+/* Conditional macros to help write code that works whether bufferevents are
+ disabled or not.
+
+ We can't just write:
+ if (conn->bufev) {
+ do bufferevent stuff;
+ } else {
+ do other stuff;
+ }
+ because the bufferevent stuff won't even compile unless we have a fairly
+ new version of Libevent. Instead, we say:
+ IF_HAS_BUFFEREVENT(conn, { do_bufferevent_stuff } );
+ or:
+ IF_HAS_BUFFEREVENT(conn, {
+ do bufferevent stuff;
+ }) ELSE_IF_NO_BUFFEREVENT {
+ do non-bufferevent stuff;
+ }
+ If we're compiling with bufferevent support, then the macros expand more or
+ less to:
+ if (conn->bufev) {
+ do_bufferevent_stuff;
+ } else {
+ do non-bufferevent stuff;
+ }
+ and if we aren't using bufferevents, they expand more or less to:
+ { do non-bufferevent stuff; }
+*/
+#ifdef USE_BUFFEREVENTS
+#define HAS_BUFFEREVENT(c) (((c)->bufev) != NULL)
+#define IF_HAS_BUFFEREVENT(c, stmt) \
+ if ((c)->bufev) do { \
+ stmt ; \
+ } while (0)
+#define ELSE_IF_NO_BUFFEREVENT ; else
+#define IF_HAS_NO_BUFFEREVENT(c) \
+ if (NULL == (c)->bufev)
+#else
+#define HAS_BUFFEREVENT(c) (0)
+#define IF_HAS_BUFFEREVENT(c, stmt) (void)0
+#define ELSE_IF_NO_BUFFEREVENT ;
+#define IF_HAS_NO_BUFFEREVENT(c) \
+ if (1)
+#endif
+
/** What action type does an address policy indicate: accept or reject? */
typedef enum {
ADDR_POLICY_ACCEPT=1,
@@@ -1517,49 -1443,59 +1517,49 @@@ typedef struct
char *contact_info; /**< Declared contact info for this router. */
unsigned int is_hibernating:1; /**< Whether the router claims to be
* hibernating */
- unsigned int has_old_dnsworkers:1; /**< Whether the router is using
- * dnsworker code. */
- unsigned int caches_extra_info:1; /**< Whether the router caches and serves
- * extrainfo documents. */
- unsigned int allow_single_hop_exits:1; /**< Whether the router allows
- * single hop exits. */
-
- /* local info */
- unsigned int is_running:1; /**< As far as we know, is this OR currently
- * running? */
- unsigned int is_valid:1; /**< Has a trusted dirserver validated this OR?
- * (For Authdir: Have we validated this OR?)
- */
- unsigned int is_named:1; /**< Do we believe the nickname that this OR gives
- * us? */
- unsigned int is_fast:1; /** Do we think this is a fast OR? */
- unsigned int is_stable:1; /** Do we think this is a stable OR? */
- unsigned int is_possible_guard:1; /**< Do we think this is an OK guard? */
- unsigned int is_exit:1; /**< Do we think this is an OK exit? */
- unsigned int is_bad_exit:1; /**< Do we think this exit is censored, borked,
- * or otherwise nasty? */
- unsigned int is_bad_directory:1; /**< Do we think this directory is junky,
- * underpowered, or otherwise useless? */
+ unsigned int caches_extra_info:1; /**< Whether the router says it caches and
+ * serves extrainfo documents. */
+ unsigned int allow_single_hop_exits:1; /**< Whether the router says
+ * it allows single hop exits. */
+
unsigned int wants_to_be_hs_dir:1; /**< True iff this router claims to be
* a hidden service directory. */
- unsigned int is_hs_dir:1; /**< True iff this router is a hidden service
- * directory according to the authorities. */
unsigned int policy_is_reject_star:1; /**< True iff the exit policy for this
* router rejects everything. */
/** True if, after we have added this router, we should re-launch
* tests for it. */
unsigned int needs_retest_if_added:1;
-/** Tor can use this router for general positions in circuits. */
+/** Tor can use this router for general positions in circuits; we got it
+ * from a directory server as usual, or we're an authority and a server
+ * uploaded it. */
#define ROUTER_PURPOSE_GENERAL 0
-/** Tor should avoid using this router for circuit-building. */
+/** Tor should avoid using this router for circuit-building: we got it
+ * from a crontroller. If the controller wants to use it, it'll have to
+ * ask for it by identity. */
#define ROUTER_PURPOSE_CONTROLLER 1
-/** Tor should use this router only for bridge positions in circuits. */
+/** Tor should use this router only for bridge positions in circuits: we got
+ * it via a directory request from the bridge itself, or a bridge
+ * authority. x*/
#define ROUTER_PURPOSE_BRIDGE 2
/** Tor should not use this router; it was marked in cached-descriptors with
* a purpose we didn't recognize. */
#define ROUTER_PURPOSE_UNKNOWN 255
- uint8_t purpose; /** What positions in a circuit is this router good for? */
+ /* In what way did we find out about this router? One of ROUTER_PURPOSE_*.
+ * Routers of different purposes are kept segregated and used for different
+ * things; see notes on ROUTER_PURPOSE_* macros above.
+ */
+ uint8_t purpose;
/* The below items are used only by authdirservers for
* reachability testing. */
+
/** When was the last time we could reach this OR? */
time_t last_reachable;
/** When did we start testing reachability for this OR? */
time_t testing_since;
- /** According to the geoip db what country is this router in? */
- country_t country;
+
} routerinfo_t;
/** Information needed to keep and cache a signed extra-info document. */
@@@ -1585,9 -1521,8 +1585,9 @@@ typedef struct routerstatus_t
* has. */
char identity_digest[DIGEST_LEN]; /**< Digest of the router's identity
* key. */
- char descriptor_digest[DIGEST_LEN]; /**< Digest of the router's most recent
- * descriptor. */
+ /** Digest of the router's most recent descriptor or microdescriptor.
+ * If it's a descriptor, we only use the first DIGEST_LEN bytes. */
+ char descriptor_digest[DIGEST256_LEN];
uint32_t addr; /**< IPv4 address for this router. */
uint16_t or_port; /**< OR port for this router. */
uint16_t dir_port; /**< Directory port for this router. */
@@@ -1595,11 -1530,7 +1595,11 @@@
unsigned int is_exit:1; /**< True iff this router is a good exit. */
unsigned int is_stable:1; /**< True iff this router stays up a long time. */
unsigned int is_fast:1; /**< True iff this router has good bandwidth. */
- unsigned int is_running:1; /**< True iff this router is up. */
+ /** True iff this router is called 'running' in the consensus. We give it
+ * this funny name so that we don't accidentally use this bit as a view of
+ * whether we think the router is *currently* running. If that's what you
+ * want to know, look at is_running in node_t. */
+ unsigned int is_flagged_running:1;
unsigned int is_named:1; /**< True iff "nickname" belongs to this router. */
unsigned int is_unnamed:1; /**< True iff "nickname" belongs to another
* router. */
@@@ -1651,31 -1582,15 +1651,31 @@@
* from this authority.) Applies in v2 networkstatus document only.
*/
unsigned int need_to_mirror:1;
- unsigned int name_lookup_warned:1; /**< Have we warned the user for referring
- * to this (unnamed) router by nickname?
- */
time_t last_dir_503_at; /**< When did this router last tell us that it
* was too busy to serve directory info? */
download_status_t dl_status;
} routerstatus_t;
+/** A single entry in a parsed policy summary, describing a range of ports. */
+typedef struct short_policy_entry_t {
+ uint16_t min_port, max_port;
+} short_policy_entry_t;
+
+/** A short_poliy_t is the parsed version of a policy summary. */
+typedef struct short_policy_t {
+ /** True if the members of 'entries' are port ranges to accept; false if
+ * they are port ranges to reject */
+ unsigned int is_accept : 1;
+ /** The actual number of values in 'entries'. */
+ unsigned int n_entries : 31;
+ /** An array of 0 or more short_policy_entry_t values, each describing a
+ * range of ports that this policy accepts or rejects (depending on the
+ * value of is_accept).
+ */
+ short_policy_entry_t entries[FLEXIBLE_ARRAY_MEMBER];
+} short_policy_t;
+
/** A microdescriptor is the smallest amount of information needed to build a
* circuit through a router. They are generated by the directory authorities,
* using information from the uploaded routerinfo documents. They are not
@@@ -1717,83 -1632,15 +1717,83 @@@ typedef struct microdesc_t
crypto_pk_env_t *onion_pkey;
/** As routerinfo_t.family */
smartlist_t *family;
- /** Encoded exit policy summary */
- char *exitsummary; /**< exit policy summary -
- * XXX this probably should not stay a string. */
+ /** Exit policy summary */
+ short_policy_t *exit_policy;
} microdesc_t;
+/** A node_t represents a Tor router.
+ *
+ * Specifically, a node_t is a Tor router as we are using it: a router that
+ * we are considering for circuits, connections, and so on. A node_t is a
+ * thin wrapper around the routerstatus, routerinfo, and microdesc for a
+ * single wrapper, and provides a consistent interface for all of them.
+ *
+ * Also, a node_t has mutable state. While a routerinfo, a routerstatus,
+ * and a microdesc have[*] only the information read from a router
+ * descriptor, a consensus entry, and a microdescriptor (respectively)...
+ * a node_t has flags based on *our own current opinion* of the node.
+ *
+ * [*] Actually, there is some leftover information in each that is mutable.
+ * We should try to excise that.
+ */
+typedef struct node_t {
+ /* Indexing information */
+
+ /** Used to look up the node_t by its identity digest. */
+ HT_ENTRY(node_t) ht_ent;
+ /** Position of the node within the list of nodes */
+ int nodelist_idx;
+
+ /** The identity digest of this node_t. No more than one node_t per
+ * identity may exist at a time. */
+ char identity[DIGEST_LEN];
+
+ microdesc_t *md;
+ routerinfo_t *ri;
+ routerstatus_t *rs;
+
+ /* local info: copied from routerstatus, then possibly frobbed based
+ * on experience. Authorities set this stuff directly. */
+
+ unsigned int is_running:1; /**< As far as we know, is this OR currently
+ * running? */
+ unsigned int is_valid:1; /**< Has a trusted dirserver validated this OR?
+ * (For Authdir: Have we validated this OR?)
+ */
+ unsigned int is_fast:1; /** Do we think this is a fast OR? */
+ unsigned int is_stable:1; /** Do we think this is a stable OR? */
+ unsigned int is_possible_guard:1; /**< Do we think this is an OK guard? */
+ unsigned int is_exit:1; /**< Do we think this is an OK exit? */
+ unsigned int is_bad_exit:1; /**< Do we think this exit is censored, borked,
+ * or otherwise nasty? */
+ unsigned int is_bad_directory:1; /**< Do we think this directory is junky,
+ * underpowered, or otherwise useless? */
+ unsigned int is_hs_dir:1; /**< True iff this router is a hidden service
+ * directory according to the authorities. */
+
+ /* Local info: warning state. */
+
+ unsigned int name_lookup_warned:1; /**< Have we warned the user for referring
+ * to this (unnamed) router by nickname?
+ */
+
+ /** Local info: we treat this node as if it rejects everything */
+ unsigned int rejects_all:1;
+
+ /* Local info: derived. */
+
+ /** According to the geoip db what country is this router in? */
+ country_t country;
+} node_t;
+
/** How many times will we try to download a router's descriptor before giving
* up? */
#define MAX_ROUTERDESC_DOWNLOAD_FAILURES 8
+/** How many times will we try to download a microdescriptor before giving
+ * up? */
+#define MAX_MICRODESC_DOWNLOAD_FAILURES 8
+
/** Contents of a v2 (non-consensus, non-vote) network status object. */
typedef struct networkstatus_v2_t {
/** When did we receive the network-status document? */
@@@ -2269,12 -2116,10 +2269,12 @@@ typedef struct circuit_t
* length ONIONSKIN_CHALLENGE_LEN. */
char *n_conn_onionskin;
- time_t timestamp_created; /**< When was this circuit created? */
+ /** When was this circuit created? We keep this timestamp with a higher
+ * resolution than most so that the circuit-build-time tracking code can
+ * get millisecond resolution. */
+ struct timeval timestamp_created;
time_t timestamp_dirty; /**< When the circuit was first used, or 0 if the
* circuit is clean. */
- struct timeval highres_created; /**< When exactly was the circuit created? */
uint16_t marked_for_close; /**< Should we close this circuit at the end of
* the main loop? (If true, holds the line number
@@@ -2499,8 -2344,10 +2499,11 @@@ typedef struct
config_line_t *Logs; /**< New-style list of configuration lines
* for logs */
+ int LogTimeGranularity; /**< Log resolution in milliseconds. */
+ int LogMessageDomains; /**< Boolean: Should we log the domain(s) in which
+ * each log message occurs? */
+
char *DebugLogFile; /**< Where to send verbose log messages. */
char *DataDirectory; /**< OR only: where to store long-term data. */
char *Nickname; /**< OR only: nickname of this onion router. */
@@@ -2719,9 -2566,6 +2722,9 @@@
* authorizations for hidden services */
char *ContactInfo; /**< Contact info to be published in the directory. */
+ int HeartbeatPeriod; /**< Log heartbeat messages after this many seconds
+ * have passed. */
+
char *HTTPProxy; /**< hostname[:port] to use as http proxy, if any. */
tor_addr_t HTTPProxyAddr; /**< Parsed IPv4 addr for http proxy, if any. */
uint16_t HTTPProxyPort; /**< Parsed port for http proxy, if any. */
@@@ -2759,8 -2603,7 +2762,8 @@@
char *MyFamily; /**< Declared family for this OR. */
config_line_t *NodeFamilies; /**< List of config lines for
- * node families */
+ * node families */
+ smartlist_t *NodeFamilySets; /**< List of parsed NodeFamilies values. */
config_line_t *AuthDirBadDir; /**< Address policy for descriptors to
* mark as bad dir mirrors. */
config_line_t *AuthDirBadExit; /**< Address policy for descriptors to
@@@ -2865,10 -2708,6 +2868,10 @@@
* possible. */
int PreferTunneledDirConns; /**< If true, avoid dirservers that don't
* support BEGIN_DIR, when possible. */
+ int PortForwarding; /**< If true, use NAT-PMP or UPnP to automatically
+ * forward the DirPort and ORPort on the NAT device */
+ char *PortForwardingHelper; /** < Filename or full path of the port
+ forwarding helper executable */
int AllowNonRFC953Hostnames; /**< If true, we allow connections to hostnames
* with weird characters. */
/** If true, we try resolving hostnames with weird characters. */
@@@ -2906,9 -2745,6 +2909,9 @@@
/** If true, the user wants us to collect statistics on port usage. */
int ExitPortStatistics;
+ /** If true, the user wants us to collect connection statistics. */
+ int ConnDirectionStatistics;
+
/** If true, the user wants us to collect cell statistics. */
int CellStatistics;
@@@ -3005,12 -2841,6 +3008,12 @@@
*/
double CircuitPriorityHalflife;
+ /** If true, do not enable IOCP on windows with bufferevents, even if
+ * we think we could. */
+ int DisableIOCP;
+ /** For testing only: will go away in 0.2.3.x. */
+ int _UseFilteringSSLBufferevents;
+
} or_options_t;
/** Persistent state for an onion router, as saved to disk. */
@@@ -3119,6 -2949,8 +3122,6 @@@ struct socks_request_t
* every connection. */
};
-/* all the function prototypes go here */
-
/********************************* circuitbuild.c **********************/
/** How many hops does a general-purpose circuit have by default? */
@@@ -3510,7 -3342,7 +3513,7 @@@ typedef enum
ADDR_POLICY_PROBABLY_ACCEPTED=1,
/** Part of the address was unknown, but as far as we can tell, it was
* rejected. */
- ADDR_POLICY_PROBABLY_REJECTED=2
+ ADDR_POLICY_PROBABLY_REJECTED=2,
} addr_policy_result_t;
/********************************* rephist.c ***************************/
@@@ -3641,8 -3473,6 +3644,8 @@@ typedef struct trusted_dir_server_t
* fetches to _any_ single directory server.]
*/
#define PDS_NO_EXISTING_SERVERDESC_FETCH (1<<3)
+#define PDS_NO_EXISTING_MICRODESC_FETCH (1<<4)
+
#define _PDS_PREFER_TUNNELED_DIR_CONNS (1<<16)
/** Possible ways to weight routers when choosing one randomly. See
@@@ -3660,8 -3490,7 +3663,8 @@@ typedef enum
CRN_NEED_GUARD = 1<<2,
CRN_ALLOW_INVALID = 1<<3,
/* XXXX not used, apparently. */
- CRN_WEIGHT_AS_EXIT = 1<<5
+ CRN_WEIGHT_AS_EXIT = 1<<5,
+ CRN_NEED_DESC = 1<<6
} router_crn_flags_t;
/** Return value for router_add_to_routerlist() and dirserv_add_descriptor() */
1
0

[tor/master] That shalt also not have a label without a statement.
by nickm@torproject.org 22 Feb '11
by nickm@torproject.org 22 Feb '11
22 Feb '11
commit ce149c10227bd4d65bfa62898e729430981328c1
Author: Nick Mathewson <nickm(a)torproject.org>
Date: Tue Feb 22 12:52:52 2011 -0500
That shalt also not have a label without a statement.
---
src/common/log.c | 1 +
1 files changed, 1 insertions(+), 0 deletions(-)
diff --git a/src/common/log.c b/src/common/log.c
index 4b21fd9..cfa0721 100644
--- a/src/common/log.c
+++ b/src/common/log.c
@@ -248,6 +248,7 @@ format_msg(char *buf, size_t buf_len,
format_msg_no_room_for_domains:
/* This will leave end_of_prefix and n unchanged, and thus cause
* whatever log domain string we had written to be clobbered. */
+ ;
}
if (funcname && should_log_function_name(domain, severity)) {
1
0
commit e261a1a3e6513eeafa1b53b83ebfec7f5d834a39
Author: Nick Mathewson <nickm(a)torproject.org>
Date: Tue Jan 25 15:03:36 2011 -0500
Simplify syntax for negated log domains
Previously if you wanted to say "All messages except network
messages", you needed to say "[*,~net]" and if you said "[~net]" by
mistake, you would get no messages at all. Now, if you say "[~net]",
you get everything except networking messages.
---
changes/log_domains | 6 +++++-
doc/tor.1.txt | 2 +-
src/common/log.c | 5 ++++-
3 files changed, 10 insertions(+), 3 deletions(-)
diff --git a/changes/log_domains b/changes/log_domains
index f4cfe6f..939b9a9 100644
--- a/changes/log_domains
+++ b/changes/log_domains
@@ -1,5 +1,9 @@
- o Documentation
+ o Minor features
+ - Make it simpler to specify "All log domains except for A and B".
+ Previously you needed to say "[*,~A,~B]". Now you can just say
+ "[~A,~B]".
+ o Documentation
- Add documentation for configuring logging at different severities in
different log domains. We've had this feature since 0.2.1.1-alpha, but
for some reason it never made it into the manpage. Fixes bug 2215.
diff --git a/doc/tor.1.txt b/doc/tor.1.txt
index 9a7ee07..17cdf37 100644
--- a/doc/tor.1.txt
+++ b/doc/tor.1.txt
@@ -341,7 +341,7 @@ Other options can be specified either on the command-line (--option
protocol, mm, http, app, control, circ, rend, bug, dir, dirserv, or, edge,
acct, hist, and handshake. Domain names are case-insensitive. +
+
- For example, "`Log [handshake]debug [*,~net,~mm]info notice stdout`" sends
+ For example, "`Log [handshake]debug [~net,~mm]info notice stdout`" sends
to stdout: all handshake messages of any severity, all info-and-higher
messages from domains other than networking and memory management, and all
messages of severity notice or higher.
diff --git a/src/common/log.c b/src/common/log.c
index 2fef2cc..28fca4e 100644
--- a/src/common/log.c
+++ b/src/common/log.c
@@ -919,7 +919,10 @@ parse_log_severity_config(const char **cfg_ptr,
smartlist_free(domains_list);
if (err)
return -1;
- domains &= ~neg_domains;
+ if (domains == 0 && neg_domains)
+ domains = ~neg_domains;
+ else
+ domains &= ~neg_domains;
cfg = eat_whitespace(closebracket+1);
} else {
++got_an_unqualified_range;
1
0

22 Feb '11
commit 0ab8b7c0f22bd45d7108ce0185e027cd8e469593
Author: Robert Ransom <rransom.8774(a)gmail.com>
Date: Fri Feb 4 05:50:44 2011 -0800
Thou shalt not overflow even stupidly small buffers
---
src/common/log.c | 10 ++++++++++
1 files changed, 10 insertions(+), 0 deletions(-)
diff --git a/src/common/log.c b/src/common/log.c
index f58b05b..4b21fd9 100644
--- a/src/common/log.c
+++ b/src/common/log.c
@@ -223,21 +223,31 @@ format_msg(char *buf, size_t buf_len,
size_t n;
int r;
char *end_of_prefix;
+ char *buf_end;
assert(buf_len >= 16); /* prevent integer underflow and general stupidity */
buf_len -= 2; /* subtract 2 characters so we have room for \n\0 */
+ buf_end = buf+buf_len; /* point *after* the last char we can write to */
n = _log_prefix(buf, buf_len, severity);
end_of_prefix = buf+n;
if (log_domains_are_logged) {
char *cp = buf+n;
+ if (cp == buf_end) goto format_msg_no_room_for_domains;
*cp++ = '{';
+ if (cp == buf_end) goto format_msg_no_room_for_domains;
cp = domain_to_string(domain, cp, (buf+buf_len-cp));
+ if (cp == buf_end) goto format_msg_no_room_for_domains;
*cp++ = '}';
+ if (cp == buf_end) goto format_msg_no_room_for_domains;
*cp++ = ' ';
+ if (cp == buf_end) goto format_msg_no_room_for_domains;
end_of_prefix = cp;
n = cp-buf;
+ format_msg_no_room_for_domains:
+ /* This will leave end_of_prefix and n unchanged, and thus cause
+ * whatever log domain string we had written to be clobbered. */
}
if (funcname && should_log_function_name(domain, severity)) {
1
0
commit 89ee779f928af4ad31ad6d45936c6a386e263584
Author: Nick Mathewson <nickm(a)torproject.org>
Date: Tue Jan 25 15:53:15 2011 -0500
Add a torrc option to report log domains
---
changes/log_domains | 3 ++
doc/tor.1.txt | 5 +++
src/common/log.c | 76 +++++++++++++++++++++++++++++++++++++++++---------
src/common/torlog.h | 1 +
src/or/config.c | 7 ++++-
src/or/or.h | 3 ++
6 files changed, 80 insertions(+), 15 deletions(-)
diff --git a/changes/log_domains b/changes/log_domains
index 939b9a9..7fc0506 100644
--- a/changes/log_domains
+++ b/changes/log_domains
@@ -2,6 +2,9 @@
- Make it simpler to specify "All log domains except for A and B".
Previously you needed to say "[*,~A,~B]". Now you can just say
"[~A,~B]".
+ - Add a LogMessageDomains option to include the domains of log messages
+ along with the messages. Without this, there's no way to use
+ log domains without reading the source or doing a lot of guessing
o Documentation
- Add documentation for configuring logging at different severities in
diff --git a/doc/tor.1.txt b/doc/tor.1.txt
index 17cdf37..a4ab0d9 100644
--- a/doc/tor.1.txt
+++ b/doc/tor.1.txt
@@ -346,6 +346,11 @@ Other options can be specified either on the command-line (--option
messages from domains other than networking and memory management, and all
messages of severity notice or higher.
+**LogMessageDomains** **0**|**1**::
+ If 1, Tor includes message domains with each log message. Every log
+ message currently has at least one domain; most currently have exactly
+ one. This doesn't affect controller log messages. (Default: 0)
+
**OutboundBindAddress** __IP__::
Make all outbound connections originate from the IP address specified. This
is only useful when you have multiple network interfaces, and you want all
diff --git a/src/common/log.c b/src/common/log.c
index 28fca4e..f58b05b 100644
--- a/src/common/log.c
+++ b/src/common/log.c
@@ -97,6 +97,9 @@ static int log_mutex_initialized = 0;
/** Linked list of logfile_t. */
static logfile_t *logfiles = NULL;
+/** Boolean: do we report logging domains? */
+static int log_domains_are_logged = 0;
+
#ifdef HAVE_SYSLOG_H
/** The number of open syslog log handlers that we have. When this reaches 0,
* we can close our connection to the syslog facility. */
@@ -126,6 +129,9 @@ int _log_global_min_severity = LOG_NOTICE;
static void delete_log(logfile_t *victim);
static void close_log(logfile_t *victim);
+static char *domain_to_string(log_domain_mask_t domain,
+ char *buf, size_t buflen);
+
/** Name of the application: used to generate the message we write at the
* start of each new log. */
static char *appname = NULL;
@@ -218,12 +224,22 @@ format_msg(char *buf, size_t buf_len,
int r;
char *end_of_prefix;
- assert(buf_len >= 2); /* prevent integer underflow */
+ assert(buf_len >= 16); /* prevent integer underflow and general stupidity */
buf_len -= 2; /* subtract 2 characters so we have room for \n\0 */
n = _log_prefix(buf, buf_len, severity);
end_of_prefix = buf+n;
+ if (log_domains_are_logged) {
+ char *cp = buf+n;
+ *cp++ = '{';
+ cp = domain_to_string(domain, cp, (buf+buf_len-cp));
+ *cp++ = '}';
+ *cp++ = ' ';
+ end_of_prefix = cp;
+ n = cp-buf;
+ }
+
if (funcname && should_log_function_name(domain, severity)) {
r = tor_snprintf(buf+n, buf_len-n, "%s(): ", funcname);
if (r<0)
@@ -305,6 +321,7 @@ logv(int severity, log_domain_mask_t domain, const char *funcname,
&msg_len);
formatted = 1;
}
+
if (lf->is_syslog) {
#ifdef HAVE_SYSLOG_H
char *m = end_of_prefix;
@@ -563,8 +580,7 @@ add_stream_log_impl(const log_severity_list_t *severity,
* to <b>fd</b>. Steals a reference to <b>severity</b>; the caller must
* not use it after calling this function. */
void
-add_stream_log(const log_severity_list_t *severity,
- const char *name, int fd)
+add_stream_log(const log_severity_list_t *severity, const char *name, int fd)
{
LOCK_LOGS();
add_stream_log_impl(severity, name, fd);
@@ -583,6 +599,16 @@ init_logging(void)
pending_cb_messages = smartlist_create();
}
+/** Set whether we report logging domains as a part of our log messages.
+ */
+void
+logs_set_domain_logging(int enabled)
+{
+ LOCK_LOGS();
+ log_domains_are_logged = enabled;
+ UNLOCK_LOGS();
+}
+
/** Add a log handler to receive messages during startup (before the real
* logs are initialized).
*/
@@ -775,7 +801,6 @@ add_syslog_log(const log_severity_list_t *severity)
lf->fd = -1;
lf->severities = tor_memdup(severity, sizeof(log_severity_list_t));
lf->filename = tor_strdup("<syslog>");
-
lf->is_syslog = 1;
LOCK_LOGS();
@@ -832,18 +857,41 @@ parse_log_domain(const char *domain)
}
return 0;
}
-#if 0
-/** Translate a bitmask of log domains to a string, or NULL if the bitmask
- * is undecodable. */
-static const char *
-domain_to_string(log_domain_mask_t domain)
+
+/** Translate a bitmask of log domains to a string. */
+static char *
+domain_to_string(log_domain_mask_t domain, char *buf, size_t buflen)
{
- int bit = tor_log2(domain);
- if ((bit == 0 && domain == 0) || bit >= N_LOGGING_DOMAINS)
- return NULL;
- return domain_list[bit];
+ char *cp = buf;
+ char *eos = buf+buflen;
+
+ buf[0] = '\0';
+ if (! domain)
+ return buf;
+ while (1) {
+ const char *d;
+ int bit = tor_log2(domain);
+ size_t n;
+ if (bit >= N_LOGGING_DOMAINS) {
+ tor_snprintf(buf, buflen, "<BUG:Unknown domain %lx>", (long)domain);
+ return buf+strlen(buf);
+ }
+ d = domain_list[bit];
+ n = strlcpy(cp, d, eos-cp);
+ if (n >= buflen) {
+ tor_snprintf(buf, buflen, "<BUG:Truncating domain %lx>", (long)domain);
+ return buf+strlen(buf);
+ }
+ cp += n;
+ domain &= ~(1<<bit);
+
+ if (domain == 0 || (eos-cp) < 2)
+ return cp;
+
+ memcpy(cp, ",", 2); /*Nul-terminated ,"*/
+ cp++;
+ }
}
-#endif
/** Parse a log severity pattern in *<b>cfg_ptr</b>. Advance cfg_ptr after
* the end of the severityPattern. Set the value of <b>severity_out</b> to
diff --git a/src/common/torlog.h b/src/common/torlog.h
index f0be732..791e363 100644
--- a/src/common/torlog.h
+++ b/src/common/torlog.h
@@ -132,6 +132,7 @@ int add_file_log(const log_severity_list_t *severity, const char *filename);
int add_syslog_log(const log_severity_list_t *severity);
#endif
int add_callback_log(const log_severity_list_t *severity, log_callback cb);
+void logs_set_domain_logging(int enabled);
int get_min_log_level(void);
void switch_logs_debug(void);
void logs_free_all(void);
diff --git a/src/or/config.c b/src/or/config.c
index 8c1205d..5600ac5 100644
--- a/src/or/config.c
+++ b/src/or/config.c
@@ -287,6 +287,7 @@ static config_var_t _option_vars[] = {
OBSOLETE("IgnoreVersion"),
V(KeepalivePeriod, INTERVAL, "5 minutes"),
VAR("Log", LINELIST, Logs, NULL),
+ V(LogMessageDomains, BOOL, "0"),
OBSOLETE("LinkPadding"),
OBSOLETE("LogLevel"),
OBSOLETE("LogFile"),
@@ -3811,7 +3812,8 @@ options_transition_affects_workers(or_options_t *old_options,
old_options->SafeLogging != new_options->SafeLogging ||
old_options->ClientOnly != new_options->ClientOnly ||
public_server_mode(old_options) != public_server_mode(new_options) ||
- !config_lines_eq(old_options->Logs, new_options->Logs))
+ !config_lines_eq(old_options->Logs, new_options->Logs) ||
+ old_options->LogMessageDomains != new_options->LogMessageDomains)
return 1;
/* Check whether log options match. */
@@ -4387,6 +4389,9 @@ options_init_logs(or_options_t *options, int validate_only)
}
smartlist_free(elts);
+ if (ok && !validate_only)
+ logs_set_domain_logging(options->LogMessageDomains);
+
return ok?0:-1;
}
diff --git a/src/or/or.h b/src/or/or.h
index 22c8498..7bccf83 100644
--- a/src/or/or.h
+++ b/src/or/or.h
@@ -2338,6 +2338,9 @@ typedef struct {
config_line_t *Logs; /**< New-style list of configuration lines
* for logs */
+ int LogMessageDomains; /**< Boolean: Should we log the domain(s) in which
+ * each log message occurs? */
+
char *DebugLogFile; /**< Where to send verbose log messages. */
char *DataDirectory; /**< OR only: where to store long-term data. */
char *Nickname; /**< OR only: nickname of this onion router. */
1
0