diff options
author | Nick Mathewson <nickm@torproject.org> | 2011-06-22 12:27:27 -0400 |
---|---|---|
committer | Nick Mathewson <nickm@torproject.org> | 2011-09-07 15:01:52 -0400 |
commit | 1f4b6944c06fce5befc3b8a21d252ba946632f63 (patch) | |
tree | 102518e3d0007bd12bae27ddfe626c80ebd754d5 | |
parent | 41eef6680e814f453cc8eedff415e941429aa627 (diff) | |
download | tor-1f4b6944c06fce5befc3b8a21d252ba946632f63.tar tor-1f4b6944c06fce5befc3b8a21d252ba946632f63.tar.gz |
Upload descriptors more often when recent desc is unlisted
Right now we only force a new descriptor upload every 18 hours.
This can make servers become unlisted if they upload a descriptor at
time T which the authorities reject as being "too similar" to one
they uploaded before. Nothing will actually make the server upload a
new descriptor later on, until another 18 hours have passed.
This patch changes the upload behavior so that the 18 hour interval
applies only when we're listed in a live consensus with a descriptor
published within the last 18 hours. Otherwise--if we're not listed
in the live consensus, or if we're listed with a publication time
over 18 hours in the past--we upload a new descriptor every 90
minutes.
This is an attempted bugfix for #3327. If we merge it, it should
obsolete #535.
-rw-r--r-- | changes/bug3327 | 8 | ||||
-rw-r--r-- | src/or/main.c | 6 | ||||
-rw-r--r-- | src/or/router.c | 44 | ||||
-rw-r--r-- | src/or/router.h | 2 |
4 files changed, 51 insertions, 9 deletions
diff --git a/changes/bug3327 b/changes/bug3327 new file mode 100644 index 000000000..32a8b9cd0 --- /dev/null +++ b/changes/bug3327 @@ -0,0 +1,8 @@ + o Major features: + - Relays now try regenerating and uploading their descriptor more + frequently if they are not listed in the consensus, or if the + version of their descriptor listed in the consensus is too + old. This fix should prevent situations where a server declines + to re-publish itself because it has done so too recently, even + though the authorities decided not to list its recent-enough + descriptor. Fix for bug 3327. diff --git a/src/or/main.c b/src/or/main.c index 2cdbe71f1..af769c412 100644 --- a/src/or/main.c +++ b/src/or/main.c @@ -1326,11 +1326,7 @@ run_scheduled_events(time_t now) time_to_check_ipaddress = now + CHECK_IPADDRESS_INTERVAL; check_descriptor_ipaddress_changed(now); } -/** If our router descriptor ever goes this long without being regenerated - * because something changed, we force an immediate regenerate-and-upload. */ -#define FORCE_REGENERATE_DESCRIPTOR_INTERVAL (18*60*60) - mark_my_descriptor_dirty_if_older_than( - now - FORCE_REGENERATE_DESCRIPTOR_INTERVAL); + mark_my_descriptor_dirty_if_too_old(now); consider_publishable_server(0); /* also, check religiously for reachability, if it's within the first * 20 minutes of our uptime. */ diff --git a/src/or/router.c b/src/or/router.c index 531d3fb40..ccaa1398f 100644 --- a/src/or/router.c +++ b/src/or/router.c @@ -1610,12 +1610,50 @@ router_rebuild_descriptor(int force) return 0; } -/** Mark descriptor out of date if it's older than <b>when</b> */ +/** If our router descriptor ever goes this long without being regenerated + * because something changed, we force an immediate regenerate-and-upload. */ +#define FORCE_REGENERATE_DESCRIPTOR_INTERVAL (18*60*60) + +/** If our router descriptor seems to be missing or unacceptable according + * to the authorities, regenerate and reupload it _this_ often. */ +#define FAST_RETRY_DESCRIPTOR_INTERVAL (90*60) + +/** Mark descriptor out of date if it's been "too long" since we last tried + * to upload one. */ void -mark_my_descriptor_dirty_if_older_than(time_t when) +mark_my_descriptor_dirty_if_too_old(time_t now) { - if (desc_clean_since < when) + networkstatus_t *ns; + routerstatus_t *rs; + const char *retry_fast_reason = NULL; /* Set if we should retry frequently */ + const time_t slow_cutoff = now - FORCE_REGENERATE_DESCRIPTOR_INTERVAL; + const time_t fast_cutoff = now - FAST_RETRY_DESCRIPTOR_INTERVAL; + + /* If it's already dirty, don't mark it. */ + if (! desc_clean_since) + return; + + /* If it's older than FORCE_REGENERATE_DESCRIPTOR_INTERVAL, it's always + * time to rebuild it. */ + if (desc_clean_since < slow_cutoff) { mark_my_descriptor_dirty("time for new descriptor"); + return; + } + /* Now we see whether we want to be retrying frequently or no. The + * rule here is that we'll retry frequently if we aren't listed in the + * live consensus we have, or if the publication time of the + * descriptor listed for us in the consensus is very old. */ + ns = networkstatus_get_live_consensus(now); + if (ns) { + rs = networkstatus_vote_find_entry(ns, server_identitykey_digest); + if (rs == NULL) + retry_fast_reason = "not listed in consensus"; + else if (rs->published_on < slow_cutoff) + retry_fast_reason = "version listed in consensus is quite old"; + } + + if (retry_fast_reason && desc_clean_since < fast_cutoff) + mark_my_descriptor_dirty(retry_fast_reason); } /** Call when the current descriptor is out of date. */ diff --git a/src/or/router.h b/src/or/router.h index f6d3c1233..af202e60c 100644 --- a/src/or/router.h +++ b/src/or/router.h @@ -62,7 +62,7 @@ void consider_publishable_server(int force); int should_refuse_unknown_exits(const or_options_t *options); void router_upload_dir_desc_to_dirservers(int force); -void mark_my_descriptor_dirty_if_older_than(time_t when); +void mark_my_descriptor_dirty_if_too_old(time_t now); void mark_my_descriptor_dirty(const char *reason); void check_descriptor_bandwidth_changed(time_t now); void check_descriptor_ipaddress_changed(time_t now); |