aboutsummaryrefslogtreecommitdiff
path: root/src/or
diff options
context:
space:
mode:
authorNick Mathewson <nickm@torproject.org>2013-02-08 12:09:46 -0500
committerNick Mathewson <nickm@torproject.org>2013-02-08 12:09:46 -0500
commit2403ef66bada5f1fb851ce424af4ab5916faca67 (patch)
treed3a87fbcb87492d02b0cd17537ee625d5d3eb5d4 /src/or
parent194bd56c8a4d6bdb49f6896712bae422887975e2 (diff)
downloadtor-2403ef66bada5f1fb851ce424af4ab5916faca67.tar
tor-2403ef66bada5f1fb851ce424af4ab5916faca67.tar.gz
Coalesce identical adjacent microdescriptor vote lines.
Diffstat (limited to 'src/or')
-rw-r--r--src/or/dirvote.c55
1 files changed, 45 insertions, 10 deletions
diff --git a/src/or/dirvote.c b/src/or/dirvote.c
index baaff488d..c10a60fa7 100644
--- a/src/or/dirvote.c
+++ b/src/or/dirvote.c
@@ -3664,31 +3664,66 @@ static const struct consensus_method_range_t {
{-1, -1}
};
+typedef struct microdesc_vote_line_t {
+ int low;
+ int high;
+ microdesc_t *md;
+ struct microdesc_vote_line_t *next;
+} microdesc_vote_line_t;
+
vote_microdesc_hash_t *
dirvote_format_all_microdesc_vote_lines(const routerinfo_t *ri, time_t now,
smartlist_t *microdescriptors_out)
{
const struct consensus_method_range_t *cmr;
+ microdesc_vote_line_t *entries = NULL, *ep;
vote_microdesc_hash_t *result = NULL;
+ /* Generate the microdescriptors. */
for (cmr = microdesc_consensus_methods;
cmr->low != -1 && cmr->high != -1;
cmr++) {
microdesc_t *md = dirvote_create_microdescriptor(ri, cmr->low);
if (md) {
- char buf[128];
- vote_microdesc_hash_t *h;
- dirvote_format_microdesc_vote_line(buf, sizeof(buf), md,
- cmr->low, cmr->high);
- h = tor_malloc_zero(sizeof(vote_microdesc_hash_t));
- h->microdesc_hash_line = tor_strdup(buf);
- h->next = result;
- result = h;
- md->last_listed = now;
- smartlist_add(microdescriptors_out, md);
+ microdesc_vote_line_t *e =
+ tor_malloc_zero(sizeof(microdesc_vote_line_t));
+ e->md = md;
+ e->low = cmr->low;
+ e->high = cmr->high;
+ e->next = entries;
+ entries = e;
}
}
+ /* Compress adjacent identical ones */
+ for (ep = entries; ep; ep = ep->next) {
+ while (ep->next &&
+ fast_memeq(ep->md->digest, ep->next->md->digest, DIGEST256_LEN) &&
+ ep->low == ep->next->high + 1) {
+ microdesc_vote_line_t *next = ep->next;
+ ep->low = next->low;
+ microdesc_free(next->md);
+ ep->next = next->next;
+ tor_free(next);
+ }
+ }
+
+ /* Format them into vote_microdesc_hash_t, and add to microdescriptors_out.*/
+ while ((ep = entries)) {
+ char buf[128];
+ vote_microdesc_hash_t *h;
+ dirvote_format_microdesc_vote_line(buf, sizeof(buf), ep->md,
+ ep->low, ep->high);
+ h = tor_malloc_zero(sizeof(vote_microdesc_hash_t));
+ h->microdesc_hash_line = tor_strdup(buf);
+ h->next = result;
+ result = h;
+ ep->md->last_listed = now;
+ smartlist_add(microdescriptors_out, ep->md);
+ entries = ep->next;
+ tor_free(ep);
+ }
+
return result;
}